1 /****************************************************************************** 2 * 3 * Copyright (C) 1999-2012 Broadcom Corporation 4 * 5 * Licensed under the Apache License, Version 2.0 (the "License"); 6 * you may not use this file except in compliance with the License. 7 * You may obtain a copy of the License at: 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 * 17 ******************************************************************************/ 18 #include "_OverrideLog.h" 19 20 #include <android/hardware/nfc/1.0/INfc.h> 21 #include <android/hardware/nfc/1.0/INfcClientCallback.h> 22 #include <hwbinder/ProcessState.h> 23 #include <pthread.h> 24 #include "NfcAdaptation.h" 25 extern "C" { 26 #include "gki.h" 27 #include "nfa_api.h" 28 #include "nfc_int.h" 29 #include "vendor_cfg.h" 30 } 31 #include "android_logmsg.h" 32 #include "config.h" 33 34 #undef LOG_TAG 35 #define LOG_TAG "NfcAdaptation" 36 37 using android::OK; 38 using android::sp; 39 using android::status_t; 40 41 using android::hardware::ProcessState; 42 using android::hardware::Return; 43 using android::hardware::Void; 44 using android::hardware::nfc::V1_0::INfc; 45 using android::hardware::nfc::V1_0::INfcClientCallback; 46 using android::hardware::hidl_vec; 47 48 extern "C" void GKI_shutdown(); 49 extern void resetConfig(); 50 extern "C" void verify_stack_non_volatile_store(); 51 extern "C" void delete_stack_non_volatile_store(bool forceDelete); 52 53 NfcAdaptation* NfcAdaptation::mpInstance = NULL; 54 ThreadMutex NfcAdaptation::sLock; 55 tHAL_NFC_CBACK* NfcAdaptation::mHalCallback = NULL; 56 tHAL_NFC_DATA_CBACK* NfcAdaptation::mHalDataCallback = NULL; 57 ThreadCondVar NfcAdaptation::mHalOpenCompletedEvent; 58 ThreadCondVar NfcAdaptation::mHalCloseCompletedEvent; 59 sp<INfc> NfcAdaptation::mHal; 60 INfcClientCallback* NfcAdaptation::mCallback; 61 62 uint32_t ScrProtocolTraceFlag = SCR_PROTO_TRACE_ALL; // 0x017F00; 63 uint8_t appl_trace_level = 0xff; 64 char bcm_nfc_location[120]; 65 66 static uint8_t nfa_dm_cfg[sizeof(tNFA_DM_CFG)]; 67 static uint8_t nfa_proprietary_cfg[sizeof(tNFA_PROPRIETARY_CFG)]; 68 extern tNFA_DM_CFG* p_nfa_dm_cfg; 69 extern tNFA_PROPRIETARY_CFG* p_nfa_proprietary_cfg; 70 extern uint8_t nfa_ee_max_ee_cfg; 71 extern const uint8_t nfca_version_string[]; 72 extern const uint8_t nfa_version_string[]; 73 static uint8_t deviceHostWhiteList[NFA_HCI_MAX_HOST_IN_NETWORK]; 74 static tNFA_HCI_CFG jni_nfa_hci_cfg; 75 extern tNFA_HCI_CFG* p_nfa_hci_cfg; 76 extern bool nfa_poll_bail_out_mode; 77 78 class NfcClientCallback : public INfcClientCallback { 79 public: 80 NfcClientCallback(tHAL_NFC_CBACK* eventCallback, 81 tHAL_NFC_DATA_CBACK dataCallback) { 82 mEventCallback = eventCallback; 83 mDataCallback = dataCallback; 84 }; 85 virtual ~NfcClientCallback() = default; 86 Return<void> sendEvent( 87 ::android::hardware::nfc::V1_0::NfcEvent event, 88 ::android::hardware::nfc::V1_0::NfcStatus event_status) override { 89 mEventCallback((uint8_t)event, (tHAL_NFC_STATUS)event_status); 90 return Void(); 91 }; 92 Return<void> sendData( 93 const ::android::hardware::nfc::V1_0::NfcData& data) override { 94 ::android::hardware::nfc::V1_0::NfcData copy = data; 95 mDataCallback(copy.size(), ©[0]); 96 return Void(); 97 }; 98 99 private: 100 tHAL_NFC_CBACK* mEventCallback; 101 tHAL_NFC_DATA_CBACK* mDataCallback; 102 }; 103 104 /******************************************************************************* 105 ** 106 ** Function: NfcAdaptation::NfcAdaptation() 107 ** 108 ** Description: class constructor 109 ** 110 ** Returns: none 111 ** 112 *******************************************************************************/ 113 NfcAdaptation::NfcAdaptation() { 114 memset(&mHalEntryFuncs, 0, sizeof(mHalEntryFuncs)); 115 } 116 117 /******************************************************************************* 118 ** 119 ** Function: NfcAdaptation::~NfcAdaptation() 120 ** 121 ** Description: class destructor 122 ** 123 ** Returns: none 124 ** 125 *******************************************************************************/ 126 NfcAdaptation::~NfcAdaptation() { mpInstance = NULL; } 127 128 /******************************************************************************* 129 ** 130 ** Function: NfcAdaptation::GetInstance() 131 ** 132 ** Description: access class singleton 133 ** 134 ** Returns: pointer to the singleton object 135 ** 136 *******************************************************************************/ 137 NfcAdaptation& NfcAdaptation::GetInstance() { 138 AutoThreadMutex a(sLock); 139 140 if (!mpInstance) mpInstance = new NfcAdaptation; 141 return *mpInstance; 142 } 143 144 /******************************************************************************* 145 ** 146 ** Function: NfcAdaptation::Initialize() 147 ** 148 ** Description: class initializer 149 ** 150 ** Returns: none 151 ** 152 *******************************************************************************/ 153 void NfcAdaptation::Initialize() { 154 const char* func = "NfcAdaptation::Initialize"; 155 ALOGD("%s: enter", func); 156 ALOGE("%s: ver=%s nfa=%s", func, nfca_version_string, nfa_version_string); 157 unsigned long num; 158 159 if (GetNumValue(NAME_USE_RAW_NCI_TRACE, &num, sizeof(num))) { 160 if (num == 1) { 161 // display protocol traces in raw format 162 ProtoDispAdapterUseRawOutput(TRUE); 163 ALOGD("%s: logging protocol in raw format", func); 164 } 165 } 166 if (!GetStrValue(NAME_NFA_STORAGE, bcm_nfc_location, 167 sizeof(bcm_nfc_location))) { 168 strlcpy(bcm_nfc_location, "/data/nfc", sizeof(bcm_nfc_location)); 169 } 170 171 initializeProtocolLogLevel(); 172 173 if (GetStrValue(NAME_NFA_DM_CFG, (char*)nfa_dm_cfg, sizeof(nfa_dm_cfg))) 174 p_nfa_dm_cfg = (tNFA_DM_CFG*)&nfa_dm_cfg[0]; 175 176 if (GetNumValue(NAME_NFA_MAX_EE_SUPPORTED, &num, sizeof(num))) { 177 nfa_ee_max_ee_cfg = num; 178 ALOGD("%s: Overriding NFA_EE_MAX_EE_SUPPORTED to use %d", func, 179 nfa_ee_max_ee_cfg); 180 } 181 if (GetNumValue(NAME_NFA_POLL_BAIL_OUT_MODE, &num, sizeof(num))) { 182 nfa_poll_bail_out_mode = num; 183 ALOGD("%s: Overriding NFA_POLL_BAIL_OUT_MODE to use %d", func, 184 nfa_poll_bail_out_mode); 185 } 186 187 if (GetStrValue(NAME_NFA_PROPRIETARY_CFG, (char*)nfa_proprietary_cfg, 188 sizeof(tNFA_PROPRIETARY_CFG))) { 189 p_nfa_proprietary_cfg = (tNFA_PROPRIETARY_CFG*)&nfa_proprietary_cfg[0]; 190 } 191 192 // configure device host whitelist of HCI host ID's; see specification ETSI TS 193 // 102 622 V11.1.10 194 //(2012-10), section 6.1.3.1 195 num = GetStrValue(NAME_DEVICE_HOST_WHITE_LIST, (char*)deviceHostWhiteList, 196 sizeof(deviceHostWhiteList)); 197 if (num) { 198 memmove(&jni_nfa_hci_cfg, p_nfa_hci_cfg, sizeof(jni_nfa_hci_cfg)); 199 jni_nfa_hci_cfg.num_whitelist_host = 200 (uint8_t)num; // number of HCI host ID's in the whitelist 201 jni_nfa_hci_cfg.p_whitelist = deviceHostWhiteList; // array of HCI host 202 // ID's 203 p_nfa_hci_cfg = &jni_nfa_hci_cfg; 204 } 205 206 initializeGlobalAppLogLevel(); 207 208 verify_stack_non_volatile_store(); 209 if (GetNumValue(NAME_PRESERVE_STORAGE, (char*)&num, sizeof(num)) && 210 (num == 1)) 211 ALOGD("%s: preserve stack NV store", __func__); 212 else { 213 delete_stack_non_volatile_store(FALSE); 214 } 215 216 GKI_init(); 217 GKI_enable(); 218 GKI_create_task((TASKPTR)NFCA_TASK, BTU_TASK, (int8_t*)"NFCA_TASK", 0, 0, 219 (pthread_cond_t*)NULL, NULL); 220 { 221 AutoThreadMutex guard(mCondVar); 222 GKI_create_task((TASKPTR)Thread, MMI_TASK, (int8_t*)"NFCA_THREAD", 0, 0, 223 (pthread_cond_t*)NULL, NULL); 224 mCondVar.wait(); 225 } 226 227 mHalCallback = NULL; 228 memset(&mHalEntryFuncs, 0, sizeof(mHalEntryFuncs)); 229 InitializeHalDeviceContext(); 230 ALOGD("%s: exit", func); 231 } 232 233 /******************************************************************************* 234 ** 235 ** Function: NfcAdaptation::Finalize() 236 ** 237 ** Description: class finalizer 238 ** 239 ** Returns: none 240 ** 241 *******************************************************************************/ 242 void NfcAdaptation::Finalize() { 243 const char* func = "NfcAdaptation::Finalize"; 244 AutoThreadMutex a(sLock); 245 246 ALOGD("%s: enter", func); 247 GKI_shutdown(); 248 249 resetConfig(); 250 251 mCallback = NULL; 252 memset(&mHalEntryFuncs, 0, sizeof(mHalEntryFuncs)); 253 254 ALOGD("%s: exit", func); 255 delete this; 256 } 257 258 /******************************************************************************* 259 ** 260 ** Function: NfcAdaptation::signal() 261 ** 262 ** Description: signal the CondVar to release the thread that is waiting 263 ** 264 ** Returns: none 265 ** 266 *******************************************************************************/ 267 void NfcAdaptation::signal() { mCondVar.signal(); } 268 269 /******************************************************************************* 270 ** 271 ** Function: NfcAdaptation::NFCA_TASK() 272 ** 273 ** Description: NFCA_TASK runs the GKI main task 274 ** 275 ** Returns: none 276 ** 277 *******************************************************************************/ 278 uint32_t NfcAdaptation::NFCA_TASK(uint32_t arg) { 279 const char* func = "NfcAdaptation::NFCA_TASK"; 280 ALOGD("%s: enter", func); 281 GKI_run(0); 282 ALOGD("%s: exit", func); 283 return 0; 284 } 285 286 /******************************************************************************* 287 ** 288 ** Function: NfcAdaptation::Thread() 289 ** 290 ** Description: Creates work threads 291 ** 292 ** Returns: none 293 ** 294 *******************************************************************************/ 295 uint32_t NfcAdaptation::Thread(uint32_t arg) { 296 const char* func = "NfcAdaptation::Thread"; 297 ALOGD("%s: enter", func); 298 299 { 300 ThreadCondVar CondVar; 301 AutoThreadMutex guard(CondVar); 302 GKI_create_task((TASKPTR)nfc_task, NFC_TASK, (int8_t*)"NFC_TASK", 0, 0, 303 (pthread_cond_t*)CondVar, (pthread_mutex_t*)CondVar); 304 CondVar.wait(); 305 } 306 307 NfcAdaptation::GetInstance().signal(); 308 309 GKI_exit_task(GKI_get_taskid()); 310 ALOGD("%s: exit", func); 311 return 0; 312 } 313 314 /******************************************************************************* 315 ** 316 ** Function: NfcAdaptation::GetHalEntryFuncs() 317 ** 318 ** Description: Get the set of HAL entry points. 319 ** 320 ** Returns: Functions pointers for HAL entry points. 321 ** 322 *******************************************************************************/ 323 tHAL_NFC_ENTRY* NfcAdaptation::GetHalEntryFuncs() { return &mHalEntryFuncs; } 324 325 /******************************************************************************* 326 ** 327 ** Function: NfcAdaptation::InitializeHalDeviceContext 328 ** 329 ** Description: Ask the generic Android HAL to find the Broadcom-specific HAL. 330 ** 331 ** Returns: None. 332 ** 333 *******************************************************************************/ 334 void NfcAdaptation::InitializeHalDeviceContext() { 335 const char* func = "NfcAdaptation::InitializeHalDeviceContext"; 336 ALOGD("%s: enter", func); 337 int ret = 0; // 0 means success 338 339 mHalEntryFuncs.initialize = HalInitialize; 340 mHalEntryFuncs.terminate = HalTerminate; 341 mHalEntryFuncs.open = HalOpen; 342 mHalEntryFuncs.close = HalClose; 343 mHalEntryFuncs.core_initialized = HalCoreInitialized; 344 mHalEntryFuncs.write = HalWrite; 345 mHalEntryFuncs.prediscover = HalPrediscover; 346 mHalEntryFuncs.control_granted = HalControlGranted; 347 mHalEntryFuncs.power_cycle = HalPowerCycle; 348 mHalEntryFuncs.get_max_ee = HalGetMaxNfcee; 349 ALOGI("%s: INfc::getService()", func); 350 mHal = INfc::getService(); 351 LOG_FATAL_IF(mHal == nullptr, "Failed to retrieve the NFC HAL!"); 352 ALOGI("%s: INfc::getService() returned %p (%s)", func, mHal.get(), 353 (mHal->isRemote() ? "remote" : "local")); 354 ALOGD("%s: exit", func); 355 } 356 357 /******************************************************************************* 358 ** 359 ** Function: NfcAdaptation::HalInitialize 360 ** 361 ** Description: Not implemented because this function is only needed 362 ** within the HAL. 363 ** 364 ** Returns: None. 365 ** 366 *******************************************************************************/ 367 void NfcAdaptation::HalInitialize() { 368 const char* func = "NfcAdaptation::HalInitialize"; 369 ALOGD("%s", func); 370 } 371 372 /******************************************************************************* 373 ** 374 ** Function: NfcAdaptation::HalTerminate 375 ** 376 ** Description: Not implemented because this function is only needed 377 ** within the HAL. 378 ** 379 ** Returns: None. 380 ** 381 *******************************************************************************/ 382 void NfcAdaptation::HalTerminate() { 383 const char* func = "NfcAdaptation::HalTerminate"; 384 ALOGD("%s", func); 385 } 386 387 /******************************************************************************* 388 ** 389 ** Function: NfcAdaptation::HalOpen 390 ** 391 ** Description: Turn on controller, download firmware. 392 ** 393 ** Returns: None. 394 ** 395 *******************************************************************************/ 396 void NfcAdaptation::HalOpen(tHAL_NFC_CBACK* p_hal_cback, 397 tHAL_NFC_DATA_CBACK* p_data_cback) { 398 const char* func = "NfcAdaptation::HalOpen"; 399 ALOGD("%s", func); 400 mCallback = new NfcClientCallback(p_hal_cback, p_data_cback); 401 mHal->open(mCallback); 402 } 403 404 /******************************************************************************* 405 ** 406 ** Function: NfcAdaptation::HalClose 407 ** 408 ** Description: Turn off controller. 409 ** 410 ** Returns: None. 411 ** 412 *******************************************************************************/ 413 void NfcAdaptation::HalClose() { 414 const char* func = "NfcAdaptation::HalClose"; 415 ALOGD("%s", func); 416 mHal->close(); 417 } 418 419 /******************************************************************************* 420 ** 421 ** Function: NfcAdaptation::HalDeviceContextCallback 422 ** 423 ** Description: Translate generic Android HAL's callback into Broadcom-specific 424 ** callback function. 425 ** 426 ** Returns: None. 427 ** 428 *******************************************************************************/ 429 void NfcAdaptation::HalDeviceContextCallback(nfc_event_t event, 430 nfc_status_t event_status) { 431 const char* func = "NfcAdaptation::HalDeviceContextCallback"; 432 ALOGD("%s: event=%u", func, event); 433 if (mHalCallback) mHalCallback(event, (tHAL_NFC_STATUS)event_status); 434 } 435 436 /******************************************************************************* 437 ** 438 ** Function: NfcAdaptation::HalDeviceContextDataCallback 439 ** 440 ** Description: Translate generic Android HAL's callback into Broadcom-specific 441 ** callback function. 442 ** 443 ** Returns: None. 444 ** 445 *******************************************************************************/ 446 void NfcAdaptation::HalDeviceContextDataCallback(uint16_t data_len, 447 uint8_t* p_data) { 448 const char* func = "NfcAdaptation::HalDeviceContextDataCallback"; 449 ALOGD("%s: len=%u", func, data_len); 450 if (mHalDataCallback) mHalDataCallback(data_len, p_data); 451 } 452 453 /******************************************************************************* 454 ** 455 ** Function: NfcAdaptation::HalWrite 456 ** 457 ** Description: Write NCI message to the controller. 458 ** 459 ** Returns: None. 460 ** 461 *******************************************************************************/ 462 void NfcAdaptation::HalWrite(uint16_t data_len, uint8_t* p_data) { 463 const char* func = "NfcAdaptation::HalWrite"; 464 ALOGD("%s", func); 465 ::android::hardware::nfc::V1_0::NfcData data; 466 data.setToExternal(p_data, data_len); 467 mHal->write(data); 468 } 469 470 /******************************************************************************* 471 ** 472 ** Function: NfcAdaptation::HalCoreInitialized 473 ** 474 ** Description: Adjust the configurable parameters in the controller. 475 ** 476 ** Returns: None. 477 ** 478 *******************************************************************************/ 479 void NfcAdaptation::HalCoreInitialized(uint16_t data_len, 480 uint8_t* p_core_init_rsp_params) { 481 const char* func = "NfcAdaptation::HalCoreInitialized"; 482 ALOGD("%s", func); 483 hidl_vec<uint8_t> data; 484 data.setToExternal(p_core_init_rsp_params, data_len); 485 486 mHal->coreInitialized(data); 487 } 488 489 /******************************************************************************* 490 ** 491 ** Function: NfcAdaptation::HalPrediscover 492 ** 493 ** Description: Perform any vendor-specific pre-discovery actions (if 494 ** needed) If any actions were performed TRUE will be returned, 495 ** and HAL_PRE_DISCOVER_CPLT_EVT will notify when actions are 496 ** completed. 497 ** 498 ** Returns: TRUE if vendor-specific pre-discovery actions initialized 499 ** FALSE if no vendor-specific pre-discovery actions are 500 ** needed. 501 ** 502 *******************************************************************************/ 503 bool NfcAdaptation::HalPrediscover() { 504 const char* func = "NfcAdaptation::HalPrediscover"; 505 ALOGD("%s", func); 506 bool retval = FALSE; 507 mHal->prediscover(); 508 return retval; 509 } 510 511 /******************************************************************************* 512 ** 513 ** Function: HAL_NfcControlGranted 514 ** 515 ** Description: Grant control to HAL control for sending NCI commands. 516 ** Call in response to HAL_REQUEST_CONTROL_EVT. 517 ** Must only be called when there are no NCI commands pending. 518 ** HAL_RELEASE_CONTROL_EVT will notify when HAL no longer 519 ** needs control of NCI. 520 ** 521 ** Returns: void 522 ** 523 *******************************************************************************/ 524 void NfcAdaptation::HalControlGranted() { 525 const char* func = "NfcAdaptation::HalControlGranted"; 526 ALOGD("%s", func); 527 mHal->controlGranted(); 528 } 529 530 /******************************************************************************* 531 ** 532 ** Function: NfcAdaptation::HalPowerCycle 533 ** 534 ** Description: Turn off and turn on the controller. 535 ** 536 ** Returns: None. 537 ** 538 *******************************************************************************/ 539 void NfcAdaptation::HalPowerCycle() { 540 const char* func = "NfcAdaptation::HalPowerCycle"; 541 ALOGD("%s", func); 542 mHal->powerCycle(); 543 } 544 545 /******************************************************************************* 546 ** 547 ** Function: NfcAdaptation::HalGetMaxNfcee 548 ** 549 ** Description: Turn off and turn on the controller. 550 ** 551 ** Returns: None. 552 ** 553 *******************************************************************************/ 554 uint8_t NfcAdaptation::HalGetMaxNfcee() { 555 const char* func = "NfcAdaptation::HalPowerCycle"; 556 uint8_t maxNfcee = 0; 557 ALOGD("%s", func); 558 559 return nfa_ee_max_ee_cfg; 560 } 561 562 /******************************************************************************* 563 ** 564 ** Function: NfcAdaptation::DownloadFirmware 565 ** 566 ** Description: Download firmware patch files. 567 ** 568 ** Returns: None. 569 ** 570 *******************************************************************************/ 571 void NfcAdaptation::DownloadFirmware() { 572 const char* func = "NfcAdaptation::DownloadFirmware"; 573 ALOGD("%s: enter", func); 574 HalInitialize(); 575 576 mHalOpenCompletedEvent.lock(); 577 ALOGD("%s: try open HAL", func); 578 HalOpen(HalDownloadFirmwareCallback, HalDownloadFirmwareDataCallback); 579 mHalOpenCompletedEvent.wait(); 580 581 mHalCloseCompletedEvent.lock(); 582 ALOGD("%s: try close HAL", func); 583 HalClose(); 584 mHalCloseCompletedEvent.wait(); 585 586 HalTerminate(); 587 ALOGD("%s: exit", func); 588 } 589 590 /******************************************************************************* 591 ** 592 ** Function: NfcAdaptation::HalDownloadFirmwareCallback 593 ** 594 ** Description: Receive events from the HAL. 595 ** 596 ** Returns: None. 597 ** 598 *******************************************************************************/ 599 void NfcAdaptation::HalDownloadFirmwareCallback(nfc_event_t event, 600 nfc_status_t event_status) { 601 const char* func = "NfcAdaptation::HalDownloadFirmwareCallback"; 602 ALOGD("%s: event=0x%X", func, event); 603 switch (event) { 604 case HAL_NFC_OPEN_CPLT_EVT: { 605 ALOGD("%s: HAL_NFC_OPEN_CPLT_EVT", func); 606 mHalOpenCompletedEvent.signal(); 607 break; 608 } 609 case HAL_NFC_CLOSE_CPLT_EVT: { 610 ALOGD("%s: HAL_NFC_CLOSE_CPLT_EVT", func); 611 mHalCloseCompletedEvent.signal(); 612 break; 613 } 614 } 615 } 616 617 /******************************************************************************* 618 ** 619 ** Function: NfcAdaptation::HalDownloadFirmwareDataCallback 620 ** 621 ** Description: Receive data events from the HAL. 622 ** 623 ** Returns: None. 624 ** 625 *******************************************************************************/ 626 void NfcAdaptation::HalDownloadFirmwareDataCallback(uint16_t data_len, 627 uint8_t* p_data) {} 628 629 /******************************************************************************* 630 ** 631 ** Function: ThreadMutex::ThreadMutex() 632 ** 633 ** Description: class constructor 634 ** 635 ** Returns: none 636 ** 637 *******************************************************************************/ 638 ThreadMutex::ThreadMutex() { 639 pthread_mutexattr_t mutexAttr; 640 641 pthread_mutexattr_init(&mutexAttr); 642 pthread_mutex_init(&mMutex, &mutexAttr); 643 pthread_mutexattr_destroy(&mutexAttr); 644 } 645 646 /******************************************************************************* 647 ** 648 ** Function: ThreadMutex::~ThreadMutex() 649 ** 650 ** Description: class destructor 651 ** 652 ** Returns: none 653 ** 654 *******************************************************************************/ 655 ThreadMutex::~ThreadMutex() { pthread_mutex_destroy(&mMutex); } 656 657 /******************************************************************************* 658 ** 659 ** Function: ThreadMutex::lock() 660 ** 661 ** Description: lock kthe mutex 662 ** 663 ** Returns: none 664 ** 665 *******************************************************************************/ 666 void ThreadMutex::lock() { pthread_mutex_lock(&mMutex); } 667 668 /******************************************************************************* 669 ** 670 ** Function: ThreadMutex::unblock() 671 ** 672 ** Description: unlock the mutex 673 ** 674 ** Returns: none 675 ** 676 *******************************************************************************/ 677 void ThreadMutex::unlock() { pthread_mutex_unlock(&mMutex); } 678 679 /******************************************************************************* 680 ** 681 ** Function: ThreadCondVar::ThreadCondVar() 682 ** 683 ** Description: class constructor 684 ** 685 ** Returns: none 686 ** 687 *******************************************************************************/ 688 ThreadCondVar::ThreadCondVar() { 689 pthread_condattr_t CondAttr; 690 691 pthread_condattr_init(&CondAttr); 692 pthread_cond_init(&mCondVar, &CondAttr); 693 694 pthread_condattr_destroy(&CondAttr); 695 } 696 697 /******************************************************************************* 698 ** 699 ** Function: ThreadCondVar::~ThreadCondVar() 700 ** 701 ** Description: class destructor 702 ** 703 ** Returns: none 704 ** 705 *******************************************************************************/ 706 ThreadCondVar::~ThreadCondVar() { pthread_cond_destroy(&mCondVar); } 707 708 /******************************************************************************* 709 ** 710 ** Function: ThreadCondVar::wait() 711 ** 712 ** Description: wait on the mCondVar 713 ** 714 ** Returns: none 715 ** 716 *******************************************************************************/ 717 void ThreadCondVar::wait() { 718 pthread_cond_wait(&mCondVar, *this); 719 pthread_mutex_unlock(*this); 720 } 721 722 /******************************************************************************* 723 ** 724 ** Function: ThreadCondVar::signal() 725 ** 726 ** Description: signal the mCondVar 727 ** 728 ** Returns: none 729 ** 730 *******************************************************************************/ 731 void ThreadCondVar::signal() { 732 AutoThreadMutex a(*this); 733 pthread_cond_signal(&mCondVar); 734 } 735 736 /******************************************************************************* 737 ** 738 ** Function: AutoThreadMutex::AutoThreadMutex() 739 ** 740 ** Description: class constructor, automatically lock the mutex 741 ** 742 ** Returns: none 743 ** 744 *******************************************************************************/ 745 AutoThreadMutex::AutoThreadMutex(ThreadMutex& m) : mm(m) { mm.lock(); } 746 747 /******************************************************************************* 748 ** 749 ** Function: AutoThreadMutex::~AutoThreadMutex() 750 ** 751 ** Description: class destructor, automatically unlock the mutex 752 ** 753 ** Returns: none 754 ** 755 *******************************************************************************/ 756 AutoThreadMutex::~AutoThreadMutex() { mm.unlock(); } 757