ril.cpp revision 03c1edf23e76a83b95ac6847e333cb1329bbfa1d
1/* //device/libs/telephony/ril.cpp 2** 3** Copyright 2006, The Android Open Source Project 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#define LOG_TAG "RILC" 19 20#include <hardware_legacy/power.h> 21 22#include <telephony/ril.h> 23#include <telephony/ril_cdma_sms.h> 24#include <cutils/sockets.h> 25#include <cutils/jstring.h> 26#include <cutils/record_stream.h> 27#include <utils/Log.h> 28#include <utils/SystemClock.h> 29#include <pthread.h> 30#include <binder/Parcel.h> 31#include <cutils/jstring.h> 32 33#include <sys/types.h> 34#include <pwd.h> 35 36#include <stdio.h> 37#include <stdlib.h> 38#include <stdarg.h> 39#include <string.h> 40#include <unistd.h> 41#include <fcntl.h> 42#include <time.h> 43#include <errno.h> 44#include <assert.h> 45#include <ctype.h> 46#include <alloca.h> 47#include <sys/un.h> 48#include <assert.h> 49#include <netinet/in.h> 50#include <cutils/properties.h> 51 52#include <ril_event.h> 53 54namespace android { 55 56#define PHONE_PROCESS "radio" 57 58#define SOCKET_NAME_RIL "rild" 59#define SOCKET_NAME_RIL_DEBUG "rild-debug" 60 61#define ANDROID_WAKE_LOCK_NAME "radio-interface" 62 63 64#define PROPERTY_RIL_IMPL "gsm.version.ril-impl" 65 66// match with constant in RIL.java 67#define MAX_COMMAND_BYTES (8 * 1024) 68 69// Basically: memset buffers that the client library 70// shouldn't be using anymore in an attempt to find 71// memory usage issues sooner. 72#define MEMSET_FREED 1 73 74#define NUM_ELEMS(a) (sizeof (a) / sizeof (a)[0]) 75 76#define MIN(a,b) ((a)<(b) ? (a) : (b)) 77 78/* Constants for response types */ 79#define RESPONSE_SOLICITED 0 80#define RESPONSE_UNSOLICITED 1 81 82/* Negative values for private RIL errno's */ 83#define RIL_ERRNO_INVALID_RESPONSE -1 84 85// request, response, and unsolicited msg print macro 86#define PRINTBUF_SIZE 8096 87 88// Enable RILC log 89#define RILC_LOG 0 90 91#if RILC_LOG 92 #define startRequest sprintf(printBuf, "(") 93 #define closeRequest sprintf(printBuf, "%s)", printBuf) 94 #define printRequest(token, req) \ 95 LOGD("[%04d]> %s %s", token, requestToString(req), printBuf) 96 97 #define startResponse sprintf(printBuf, "%s {", printBuf) 98 #define closeResponse sprintf(printBuf, "%s}", printBuf) 99 #define printResponse LOGD("%s", printBuf) 100 101 #define clearPrintBuf printBuf[0] = 0 102 #define removeLastChar printBuf[strlen(printBuf)-1] = 0 103 #define appendPrintBuf(x...) sprintf(printBuf, x) 104#else 105 #define startRequest 106 #define closeRequest 107 #define printRequest(token, req) 108 #define startResponse 109 #define closeResponse 110 #define printResponse 111 #define clearPrintBuf 112 #define removeLastChar 113 #define appendPrintBuf(x...) 114#endif 115 116enum WakeType {DONT_WAKE, WAKE_PARTIAL}; 117 118typedef struct { 119 int requestNumber; 120 void (*dispatchFunction) (Parcel &p, struct RequestInfo *pRI); 121 int(*responseFunction) (Parcel &p, void *response, size_t responselen); 122} CommandInfo; 123 124typedef struct { 125 int requestNumber; 126 int (*responseFunction) (Parcel &p, void *response, size_t responselen); 127 WakeType wakeType; 128} UnsolResponseInfo; 129 130typedef struct RequestInfo { 131 int32_t token; //this is not RIL_Token 132 CommandInfo *pCI; 133 struct RequestInfo *p_next; 134 char cancelled; 135 char local; // responses to local commands do not go back to command process 136} RequestInfo; 137 138typedef struct UserCallbackInfo { 139 RIL_TimedCallback p_callback; 140 void *userParam; 141 struct ril_event event; 142 struct UserCallbackInfo *p_next; 143} UserCallbackInfo; 144 145 146/*******************************************************************/ 147 148RIL_RadioFunctions s_callbacks = {0, NULL, NULL, NULL, NULL, NULL}; 149static int s_registerCalled = 0; 150 151static pthread_t s_tid_dispatch; 152static pthread_t s_tid_reader; 153static int s_started = 0; 154 155static int s_fdListen = -1; 156static int s_fdCommand = -1; 157static int s_fdDebug = -1; 158 159static int s_fdWakeupRead; 160static int s_fdWakeupWrite; 161 162static struct ril_event s_commands_event; 163static struct ril_event s_wakeupfd_event; 164static struct ril_event s_listen_event; 165static struct ril_event s_wake_timeout_event; 166static struct ril_event s_debug_event; 167 168 169static const struct timeval TIMEVAL_WAKE_TIMEOUT = {1,0}; 170 171static pthread_mutex_t s_pendingRequestsMutex = PTHREAD_MUTEX_INITIALIZER; 172static pthread_mutex_t s_writeMutex = PTHREAD_MUTEX_INITIALIZER; 173static pthread_mutex_t s_startupMutex = PTHREAD_MUTEX_INITIALIZER; 174static pthread_cond_t s_startupCond = PTHREAD_COND_INITIALIZER; 175 176static pthread_mutex_t s_dispatchMutex = PTHREAD_MUTEX_INITIALIZER; 177static pthread_cond_t s_dispatchCond = PTHREAD_COND_INITIALIZER; 178 179static RequestInfo *s_pendingRequests = NULL; 180 181static RequestInfo *s_toDispatchHead = NULL; 182static RequestInfo *s_toDispatchTail = NULL; 183 184static UserCallbackInfo *s_last_wake_timeout_info = NULL; 185 186static void *s_lastNITZTimeData = NULL; 187static size_t s_lastNITZTimeDataSize; 188 189#if RILC_LOG 190 static char printBuf[PRINTBUF_SIZE]; 191#endif 192 193/*******************************************************************/ 194 195static void dispatchVoid (Parcel& p, RequestInfo *pRI); 196static void dispatchString (Parcel& p, RequestInfo *pRI); 197static void dispatchStrings (Parcel& p, RequestInfo *pRI); 198static void dispatchInts (Parcel& p, RequestInfo *pRI); 199static void dispatchDial (Parcel& p, RequestInfo *pRI); 200static void dispatchSIM_IO (Parcel& p, RequestInfo *pRI); 201static void dispatchCallForward(Parcel& p, RequestInfo *pRI); 202static void dispatchRaw(Parcel& p, RequestInfo *pRI); 203static void dispatchSmsWrite (Parcel &p, RequestInfo *pRI); 204 205static void dispatchCdmaSms(Parcel &p, RequestInfo *pRI); 206static void dispatchCdmaSmsAck(Parcel &p, RequestInfo *pRI); 207static void dispatchGsmBrSmsCnf(Parcel &p, RequestInfo *pRI); 208static void dispatchCdmaBrSmsCnf(Parcel &p, RequestInfo *pRI); 209static void dispatchRilCdmaSmsWriteArgs(Parcel &p, RequestInfo *pRI); 210static int responseInts(Parcel &p, void *response, size_t responselen); 211static int responseStrings(Parcel &p, void *response, size_t responselen); 212static int responseString(Parcel &p, void *response, size_t responselen); 213static int responseVoid(Parcel &p, void *response, size_t responselen); 214static int responseCallList(Parcel &p, void *response, size_t responselen); 215static int responseSMS(Parcel &p, void *response, size_t responselen); 216static int responseSIM_IO(Parcel &p, void *response, size_t responselen); 217static int responseCallForwards(Parcel &p, void *response, size_t responselen); 218static int responseDataCallList(Parcel &p, void *response, size_t responselen); 219static int responseRaw(Parcel &p, void *response, size_t responselen); 220static int responseSsn(Parcel &p, void *response, size_t responselen); 221static int responseSimStatus(Parcel &p, void *response, size_t responselen); 222static int responseGsmBrSmsCnf(Parcel &p, void *response, size_t responselen); 223static int responseCdmaBrSmsCnf(Parcel &p, void *response, size_t responselen); 224static int responseCdmaSms(Parcel &p, void *response, size_t responselen); 225static int responseCellList(Parcel &p, void *response, size_t responselen); 226static int responseCdmaInformationRecords(Parcel &p,void *response, size_t responselen); 227static int responseRilSignalStrength(Parcel &p,void *response, size_t responselen); 228static int responseCallRing(Parcel &p, void *response, size_t responselen); 229static int responseCdmaSignalInfoRecord(Parcel &p,void *response, size_t responselen); 230static int responseCdmaCallWaiting(Parcel &p,void *response, size_t responselen); 231 232extern "C" const char * requestToString(int request); 233extern "C" const char * failCauseToString(RIL_Errno); 234extern "C" const char * callStateToString(RIL_CallState); 235extern "C" const char * radioStateToString(RIL_RadioState); 236 237#ifdef RIL_SHLIB 238extern "C" void RIL_onUnsolicitedResponse(int unsolResponse, void *data, 239 size_t datalen); 240#endif 241 242static UserCallbackInfo * internalRequestTimedCallback 243 (RIL_TimedCallback callback, void *param, 244 const struct timeval *relativeTime); 245 246/** Index == requestNumber */ 247static CommandInfo s_commands[] = { 248#include "ril_commands.h" 249}; 250 251static UnsolResponseInfo s_unsolResponses[] = { 252#include "ril_unsol_commands.h" 253}; 254 255 256static char * 257strdupReadString(Parcel &p) { 258 size_t stringlen; 259 const char16_t *s16; 260 261 s16 = p.readString16Inplace(&stringlen); 262 263 return strndup16to8(s16, stringlen); 264} 265 266static void writeStringToParcel(Parcel &p, const char *s) { 267 char16_t *s16; 268 size_t s16_len; 269 s16 = strdup8to16(s, &s16_len); 270 p.writeString16(s16, s16_len); 271 free(s16); 272} 273 274 275static void 276memsetString (char *s) { 277 if (s != NULL) { 278 memset (s, 0, strlen(s)); 279 } 280} 281 282void nullParcelReleaseFunction (const uint8_t* data, size_t dataSize, 283 const size_t* objects, size_t objectsSize, 284 void* cookie) { 285 // do nothing -- the data reference lives longer than the Parcel object 286} 287 288/** 289 * To be called from dispatch thread 290 * Issue a single local request, ensuring that the response 291 * is not sent back up to the command process 292 */ 293static void 294issueLocalRequest(int request, void *data, int len) { 295 RequestInfo *pRI; 296 int ret; 297 298 pRI = (RequestInfo *)calloc(1, sizeof(RequestInfo)); 299 300 pRI->local = 1; 301 pRI->token = 0xffffffff; // token is not used in this context 302 pRI->pCI = &(s_commands[request]); 303 304 ret = pthread_mutex_lock(&s_pendingRequestsMutex); 305 assert (ret == 0); 306 307 pRI->p_next = s_pendingRequests; 308 s_pendingRequests = pRI; 309 310 ret = pthread_mutex_unlock(&s_pendingRequestsMutex); 311 assert (ret == 0); 312 313 LOGD("C[locl]> %s", requestToString(request)); 314 315 s_callbacks.onRequest(request, data, len, pRI); 316} 317 318 319 320static int 321processCommandBuffer(void *buffer, size_t buflen) { 322 Parcel p; 323 status_t status; 324 int32_t request; 325 int32_t token; 326 RequestInfo *pRI; 327 int ret; 328 329 p.setData((uint8_t *) buffer, buflen); 330 331 // status checked at end 332 status = p.readInt32(&request); 333 status = p.readInt32 (&token); 334 335 if (status != NO_ERROR) { 336 LOGE("invalid request block"); 337 return 0; 338 } 339 340 if (request < 1 || request >= (int32_t)NUM_ELEMS(s_commands)) { 341 LOGE("unsupported request code %d token %d", request, token); 342 // FIXME this should perhaps return a response 343 return 0; 344 } 345 346 347 pRI = (RequestInfo *)calloc(1, sizeof(RequestInfo)); 348 349 pRI->token = token; 350 pRI->pCI = &(s_commands[request]); 351 352 ret = pthread_mutex_lock(&s_pendingRequestsMutex); 353 assert (ret == 0); 354 355 pRI->p_next = s_pendingRequests; 356 s_pendingRequests = pRI; 357 358 ret = pthread_mutex_unlock(&s_pendingRequestsMutex); 359 assert (ret == 0); 360 361/* sLastDispatchedToken = token; */ 362 363 pRI->pCI->dispatchFunction(p, pRI); 364 365 return 0; 366} 367 368static void 369invalidCommandBlock (RequestInfo *pRI) { 370 LOGE("invalid command block for token %d request %s", 371 pRI->token, requestToString(pRI->pCI->requestNumber)); 372} 373 374/** Callee expects NULL */ 375static void 376dispatchVoid (Parcel& p, RequestInfo *pRI) { 377 clearPrintBuf; 378 printRequest(pRI->token, pRI->pCI->requestNumber); 379 s_callbacks.onRequest(pRI->pCI->requestNumber, NULL, 0, pRI); 380} 381 382/** Callee expects const char * */ 383static void 384dispatchString (Parcel& p, RequestInfo *pRI) { 385 status_t status; 386 size_t datalen; 387 size_t stringlen; 388 char *string8 = NULL; 389 390 string8 = strdupReadString(p); 391 392 startRequest; 393 appendPrintBuf("%s%s", printBuf, string8); 394 closeRequest; 395 printRequest(pRI->token, pRI->pCI->requestNumber); 396 397 s_callbacks.onRequest(pRI->pCI->requestNumber, string8, 398 sizeof(char *), pRI); 399 400#ifdef MEMSET_FREED 401 memsetString(string8); 402#endif 403 404 free(string8); 405 return; 406invalid: 407 invalidCommandBlock(pRI); 408 return; 409} 410 411/** Callee expects const char ** */ 412static void 413dispatchStrings (Parcel &p, RequestInfo *pRI) { 414 int32_t countStrings; 415 status_t status; 416 size_t datalen; 417 char **pStrings; 418 419 status = p.readInt32 (&countStrings); 420 421 if (status != NO_ERROR) { 422 goto invalid; 423 } 424 425 startRequest; 426 if (countStrings == 0) { 427 // just some non-null pointer 428 pStrings = (char **)alloca(sizeof(char *)); 429 datalen = 0; 430 } else if (((int)countStrings) == -1) { 431 pStrings = NULL; 432 datalen = 0; 433 } else { 434 datalen = sizeof(char *) * countStrings; 435 436 pStrings = (char **)alloca(datalen); 437 438 for (int i = 0 ; i < countStrings ; i++) { 439 pStrings[i] = strdupReadString(p); 440 appendPrintBuf("%s%s,", printBuf, pStrings[i]); 441 } 442 } 443 removeLastChar; 444 closeRequest; 445 printRequest(pRI->token, pRI->pCI->requestNumber); 446 447 s_callbacks.onRequest(pRI->pCI->requestNumber, pStrings, datalen, pRI); 448 449 if (pStrings != NULL) { 450 for (int i = 0 ; i < countStrings ; i++) { 451#ifdef MEMSET_FREED 452 memsetString (pStrings[i]); 453#endif 454 free(pStrings[i]); 455 } 456 457#ifdef MEMSET_FREED 458 memset(pStrings, 0, datalen); 459#endif 460 } 461 462 return; 463invalid: 464 invalidCommandBlock(pRI); 465 return; 466} 467 468/** Callee expects const int * */ 469static void 470dispatchInts (Parcel &p, RequestInfo *pRI) { 471 int32_t count; 472 status_t status; 473 size_t datalen; 474 int *pInts; 475 476 status = p.readInt32 (&count); 477 478 if (status != NO_ERROR || count == 0) { 479 goto invalid; 480 } 481 482 datalen = sizeof(int) * count; 483 pInts = (int *)alloca(datalen); 484 485 startRequest; 486 for (int i = 0 ; i < count ; i++) { 487 int32_t t; 488 489 status = p.readInt32(&t); 490 pInts[i] = (int)t; 491 appendPrintBuf("%s%d,", printBuf, t); 492 493 if (status != NO_ERROR) { 494 goto invalid; 495 } 496 } 497 removeLastChar; 498 closeRequest; 499 printRequest(pRI->token, pRI->pCI->requestNumber); 500 501 s_callbacks.onRequest(pRI->pCI->requestNumber, const_cast<int *>(pInts), 502 datalen, pRI); 503 504#ifdef MEMSET_FREED 505 memset(pInts, 0, datalen); 506#endif 507 508 return; 509invalid: 510 invalidCommandBlock(pRI); 511 return; 512} 513 514 515/** 516 * Callee expects const RIL_SMS_WriteArgs * 517 * Payload is: 518 * int32_t status 519 * String pdu 520 */ 521static void 522dispatchSmsWrite (Parcel &p, RequestInfo *pRI) { 523 RIL_SMS_WriteArgs args; 524 int32_t t; 525 status_t status; 526 527 memset (&args, 0, sizeof(args)); 528 529 status = p.readInt32(&t); 530 args.status = (int)t; 531 532 args.pdu = strdupReadString(p); 533 534 if (status != NO_ERROR || args.pdu == NULL) { 535 goto invalid; 536 } 537 538 args.smsc = strdupReadString(p); 539 540 startRequest; 541 appendPrintBuf("%s%d,%s,smsc=%s", printBuf, args.status, 542 (char*)args.pdu, (char*)args.smsc); 543 closeRequest; 544 printRequest(pRI->token, pRI->pCI->requestNumber); 545 546 s_callbacks.onRequest(pRI->pCI->requestNumber, &args, sizeof(args), pRI); 547 548#ifdef MEMSET_FREED 549 memsetString (args.pdu); 550#endif 551 552 free (args.pdu); 553 554#ifdef MEMSET_FREED 555 memset(&args, 0, sizeof(args)); 556#endif 557 558 return; 559invalid: 560 invalidCommandBlock(pRI); 561 return; 562} 563 564/** 565 * Callee expects const RIL_Dial * 566 * Payload is: 567 * String address 568 * int32_t clir 569 */ 570static void 571dispatchDial (Parcel &p, RequestInfo *pRI) { 572 RIL_Dial dial; 573 int32_t t; 574 status_t status; 575 576 memset (&dial, 0, sizeof(dial)); 577 578 dial.address = strdupReadString(p); 579 580 status = p.readInt32(&t); 581 dial.clir = (int)t; 582 583 if (status != NO_ERROR || dial.address == NULL) { 584 goto invalid; 585 } 586 587 startRequest; 588 appendPrintBuf("%snum=%s,clir=%d", printBuf, dial.address, dial.clir); 589 closeRequest; 590 printRequest(pRI->token, pRI->pCI->requestNumber); 591 592 s_callbacks.onRequest(pRI->pCI->requestNumber, &dial, sizeof(dial), pRI); 593 594#ifdef MEMSET_FREED 595 memsetString (dial.address); 596#endif 597 598 free (dial.address); 599 600#ifdef MEMSET_FREED 601 memset(&dial, 0, sizeof(dial)); 602#endif 603 604 return; 605invalid: 606 invalidCommandBlock(pRI); 607 return; 608} 609 610/** 611 * Callee expects const RIL_SIM_IO * 612 * Payload is: 613 * int32_t command 614 * int32_t fileid 615 * String path 616 * int32_t p1, p2, p3 617 * String data 618 * String pin2 619 */ 620static void 621dispatchSIM_IO (Parcel &p, RequestInfo *pRI) { 622 RIL_SIM_IO simIO; 623 int32_t t; 624 status_t status; 625 626 memset (&simIO, 0, sizeof(simIO)); 627 628 // note we only check status at the end 629 630 status = p.readInt32(&t); 631 simIO.command = (int)t; 632 633 status = p.readInt32(&t); 634 simIO.fileid = (int)t; 635 636 simIO.path = strdupReadString(p); 637 638 status = p.readInt32(&t); 639 simIO.p1 = (int)t; 640 641 status = p.readInt32(&t); 642 simIO.p2 = (int)t; 643 644 status = p.readInt32(&t); 645 simIO.p3 = (int)t; 646 647 simIO.data = strdupReadString(p); 648 simIO.pin2 = strdupReadString(p); 649 650 startRequest; 651 appendPrintBuf("%scmd=0x%X,efid=0x%X,path=%s,%d,%d,%d,%s,pin2=%s", printBuf, 652 simIO.command, simIO.fileid, (char*)simIO.path, 653 simIO.p1, simIO.p2, simIO.p3, 654 (char*)simIO.data, (char*)simIO.pin2); 655 closeRequest; 656 printRequest(pRI->token, pRI->pCI->requestNumber); 657 658 if (status != NO_ERROR) { 659 goto invalid; 660 } 661 662 s_callbacks.onRequest(pRI->pCI->requestNumber, &simIO, sizeof(simIO), pRI); 663 664#ifdef MEMSET_FREED 665 memsetString (simIO.path); 666 memsetString (simIO.data); 667 memsetString (simIO.pin2); 668#endif 669 670 free (simIO.path); 671 free (simIO.data); 672 free (simIO.pin2); 673 674#ifdef MEMSET_FREED 675 memset(&simIO, 0, sizeof(simIO)); 676#endif 677 678 return; 679invalid: 680 invalidCommandBlock(pRI); 681 return; 682} 683 684/** 685 * Callee expects const RIL_CallForwardInfo * 686 * Payload is: 687 * int32_t status/action 688 * int32_t reason 689 * int32_t serviceCode 690 * int32_t toa 691 * String number (0 length -> null) 692 * int32_t timeSeconds 693 */ 694static void 695dispatchCallForward(Parcel &p, RequestInfo *pRI) { 696 RIL_CallForwardInfo cff; 697 int32_t t; 698 status_t status; 699 700 memset (&cff, 0, sizeof(cff)); 701 702 // note we only check status at the end 703 704 status = p.readInt32(&t); 705 cff.status = (int)t; 706 707 status = p.readInt32(&t); 708 cff.reason = (int)t; 709 710 status = p.readInt32(&t); 711 cff.serviceClass = (int)t; 712 713 status = p.readInt32(&t); 714 cff.toa = (int)t; 715 716 cff.number = strdupReadString(p); 717 718 status = p.readInt32(&t); 719 cff.timeSeconds = (int)t; 720 721 if (status != NO_ERROR) { 722 goto invalid; 723 } 724 725 // special case: number 0-length fields is null 726 727 if (cff.number != NULL && strlen (cff.number) == 0) { 728 cff.number = NULL; 729 } 730 731 startRequest; 732 appendPrintBuf("%sstat=%d,reason=%d,serv=%d,toa=%d,%s,tout=%d", printBuf, 733 cff.status, cff.reason, cff.serviceClass, cff.toa, 734 (char*)cff.number, cff.timeSeconds); 735 closeRequest; 736 printRequest(pRI->token, pRI->pCI->requestNumber); 737 738 s_callbacks.onRequest(pRI->pCI->requestNumber, &cff, sizeof(cff), pRI); 739 740#ifdef MEMSET_FREED 741 memsetString(cff.number); 742#endif 743 744 free (cff.number); 745 746#ifdef MEMSET_FREED 747 memset(&cff, 0, sizeof(cff)); 748#endif 749 750 return; 751invalid: 752 invalidCommandBlock(pRI); 753 return; 754} 755 756 757static void 758dispatchRaw(Parcel &p, RequestInfo *pRI) { 759 int32_t len; 760 status_t status; 761 const void *data; 762 763 status = p.readInt32(&len); 764 765 if (status != NO_ERROR) { 766 goto invalid; 767 } 768 769 // The java code writes -1 for null arrays 770 if (((int)len) == -1) { 771 data = NULL; 772 len = 0; 773 } 774 775 data = p.readInplace(len); 776 777 startRequest; 778 appendPrintBuf("%sraw_size=%d", printBuf, len); 779 closeRequest; 780 printRequest(pRI->token, pRI->pCI->requestNumber); 781 782 s_callbacks.onRequest(pRI->pCI->requestNumber, const_cast<void *>(data), len, pRI); 783 784 return; 785invalid: 786 invalidCommandBlock(pRI); 787 return; 788} 789 790static void 791dispatchCdmaSms(Parcel &p, RequestInfo *pRI) { 792 RIL_CDMA_SMS_Message rcsm; 793 int32_t t; 794 uint8_t ut; 795 status_t status; 796 int32_t digitCount; 797 int digitLimit; 798 799 memset(&rcsm, 0, sizeof(rcsm)); 800 801 status = p.readInt32(&t); 802 rcsm.uTeleserviceID = (int) t; 803 804 status = p.read(&ut,sizeof(ut)); 805 rcsm.bIsServicePresent = (uint8_t) ut; 806 807 status = p.readInt32(&t); 808 rcsm.uServicecategory = (int) t; 809 810 status = p.readInt32(&t); 811 rcsm.sAddress.digit_mode = (RIL_CDMA_SMS_DigitMode) t; 812 813 status = p.readInt32(&t); 814 rcsm.sAddress.number_mode = (RIL_CDMA_SMS_NumberMode) t; 815 816 status = p.readInt32(&t); 817 rcsm.sAddress.number_type = (RIL_CDMA_SMS_NumberType) t; 818 819 status = p.readInt32(&t); 820 rcsm.sAddress.number_plan = (RIL_CDMA_SMS_NumberPlan) t; 821 822 status = p.read(&ut,sizeof(ut)); 823 rcsm.sAddress.number_of_digits= (uint8_t) ut; 824 825 digitLimit= MIN((rcsm.sAddress.number_of_digits), RIL_CDMA_SMS_ADDRESS_MAX); 826 for(digitCount =0 ; digitCount < digitLimit; digitCount ++) { 827 status = p.read(&ut,sizeof(ut)); 828 rcsm.sAddress.digits[digitCount] = (uint8_t) ut; 829 } 830 831 status = p.readInt32(&t); 832 rcsm.sSubAddress.subaddressType = (RIL_CDMA_SMS_SubaddressType) t; 833 834 status = p.read(&ut,sizeof(ut)); 835 rcsm.sSubAddress.odd = (uint8_t) ut; 836 837 status = p.read(&ut,sizeof(ut)); 838 rcsm.sSubAddress.number_of_digits = (uint8_t) ut; 839 840 digitLimit= MIN((rcsm.sSubAddress.number_of_digits), RIL_CDMA_SMS_SUBADDRESS_MAX); 841 for(digitCount =0 ; digitCount < digitLimit; digitCount ++) { 842 status = p.read(&ut,sizeof(ut)); 843 rcsm.sSubAddress.digits[digitCount] = (uint8_t) ut; 844 } 845 846 status = p.readInt32(&t); 847 rcsm.uBearerDataLen = (int) t; 848 849 digitLimit= MIN((rcsm.uBearerDataLen), RIL_CDMA_SMS_BEARER_DATA_MAX); 850 for(digitCount =0 ; digitCount < digitLimit; digitCount ++) { 851 status = p.read(&ut, sizeof(ut)); 852 rcsm.aBearerData[digitCount] = (uint8_t) ut; 853 } 854 855 if (status != NO_ERROR) { 856 goto invalid; 857 } 858 859 startRequest; 860 appendPrintBuf("%suTeleserviceID=%d, bIsServicePresent=%d, uServicecategory=%d, \ 861 sAddress.digit_mode=%d, sAddress.Number_mode=%d, sAddress.number_type=%d, ", 862 printBuf, rcsm.uTeleserviceID,rcsm.bIsServicePresent,rcsm.uServicecategory, 863 rcsm.sAddress.digit_mode, rcsm.sAddress.number_mode,rcsm.sAddress.number_type); 864 closeRequest; 865 866 printRequest(pRI->token, pRI->pCI->requestNumber); 867 868 s_callbacks.onRequest(pRI->pCI->requestNumber, &rcsm, sizeof(rcsm),pRI); 869 870#ifdef MEMSET_FREED 871 memset(&rcsm, 0, sizeof(rcsm)); 872#endif 873 874 return; 875 876invalid: 877 invalidCommandBlock(pRI); 878 return; 879} 880 881static void 882dispatchCdmaSmsAck(Parcel &p, RequestInfo *pRI) { 883 RIL_CDMA_SMS_Ack rcsa; 884 int32_t t; 885 status_t status; 886 int32_t digitCount; 887 888 memset(&rcsa, 0, sizeof(rcsa)); 889 890 status = p.readInt32(&t); 891 rcsa.uErrorClass = (RIL_CDMA_SMS_ErrorClass) t; 892 893 status = p.readInt32(&t); 894 rcsa.uSMSCauseCode = (int) t; 895 896 if (status != NO_ERROR) { 897 goto invalid; 898 } 899 900 startRequest; 901 appendPrintBuf("%suErrorClass=%d, uTLStatus=%d, ", 902 printBuf, rcsa.uErrorClass, rcsa.uSMSCauseCode); 903 closeRequest; 904 905 printRequest(pRI->token, pRI->pCI->requestNumber); 906 907 s_callbacks.onRequest(pRI->pCI->requestNumber, &rcsa, sizeof(rcsa),pRI); 908 909#ifdef MEMSET_FREED 910 memset(&rcsa, 0, sizeof(rcsa)); 911#endif 912 913 return; 914 915invalid: 916 invalidCommandBlock(pRI); 917 return; 918} 919 920static void 921dispatchGsmBrSmsCnf(Parcel &p, RequestInfo *pRI) { 922 int32_t t; 923 status_t status; 924 int32_t num; 925 926 status = p.readInt32(&num); 927 if (status != NO_ERROR) { 928 goto invalid; 929 } 930 931 RIL_GSM_BroadcastSmsConfigInfo gsmBci[num]; 932 RIL_GSM_BroadcastSmsConfigInfo *gsmBciPtrs[num]; 933 934 startRequest; 935 for (int i = 0 ; i < num ; i++ ) { 936 gsmBciPtrs[i] = &gsmBci[i]; 937 938 status = p.readInt32(&t); 939 gsmBci[i].fromServiceId = (int) t; 940 941 status = p.readInt32(&t); 942 gsmBci[i].toServiceId = (int) t; 943 944 status = p.readInt32(&t); 945 gsmBci[i].fromCodeScheme = (int) t; 946 947 status = p.readInt32(&t); 948 gsmBci[i].toCodeScheme = (int) t; 949 950 status = p.readInt32(&t); 951 gsmBci[i].selected = (uint8_t) t; 952 953 appendPrintBuf("%s [%d: fromServiceId=%d, toServiceId =%d, \ 954 fromCodeScheme=%d, toCodeScheme=%d, selected =%d]", printBuf, i, 955 gsmBci[i].fromServiceId, gsmBci[i].toServiceId, 956 gsmBci[i].fromCodeScheme, gsmBci[i].toCodeScheme, 957 gsmBci[i].selected); 958 } 959 closeRequest; 960 961 if (status != NO_ERROR) { 962 goto invalid; 963 } 964 965 s_callbacks.onRequest(pRI->pCI->requestNumber, 966 gsmBciPtrs, 967 num * sizeof(RIL_GSM_BroadcastSmsConfigInfo *), 968 pRI); 969 970#ifdef MEMSET_FREED 971 memset(gsmBci, 0, num * sizeof(RIL_GSM_BroadcastSmsConfigInfo)); 972 memset(gsmBciPtrs, 0, num * sizeof(RIL_GSM_BroadcastSmsConfigInfo *)); 973#endif 974 975 return; 976 977invalid: 978 invalidCommandBlock(pRI); 979 return; 980} 981 982static void 983dispatchCdmaBrSmsCnf(Parcel &p, RequestInfo *pRI) { 984 int32_t t; 985 status_t status; 986 int32_t num; 987 988 status = p.readInt32(&num); 989 if (status != NO_ERROR) { 990 goto invalid; 991 } 992 993 RIL_CDMA_BroadcastSmsConfigInfo cdmaBci[num]; 994 RIL_CDMA_BroadcastSmsConfigInfo *cdmaBciPtrs[num]; 995 996 startRequest; 997 for (int i = 0 ; i < num ; i++ ) { 998 cdmaBciPtrs[i] = &cdmaBci[i]; 999 1000 status = p.readInt32(&t); 1001 cdmaBci[i].service_category = (int) t; 1002 1003 status = p.readInt32(&t); 1004 cdmaBci[i].language = (int) t; 1005 1006 status = p.readInt32(&t); 1007 cdmaBci[i].selected = (uint8_t) t; 1008 1009 appendPrintBuf("%s [%d: service_category=%d, language =%d, \ 1010 entries.bSelected =%d]", printBuf, i, cdmaBci[i].service_category, 1011 cdmaBci[i].language, cdmaBci[i].selected); 1012 } 1013 closeRequest; 1014 1015 if (status != NO_ERROR) { 1016 goto invalid; 1017 } 1018 1019 s_callbacks.onRequest(pRI->pCI->requestNumber, 1020 cdmaBciPtrs, 1021 num * sizeof(RIL_CDMA_BroadcastSmsConfigInfo *), 1022 pRI); 1023 1024#ifdef MEMSET_FREED 1025 memset(cdmaBci, 0, num * sizeof(RIL_CDMA_BroadcastSmsConfigInfo)); 1026 memset(cdmaBciPtrs, 0, num * sizeof(RIL_CDMA_BroadcastSmsConfigInfo *)); 1027#endif 1028 1029 return; 1030 1031invalid: 1032 invalidCommandBlock(pRI); 1033 return; 1034} 1035 1036static void dispatchRilCdmaSmsWriteArgs(Parcel &p, RequestInfo *pRI) { 1037 RIL_CDMA_SMS_WriteArgs rcsw; 1038 int32_t t; 1039 uint32_t ut; 1040 uint8_t uct; 1041 status_t status; 1042 int32_t digitCount; 1043 1044 memset(&rcsw, 0, sizeof(rcsw)); 1045 1046 status = p.readInt32(&t); 1047 rcsw.status = t; 1048 1049 status = p.readInt32(&t); 1050 rcsw.message.uTeleserviceID = (int) t; 1051 1052 status = p.read(&uct,sizeof(uct)); 1053 rcsw.message.bIsServicePresent = (uint8_t) uct; 1054 1055 status = p.readInt32(&t); 1056 rcsw.message.uServicecategory = (int) t; 1057 1058 status = p.readInt32(&t); 1059 rcsw.message.sAddress.digit_mode = (RIL_CDMA_SMS_DigitMode) t; 1060 1061 status = p.readInt32(&t); 1062 rcsw.message.sAddress.number_mode = (RIL_CDMA_SMS_NumberMode) t; 1063 1064 status = p.readInt32(&t); 1065 rcsw.message.sAddress.number_type = (RIL_CDMA_SMS_NumberType) t; 1066 1067 status = p.readInt32(&t); 1068 rcsw.message.sAddress.number_plan = (RIL_CDMA_SMS_NumberPlan) t; 1069 1070 status = p.read(&uct,sizeof(uct)); 1071 rcsw.message.sAddress.number_of_digits = (uint8_t) uct; 1072 1073 for(digitCount = 0 ; digitCount < RIL_CDMA_SMS_ADDRESS_MAX; digitCount ++) { 1074 status = p.read(&uct,sizeof(uct)); 1075 rcsw.message.sAddress.digits[digitCount] = (uint8_t) uct; 1076 } 1077 1078 status = p.readInt32(&t); 1079 rcsw.message.sSubAddress.subaddressType = (RIL_CDMA_SMS_SubaddressType) t; 1080 1081 status = p.read(&uct,sizeof(uct)); 1082 rcsw.message.sSubAddress.odd = (uint8_t) uct; 1083 1084 status = p.read(&uct,sizeof(uct)); 1085 rcsw.message.sSubAddress.number_of_digits = (uint8_t) uct; 1086 1087 for(digitCount = 0 ; digitCount < RIL_CDMA_SMS_SUBADDRESS_MAX; digitCount ++) { 1088 status = p.read(&uct,sizeof(uct)); 1089 rcsw.message.sSubAddress.digits[digitCount] = (uint8_t) uct; 1090 } 1091 1092 status = p.readInt32(&t); 1093 rcsw.message.uBearerDataLen = (int) t; 1094 1095 for(digitCount = 0 ; digitCount < RIL_CDMA_SMS_BEARER_DATA_MAX; digitCount ++) { 1096 status = p.read(&uct, sizeof(uct)); 1097 rcsw.message.aBearerData[digitCount] = (uint8_t) uct; 1098 } 1099 1100 if (status != NO_ERROR) { 1101 goto invalid; 1102 } 1103 1104 startRequest; 1105 appendPrintBuf("%sstatus=%d, message.uTeleserviceID=%d, message.bIsServicePresent=%d, \ 1106 message.uServicecategory=%d, message.sAddress.digit_mode=%d, \ 1107 message.sAddress.number_mode=%d, \ 1108 message.sAddress.number_type=%d, ", 1109 printBuf, rcsw.status, rcsw.message.uTeleserviceID, rcsw.message.bIsServicePresent, 1110 rcsw.message.uServicecategory, rcsw.message.sAddress.digit_mode, 1111 rcsw.message.sAddress.number_mode, 1112 rcsw.message.sAddress.number_type); 1113 closeRequest; 1114 1115 printRequest(pRI->token, pRI->pCI->requestNumber); 1116 1117 s_callbacks.onRequest(pRI->pCI->requestNumber, &rcsw, sizeof(rcsw),pRI); 1118 1119#ifdef MEMSET_FREED 1120 memset(&rcsw, 0, sizeof(rcsw)); 1121#endif 1122 1123 return; 1124 1125invalid: 1126 invalidCommandBlock(pRI); 1127 return; 1128 1129} 1130 1131static int 1132blockingWrite(int fd, const void *buffer, size_t len) { 1133 size_t writeOffset = 0; 1134 const uint8_t *toWrite; 1135 1136 toWrite = (const uint8_t *)buffer; 1137 1138 while (writeOffset < len) { 1139 ssize_t written; 1140 do { 1141 written = write (fd, toWrite + writeOffset, 1142 len - writeOffset); 1143 } while (written < 0 && errno == EINTR); 1144 1145 if (written >= 0) { 1146 writeOffset += written; 1147 } else { // written < 0 1148 LOGE ("RIL Response: unexpected error on write errno:%d", errno); 1149 close(fd); 1150 return -1; 1151 } 1152 } 1153 1154 return 0; 1155} 1156 1157static int 1158sendResponseRaw (const void *data, size_t dataSize) { 1159 int fd = s_fdCommand; 1160 int ret; 1161 uint32_t header; 1162 1163 if (s_fdCommand < 0) { 1164 return -1; 1165 } 1166 1167 if (dataSize > MAX_COMMAND_BYTES) { 1168 LOGE("RIL: packet larger than %u (%u)", 1169 MAX_COMMAND_BYTES, (unsigned int )dataSize); 1170 1171 return -1; 1172 } 1173 1174 pthread_mutex_lock(&s_writeMutex); 1175 1176 header = htonl(dataSize); 1177 1178 ret = blockingWrite(fd, (void *)&header, sizeof(header)); 1179 1180 if (ret < 0) { 1181 pthread_mutex_unlock(&s_writeMutex); 1182 return ret; 1183 } 1184 1185 ret = blockingWrite(fd, data, dataSize); 1186 1187 if (ret < 0) { 1188 pthread_mutex_unlock(&s_writeMutex); 1189 return ret; 1190 } 1191 1192 pthread_mutex_unlock(&s_writeMutex); 1193 1194 return 0; 1195} 1196 1197static int 1198sendResponse (Parcel &p) { 1199 printResponse; 1200 return sendResponseRaw(p.data(), p.dataSize()); 1201} 1202 1203/** response is an int* pointing to an array of ints*/ 1204 1205static int 1206responseInts(Parcel &p, void *response, size_t responselen) { 1207 int numInts; 1208 1209 if (response == NULL && responselen != 0) { 1210 LOGE("invalid response: NULL"); 1211 return RIL_ERRNO_INVALID_RESPONSE; 1212 } 1213 if (responselen % sizeof(int) != 0) { 1214 LOGE("invalid response length %d expected multiple of %d\n", 1215 (int)responselen, (int)sizeof(int)); 1216 return RIL_ERRNO_INVALID_RESPONSE; 1217 } 1218 1219 int *p_int = (int *) response; 1220 1221 numInts = responselen / sizeof(int *); 1222 p.writeInt32 (numInts); 1223 1224 /* each int*/ 1225 startResponse; 1226 for (int i = 0 ; i < numInts ; i++) { 1227 appendPrintBuf("%s%d,", printBuf, p_int[i]); 1228 p.writeInt32(p_int[i]); 1229 } 1230 removeLastChar; 1231 closeResponse; 1232 1233 return 0; 1234} 1235 1236/** response is a char **, pointing to an array of char *'s */ 1237static int responseStrings(Parcel &p, void *response, size_t responselen) { 1238 int numStrings; 1239 1240 if (response == NULL && responselen != 0) { 1241 LOGE("invalid response: NULL"); 1242 return RIL_ERRNO_INVALID_RESPONSE; 1243 } 1244 if (responselen % sizeof(char *) != 0) { 1245 LOGE("invalid response length %d expected multiple of %d\n", 1246 (int)responselen, (int)sizeof(char *)); 1247 return RIL_ERRNO_INVALID_RESPONSE; 1248 } 1249 1250 if (response == NULL) { 1251 p.writeInt32 (0); 1252 } else { 1253 char **p_cur = (char **) response; 1254 1255 numStrings = responselen / sizeof(char *); 1256 p.writeInt32 (numStrings); 1257 1258 /* each string*/ 1259 startResponse; 1260 for (int i = 0 ; i < numStrings ; i++) { 1261 appendPrintBuf("%s%s,", printBuf, (char*)p_cur[i]); 1262 writeStringToParcel (p, p_cur[i]); 1263 } 1264 removeLastChar; 1265 closeResponse; 1266 } 1267 return 0; 1268} 1269 1270 1271/** 1272 * NULL strings are accepted 1273 * FIXME currently ignores responselen 1274 */ 1275static int responseString(Parcel &p, void *response, size_t responselen) { 1276 /* one string only */ 1277 startResponse; 1278 appendPrintBuf("%s%s", printBuf, (char*)response); 1279 closeResponse; 1280 1281 writeStringToParcel(p, (const char *)response); 1282 1283 return 0; 1284} 1285 1286static int responseVoid(Parcel &p, void *response, size_t responselen) { 1287 startResponse; 1288 removeLastChar; 1289 return 0; 1290} 1291 1292static int responseCallList(Parcel &p, void *response, size_t responselen) { 1293 int num; 1294 1295 if (response == NULL && responselen != 0) { 1296 LOGE("invalid response: NULL"); 1297 return RIL_ERRNO_INVALID_RESPONSE; 1298 } 1299 1300 if (responselen % sizeof (RIL_Call *) != 0) { 1301 LOGE("invalid response length %d expected multiple of %d\n", 1302 (int)responselen, (int)sizeof (RIL_Call *)); 1303 return RIL_ERRNO_INVALID_RESPONSE; 1304 } 1305 1306 startResponse; 1307 /* number of call info's */ 1308 num = responselen / sizeof(RIL_Call *); 1309 p.writeInt32(num); 1310 1311 for (int i = 0 ; i < num ; i++) { 1312 RIL_Call *p_cur = ((RIL_Call **) response)[i]; 1313 /* each call info */ 1314 p.writeInt32(p_cur->state); 1315 p.writeInt32(p_cur->index); 1316 p.writeInt32(p_cur->toa); 1317 p.writeInt32(p_cur->isMpty); 1318 p.writeInt32(p_cur->isMT); 1319 p.writeInt32(p_cur->als); 1320 p.writeInt32(p_cur->isVoice); 1321 p.writeInt32(p_cur->isVoicePrivacy); 1322 writeStringToParcel(p, p_cur->number); 1323 p.writeInt32(p_cur->numberPresentation); 1324 writeStringToParcel(p, p_cur->name); 1325 p.writeInt32(p_cur->namePresentation); 1326 appendPrintBuf("%s[id=%d,%s,toa=%d,", 1327 printBuf, 1328 p_cur->index, 1329 callStateToString(p_cur->state), 1330 p_cur->toa); 1331 appendPrintBuf("%s%s,%s,als=%d,%s,%s,", 1332 printBuf, 1333 (p_cur->isMpty)?"conf":"norm", 1334 (p_cur->isMT)?"mt":"mo", 1335 p_cur->als, 1336 (p_cur->isVoice)?"voc":"nonvoc", 1337 (p_cur->isVoicePrivacy)?"evp":"noevp"); 1338 appendPrintBuf("%s%s,cli=%d,name='%s',%d]", 1339 printBuf, 1340 p_cur->number, 1341 p_cur->numberPresentation, 1342 p_cur->name, 1343 p_cur->namePresentation); 1344 } 1345 removeLastChar; 1346 closeResponse; 1347 1348 return 0; 1349} 1350 1351static int responseSMS(Parcel &p, void *response, size_t responselen) { 1352 if (response == NULL) { 1353 LOGE("invalid response: NULL"); 1354 return RIL_ERRNO_INVALID_RESPONSE; 1355 } 1356 1357 if (responselen != sizeof (RIL_SMS_Response) ) { 1358 LOGE("invalid response length %d expected %d", 1359 (int)responselen, (int)sizeof (RIL_SMS_Response)); 1360 return RIL_ERRNO_INVALID_RESPONSE; 1361 } 1362 1363 RIL_SMS_Response *p_cur = (RIL_SMS_Response *) response; 1364 1365 p.writeInt32(p_cur->messageRef); 1366 writeStringToParcel(p, p_cur->ackPDU); 1367 p.writeInt32(p_cur->errorCode); 1368 1369 startResponse; 1370 appendPrintBuf("%s%d,%s,%d", printBuf, p_cur->messageRef, 1371 (char*)p_cur->ackPDU, p_cur->errorCode); 1372 closeResponse; 1373 1374 return 0; 1375} 1376 1377static int responseDataCallList(Parcel &p, void *response, size_t responselen) 1378{ 1379 if (response == NULL && responselen != 0) { 1380 LOGE("invalid response: NULL"); 1381 return RIL_ERRNO_INVALID_RESPONSE; 1382 } 1383 1384 if (responselen % sizeof(RIL_Data_Call_Response) != 0) { 1385 LOGE("invalid response length %d expected multiple of %d", 1386 (int)responselen, (int)sizeof(RIL_Data_Call_Response)); 1387 return RIL_ERRNO_INVALID_RESPONSE; 1388 } 1389 1390 int num = responselen / sizeof(RIL_Data_Call_Response); 1391 p.writeInt32(num); 1392 1393 RIL_Data_Call_Response *p_cur = (RIL_Data_Call_Response *) response; 1394 startResponse; 1395 int i; 1396 for (i = 0; i < num; i++) { 1397 p.writeInt32(p_cur[i].cid); 1398 p.writeInt32(p_cur[i].active); 1399 writeStringToParcel(p, p_cur[i].type); 1400 writeStringToParcel(p, p_cur[i].apn); 1401 writeStringToParcel(p, p_cur[i].address); 1402 appendPrintBuf("%s[cid=%d,%s,%s,%s,%s],", printBuf, 1403 p_cur[i].cid, 1404 (p_cur[i].active==0)?"down":"up", 1405 (char*)p_cur[i].type, 1406 (char*)p_cur[i].apn, 1407 (char*)p_cur[i].address); 1408 } 1409 removeLastChar; 1410 closeResponse; 1411 1412 return 0; 1413} 1414 1415static int responseRaw(Parcel &p, void *response, size_t responselen) { 1416 if (response == NULL && responselen != 0) { 1417 LOGE("invalid response: NULL with responselen != 0"); 1418 return RIL_ERRNO_INVALID_RESPONSE; 1419 } 1420 1421 // The java code reads -1 size as null byte array 1422 if (response == NULL) { 1423 p.writeInt32(-1); 1424 } else { 1425 p.writeInt32(responselen); 1426 p.write(response, responselen); 1427 } 1428 1429 return 0; 1430} 1431 1432 1433static int responseSIM_IO(Parcel &p, void *response, size_t responselen) { 1434 if (response == NULL) { 1435 LOGE("invalid response: NULL"); 1436 return RIL_ERRNO_INVALID_RESPONSE; 1437 } 1438 1439 if (responselen != sizeof (RIL_SIM_IO_Response) ) { 1440 LOGE("invalid response length was %d expected %d", 1441 (int)responselen, (int)sizeof (RIL_SIM_IO_Response)); 1442 return RIL_ERRNO_INVALID_RESPONSE; 1443 } 1444 1445 RIL_SIM_IO_Response *p_cur = (RIL_SIM_IO_Response *) response; 1446 p.writeInt32(p_cur->sw1); 1447 p.writeInt32(p_cur->sw2); 1448 writeStringToParcel(p, p_cur->simResponse); 1449 1450 startResponse; 1451 appendPrintBuf("%ssw1=0x%X,sw2=0x%X,%s", printBuf, p_cur->sw1, p_cur->sw2, 1452 (char*)p_cur->simResponse); 1453 closeResponse; 1454 1455 1456 return 0; 1457} 1458 1459static int responseCallForwards(Parcel &p, void *response, size_t responselen) { 1460 int num; 1461 1462 if (response == NULL && responselen != 0) { 1463 LOGE("invalid response: NULL"); 1464 return RIL_ERRNO_INVALID_RESPONSE; 1465 } 1466 1467 if (responselen % sizeof(RIL_CallForwardInfo *) != 0) { 1468 LOGE("invalid response length %d expected multiple of %d", 1469 (int)responselen, (int)sizeof(RIL_CallForwardInfo *)); 1470 return RIL_ERRNO_INVALID_RESPONSE; 1471 } 1472 1473 /* number of call info's */ 1474 num = responselen / sizeof(RIL_CallForwardInfo *); 1475 p.writeInt32(num); 1476 1477 startResponse; 1478 for (int i = 0 ; i < num ; i++) { 1479 RIL_CallForwardInfo *p_cur = ((RIL_CallForwardInfo **) response)[i]; 1480 1481 p.writeInt32(p_cur->status); 1482 p.writeInt32(p_cur->reason); 1483 p.writeInt32(p_cur->serviceClass); 1484 p.writeInt32(p_cur->toa); 1485 writeStringToParcel(p, p_cur->number); 1486 p.writeInt32(p_cur->timeSeconds); 1487 appendPrintBuf("%s[%s,reason=%d,cls=%d,toa=%d,%s,tout=%d],", printBuf, 1488 (p_cur->status==1)?"enable":"disable", 1489 p_cur->reason, p_cur->serviceClass, p_cur->toa, 1490 (char*)p_cur->number, 1491 p_cur->timeSeconds); 1492 } 1493 removeLastChar; 1494 closeResponse; 1495 1496 return 0; 1497} 1498 1499static int responseSsn(Parcel &p, void *response, size_t responselen) { 1500 if (response == NULL) { 1501 LOGE("invalid response: NULL"); 1502 return RIL_ERRNO_INVALID_RESPONSE; 1503 } 1504 1505 if (responselen != sizeof(RIL_SuppSvcNotification)) { 1506 LOGE("invalid response length was %d expected %d", 1507 (int)responselen, (int)sizeof (RIL_SuppSvcNotification)); 1508 return RIL_ERRNO_INVALID_RESPONSE; 1509 } 1510 1511 RIL_SuppSvcNotification *p_cur = (RIL_SuppSvcNotification *) response; 1512 p.writeInt32(p_cur->notificationType); 1513 p.writeInt32(p_cur->code); 1514 p.writeInt32(p_cur->index); 1515 p.writeInt32(p_cur->type); 1516 writeStringToParcel(p, p_cur->number); 1517 1518 startResponse; 1519 appendPrintBuf("%s%s,code=%d,id=%d,type=%d,%s", printBuf, 1520 (p_cur->notificationType==0)?"mo":"mt", 1521 p_cur->code, p_cur->index, p_cur->type, 1522 (char*)p_cur->number); 1523 closeResponse; 1524 1525 return 0; 1526} 1527 1528static int responseCellList(Parcel &p, void *response, size_t responselen) { 1529 int num; 1530 1531 if (response == NULL && responselen != 0) { 1532 LOGE("invalid response: NULL"); 1533 return RIL_ERRNO_INVALID_RESPONSE; 1534 } 1535 1536 if (responselen % sizeof (RIL_NeighboringCell *) != 0) { 1537 LOGE("invalid response length %d expected multiple of %d\n", 1538 (int)responselen, (int)sizeof (RIL_NeighboringCell *)); 1539 return RIL_ERRNO_INVALID_RESPONSE; 1540 } 1541 1542 startResponse; 1543 /* number of records */ 1544 num = responselen / sizeof(RIL_NeighboringCell *); 1545 p.writeInt32(num); 1546 1547 for (int i = 0 ; i < num ; i++) { 1548 RIL_NeighboringCell *p_cur = ((RIL_NeighboringCell **) response)[i]; 1549 1550 p.writeInt32(p_cur->rssi); 1551 writeStringToParcel (p, p_cur->cid); 1552 1553 appendPrintBuf("%s[cid=%s,rssi=%d],", printBuf, 1554 p_cur->cid, p_cur->rssi); 1555 } 1556 removeLastChar; 1557 closeResponse; 1558 1559 return 0; 1560} 1561 1562/** 1563 * Marshall the signalInfoRecord into the parcel if it exists. 1564 */ 1565static void marshallSignalInfoRecord(Parcel &p, 1566 RIL_CDMA_SignalInfoRecord &p_signalInfoRecord) { 1567 p.writeInt32(p_signalInfoRecord.isPresent); 1568 p.writeInt32(p_signalInfoRecord.signalType); 1569 p.writeInt32(p_signalInfoRecord.alertPitch); 1570 p.writeInt32(p_signalInfoRecord.signal); 1571} 1572 1573static int responseCdmaInformationRecords(Parcel &p, 1574 void *response, size_t responselen) { 1575 int num; 1576 char* string8 = NULL; 1577 int buffer_lenght; 1578 RIL_CDMA_InformationRecord *infoRec; 1579 1580 if (response == NULL && responselen != 0) { 1581 LOGE("invalid response: NULL"); 1582 return RIL_ERRNO_INVALID_RESPONSE; 1583 } 1584 1585 if (responselen != sizeof (RIL_CDMA_InformationRecords)) { 1586 LOGE("invalid response length %d expected multiple of %d\n", 1587 (int)responselen, (int)sizeof (RIL_CDMA_InformationRecords *)); 1588 return RIL_ERRNO_INVALID_RESPONSE; 1589 } 1590 1591 RIL_CDMA_InformationRecords *p_cur = 1592 (RIL_CDMA_InformationRecords *) response; 1593 num = MIN(p_cur->numberOfInfoRecs, RIL_CDMA_MAX_NUMBER_OF_INFO_RECS); 1594 1595 startResponse; 1596 p.writeInt32(num); 1597 1598 for (int i = 0 ; i < num ; i++) { 1599 infoRec = &p_cur->infoRec[i]; 1600 p.writeInt32(infoRec->name); 1601 switch (infoRec->name) { 1602 case RIL_CDMA_DISPLAY_INFO_REC: 1603 case RIL_CDMA_EXTENDED_DISPLAY_INFO_REC: 1604 if (infoRec->rec.display.alpha_len > 1605 CDMA_ALPHA_INFO_BUFFER_LENGTH) { 1606 LOGE("invalid display info response length %d \ 1607 expected not more than %d\n", 1608 (int)infoRec->rec.display.alpha_len, 1609 CDMA_ALPHA_INFO_BUFFER_LENGTH); 1610 return RIL_ERRNO_INVALID_RESPONSE; 1611 } 1612 string8 = (char*) malloc((infoRec->rec.display.alpha_len + 1) 1613 * sizeof(char) ); 1614 for (int i = 0 ; i < infoRec->rec.display.alpha_len ; i++) { 1615 string8[i] = infoRec->rec.display.alpha_buf[i]; 1616 } 1617 string8[infoRec->rec.display.alpha_len] = '\0'; 1618 writeStringToParcel(p, (const char*)string8); 1619 free(string8); 1620 string8 = NULL; 1621 break; 1622 case RIL_CDMA_CALLED_PARTY_NUMBER_INFO_REC: 1623 case RIL_CDMA_CALLING_PARTY_NUMBER_INFO_REC: 1624 case RIL_CDMA_CONNECTED_NUMBER_INFO_REC: 1625 if (infoRec->rec.number.len > CDMA_NUMBER_INFO_BUFFER_LENGTH) { 1626 LOGE("invalid display info response length %d \ 1627 expected not more than %d\n", 1628 (int)infoRec->rec.number.len, 1629 CDMA_NUMBER_INFO_BUFFER_LENGTH); 1630 return RIL_ERRNO_INVALID_RESPONSE; 1631 } 1632 string8 = (char*) malloc((infoRec->rec.number.len + 1) 1633 * sizeof(char) ); 1634 for (int i = 0 ; i < infoRec->rec.number.len; i++) { 1635 string8[i] = infoRec->rec.number.buf[i]; 1636 } 1637 string8[infoRec->rec.number.len] = '\0'; 1638 writeStringToParcel(p, (const char*)string8); 1639 free(string8); 1640 string8 = NULL; 1641 p.writeInt32(infoRec->rec.number.number_type); 1642 p.writeInt32(infoRec->rec.number.number_plan); 1643 p.writeInt32(infoRec->rec.number.pi); 1644 p.writeInt32(infoRec->rec.number.si); 1645 break; 1646 case RIL_CDMA_SIGNAL_INFO_REC: 1647 p.writeInt32(infoRec->rec.signal.isPresent); 1648 p.writeInt32(infoRec->rec.signal.signalType); 1649 p.writeInt32(infoRec->rec.signal.alertPitch); 1650 p.writeInt32(infoRec->rec.signal.signal); 1651 1652 appendPrintBuf("%sisPresent=%X, signalType=%X, \ 1653 alertPitch=%X, signal=%X, ", 1654 printBuf, (int)infoRec->rec.signal.isPresent, 1655 (int)infoRec->rec.signal.signalType, 1656 (int)infoRec->rec.signal.alertPitch, 1657 (int)infoRec->rec.signal.signal); 1658 removeLastChar; 1659 break; 1660 case RIL_CDMA_REDIRECTING_NUMBER_INFO_REC: 1661 if (infoRec->rec.redir.redirectingNumber.len > 1662 CDMA_NUMBER_INFO_BUFFER_LENGTH) { 1663 LOGE("invalid display info response length %d \ 1664 expected not more than %d\n", 1665 (int)infoRec->rec.redir.redirectingNumber.len, 1666 CDMA_NUMBER_INFO_BUFFER_LENGTH); 1667 return RIL_ERRNO_INVALID_RESPONSE; 1668 } 1669 string8 = (char*) malloc((infoRec->rec.redir.redirectingNumber 1670 .len + 1) * sizeof(char) ); 1671 for (int i = 0; 1672 i < infoRec->rec.redir.redirectingNumber.len; 1673 i++) { 1674 string8[i] = infoRec->rec.redir.redirectingNumber.buf[i]; 1675 } 1676 string8[infoRec->rec.redir.redirectingNumber.len] = '\0'; 1677 writeStringToParcel(p, (const char*)string8); 1678 free(string8); 1679 string8 = NULL; 1680 p.writeInt32(infoRec->rec.redir.redirectingNumber.number_type); 1681 p.writeInt32(infoRec->rec.redir.redirectingNumber.number_plan); 1682 p.writeInt32(infoRec->rec.redir.redirectingNumber.pi); 1683 p.writeInt32(infoRec->rec.redir.redirectingNumber.si); 1684 p.writeInt32(infoRec->rec.redir.redirectingReason); 1685 break; 1686 case RIL_CDMA_LINE_CONTROL_INFO_REC: 1687 p.writeInt32(infoRec->rec.lineCtrl.lineCtrlPolarityIncluded); 1688 p.writeInt32(infoRec->rec.lineCtrl.lineCtrlToggle); 1689 p.writeInt32(infoRec->rec.lineCtrl.lineCtrlReverse); 1690 p.writeInt32(infoRec->rec.lineCtrl.lineCtrlPowerDenial); 1691 1692 appendPrintBuf("%slineCtrlPolarityIncluded=%d, \ 1693 lineCtrlToggle=%d, lineCtrlReverse=%d, \ 1694 lineCtrlPowerDenial=%d, ", printBuf, 1695 (int)infoRec->rec.lineCtrl.lineCtrlPolarityIncluded, 1696 (int)infoRec->rec.lineCtrl.lineCtrlToggle, 1697 (int)infoRec->rec.lineCtrl.lineCtrlReverse, 1698 (int)infoRec->rec.lineCtrl.lineCtrlPowerDenial); 1699 removeLastChar; 1700 break; 1701 case RIL_CDMA_T53_CLIR_INFO_REC: 1702 p.writeInt32((int)(infoRec->rec.clir.cause)); 1703 1704 appendPrintBuf("%scause%d", printBuf, infoRec->rec.clir.cause); 1705 removeLastChar; 1706 break; 1707 case RIL_CDMA_T53_AUDIO_CONTROL_INFO_REC: 1708 p.writeInt32(infoRec->rec.audioCtrl.upLink); 1709 p.writeInt32(infoRec->rec.audioCtrl.downLink); 1710 1711 appendPrintBuf("%supLink=%d, downLink=%d, ", printBuf, 1712 infoRec->rec.audioCtrl.upLink, 1713 infoRec->rec.audioCtrl.downLink); 1714 removeLastChar; 1715 break; 1716 case RIL_CDMA_T53_RELEASE_INFO_REC: 1717 // TODO(Moto): See David Krause, he has the answer:) 1718 LOGE("RIL_CDMA_T53_RELEASE_INFO_REC: return INVALID_RESPONSE"); 1719 return RIL_ERRNO_INVALID_RESPONSE; 1720 default: 1721 LOGE("Incorrect name value"); 1722 return RIL_ERRNO_INVALID_RESPONSE; 1723 } 1724 } 1725 closeResponse; 1726 1727 return 0; 1728} 1729 1730static int responseRilSignalStrength(Parcel &p, 1731 void *response, size_t responselen) { 1732 if (response == NULL && responselen != 0) { 1733 LOGE("invalid response: NULL"); 1734 return RIL_ERRNO_INVALID_RESPONSE; 1735 } 1736 1737 if (responselen == sizeof (RIL_SignalStrength)) { 1738 // New RIL 1739 RIL_SignalStrength *p_cur = ((RIL_SignalStrength *) response); 1740 1741 p.writeInt32(p_cur->GW_SignalStrength.signalStrength); 1742 p.writeInt32(p_cur->GW_SignalStrength.bitErrorRate); 1743 p.writeInt32(p_cur->CDMA_SignalStrength.dbm); 1744 p.writeInt32(p_cur->CDMA_SignalStrength.ecio); 1745 p.writeInt32(p_cur->EVDO_SignalStrength.dbm); 1746 p.writeInt32(p_cur->EVDO_SignalStrength.ecio); 1747 p.writeInt32(p_cur->EVDO_SignalStrength.signalNoiseRatio); 1748 1749 startResponse; 1750 appendPrintBuf("%s[signalStrength=%d,bitErrorRate=%d,\ 1751 CDMA_SignalStrength.dbm=%d,CDMA_SignalStrength.ecio=%d,\ 1752 EVDO_SignalStrength.dbm =%d,EVDO_SignalStrength.ecio=%d,\ 1753 EVDO_SignalStrength.signalNoiseRatio=%d]", 1754 printBuf, 1755 p_cur->GW_SignalStrength.signalStrength, 1756 p_cur->GW_SignalStrength.bitErrorRate, 1757 p_cur->CDMA_SignalStrength.dbm, 1758 p_cur->CDMA_SignalStrength.ecio, 1759 p_cur->EVDO_SignalStrength.dbm, 1760 p_cur->EVDO_SignalStrength.ecio, 1761 p_cur->EVDO_SignalStrength.signalNoiseRatio); 1762 1763 closeResponse; 1764 1765 } else if (responselen % sizeof (int) == 0) { 1766 // Old RIL deprecated 1767 int *p_cur = (int *) response; 1768 1769 startResponse; 1770 1771 // With the Old RIL we see one or 2 integers. 1772 size_t num = responselen / sizeof (int); // Number of integers from ril 1773 size_t totalIntegers = 7; // Number of integers in RIL_SignalStrength 1774 size_t i; 1775 1776 appendPrintBuf("%s[", printBuf); 1777 for (i = 0; i < num; i++) { 1778 appendPrintBuf("%s %d", printBuf, *p_cur); 1779 p.writeInt32(*p_cur++); 1780 } 1781 appendPrintBuf("%s]", printBuf); 1782 1783 // Fill the remainder with zero's. 1784 for (; i < totalIntegers; i++) { 1785 p.writeInt32(0); 1786 } 1787 1788 closeResponse; 1789 } else { 1790 LOGE("invalid response length"); 1791 return RIL_ERRNO_INVALID_RESPONSE; 1792 } 1793 1794 return 0; 1795} 1796 1797static int responseCallRing(Parcel &p, void *response, size_t responselen) { 1798 if ((response == NULL) || (responselen == 0)) { 1799 return responseVoid(p, response, responselen); 1800 } else { 1801 return responseCdmaSignalInfoRecord(p, response, responselen); 1802 } 1803} 1804 1805static int responseCdmaSignalInfoRecord(Parcel &p, void *response, size_t responselen) { 1806 if (response == NULL || responselen == 0) { 1807 LOGE("invalid response: NULL"); 1808 return RIL_ERRNO_INVALID_RESPONSE; 1809 } 1810 1811 if (responselen != sizeof (RIL_CDMA_SignalInfoRecord)) { 1812 LOGE("invalid response length %d expected sizeof (RIL_CDMA_SignalInfoRecord) of %d\n", 1813 (int)responselen, (int)sizeof (RIL_CDMA_SignalInfoRecord)); 1814 return RIL_ERRNO_INVALID_RESPONSE; 1815 } 1816 1817 startResponse; 1818 1819 RIL_CDMA_SignalInfoRecord *p_cur = ((RIL_CDMA_SignalInfoRecord *) response); 1820 marshallSignalInfoRecord(p, *p_cur); 1821 1822 appendPrintBuf("%s[isPresent=%d,signalType=%d,alertPitch=%d\ 1823 signal=%d]", 1824 printBuf, 1825 p_cur->isPresent, 1826 p_cur->signalType, 1827 p_cur->alertPitch, 1828 p_cur->signal); 1829 1830 closeResponse; 1831 return 0; 1832} 1833 1834static int responseCdmaCallWaiting(Parcel &p, void *response, 1835 size_t responselen) { 1836 if (response == NULL && responselen != 0) { 1837 LOGE("invalid response: NULL"); 1838 return RIL_ERRNO_INVALID_RESPONSE; 1839 } 1840 1841 if (responselen != sizeof(RIL_CDMA_CallWaiting)) { 1842 LOGE("invalid response length %d expected %d\n", 1843 (int)responselen, (int)sizeof(RIL_CDMA_CallWaiting)); 1844 return RIL_ERRNO_INVALID_RESPONSE; 1845 } 1846 1847 startResponse; 1848 RIL_CDMA_CallWaiting *p_cur = ((RIL_CDMA_CallWaiting *) response); 1849 1850 writeStringToParcel (p, p_cur->number); 1851 p.writeInt32(p_cur->numberPresentation); 1852 writeStringToParcel (p, p_cur->name); 1853 marshallSignalInfoRecord(p, p_cur->signalInfoRecord); 1854 1855 appendPrintBuf("%snumber=%s,numberPresentation=%d, name=%s,\ 1856 signalInfoRecord[isPresent=%d,signalType=%d,alertPitch=%d\ 1857 signal=%d]", 1858 printBuf, 1859 p_cur->number, 1860 p_cur->numberPresentation, 1861 p_cur->name, 1862 p_cur->signalInfoRecord.isPresent, 1863 p_cur->signalInfoRecord.signalType, 1864 p_cur->signalInfoRecord.alertPitch, 1865 p_cur->signalInfoRecord.signal); 1866 1867 closeResponse; 1868 1869 return 0; 1870} 1871 1872static void triggerEvLoop() { 1873 int ret; 1874 if (!pthread_equal(pthread_self(), s_tid_dispatch)) { 1875 /* trigger event loop to wakeup. No reason to do this, 1876 * if we're in the event loop thread */ 1877 do { 1878 ret = write (s_fdWakeupWrite, " ", 1); 1879 } while (ret < 0 && errno == EINTR); 1880 } 1881} 1882 1883static void rilEventAddWakeup(struct ril_event *ev) { 1884 ril_event_add(ev); 1885 triggerEvLoop(); 1886} 1887 1888static int responseSimStatus(Parcel &p, void *response, size_t responselen) { 1889 int i; 1890 1891 if (response == NULL && responselen != 0) { 1892 LOGE("invalid response: NULL"); 1893 return RIL_ERRNO_INVALID_RESPONSE; 1894 } 1895 1896 if (responselen % sizeof (RIL_CardStatus *) != 0) { 1897 LOGE("invalid response length %d expected multiple of %d\n", 1898 (int)responselen, (int)sizeof (RIL_CardStatus *)); 1899 return RIL_ERRNO_INVALID_RESPONSE; 1900 } 1901 1902 RIL_CardStatus *p_cur = ((RIL_CardStatus *) response); 1903 1904 p.writeInt32(p_cur->card_state); 1905 p.writeInt32(p_cur->universal_pin_state); 1906 p.writeInt32(p_cur->gsm_umts_subscription_app_index); 1907 p.writeInt32(p_cur->cdma_subscription_app_index); 1908 p.writeInt32(p_cur->num_applications); 1909 1910 startResponse; 1911 for (i = 0; i < p_cur->num_applications; i++) { 1912 p.writeInt32(p_cur->applications[i].app_type); 1913 p.writeInt32(p_cur->applications[i].app_state); 1914 p.writeInt32(p_cur->applications[i].perso_substate); 1915 writeStringToParcel(p, (const char*)(p_cur->applications[i].aid_ptr)); 1916 writeStringToParcel(p, (const char*) 1917 (p_cur->applications[i].app_label_ptr)); 1918 p.writeInt32(p_cur->applications[i].pin1_replaced); 1919 p.writeInt32(p_cur->applications[i].pin1); 1920 p.writeInt32(p_cur->applications[i].pin2); 1921 appendPrintBuf("%s[app_type=%d,app_state=%d,perso_substate=%d,\ 1922 aid_ptr=%s,app_label_ptr=%s,pin1_replaced=%d,pin1=%d,pin2=%d],", 1923 printBuf, 1924 p_cur->applications[i].app_type, 1925 p_cur->applications[i].app_state, 1926 p_cur->applications[i].perso_substate, 1927 p_cur->applications[i].aid_ptr, 1928 p_cur->applications[i].app_label_ptr, 1929 p_cur->applications[i].pin1_replaced, 1930 p_cur->applications[i].pin1, 1931 p_cur->applications[i].pin2); 1932 } 1933 closeResponse; 1934 1935 return 0; 1936} 1937 1938static int responseGsmBrSmsCnf(Parcel &p, void *response, size_t responselen) { 1939 int num = responselen / sizeof(RIL_GSM_BroadcastSmsConfigInfo *); 1940 p.writeInt32(num); 1941 1942 startResponse; 1943 RIL_GSM_BroadcastSmsConfigInfo **p_cur = 1944 (RIL_GSM_BroadcastSmsConfigInfo **) response; 1945 for (int i = 0; i < num; i++) { 1946 p.writeInt32(p_cur[i]->fromServiceId); 1947 p.writeInt32(p_cur[i]->toServiceId); 1948 p.writeInt32(p_cur[i]->fromCodeScheme); 1949 p.writeInt32(p_cur[i]->toCodeScheme); 1950 p.writeInt32(p_cur[i]->selected); 1951 1952 appendPrintBuf("%s [%d: fromServiceId=%d, toServiceId=%d, \ 1953 fromCodeScheme=%d, toCodeScheme=%d, selected =%d]", 1954 printBuf, i, p_cur[i]->fromServiceId, p_cur[i]->toServiceId, 1955 p_cur[i]->fromCodeScheme, p_cur[i]->toCodeScheme, 1956 p_cur[i]->selected); 1957 } 1958 closeResponse; 1959 1960 return 0; 1961} 1962 1963static int responseCdmaBrSmsCnf(Parcel &p, void *response, size_t responselen) { 1964 RIL_CDMA_BroadcastSmsConfigInfo **p_cur = 1965 (RIL_CDMA_BroadcastSmsConfigInfo **) response; 1966 1967 int num = responselen / sizeof (RIL_CDMA_BroadcastSmsConfigInfo *); 1968 p.writeInt32(num); 1969 1970 startResponse; 1971 for (int i = 0 ; i < num ; i++ ) { 1972 p.writeInt32(p_cur[i]->service_category); 1973 p.writeInt32(p_cur[i]->language); 1974 p.writeInt32(p_cur[i]->selected); 1975 1976 appendPrintBuf("%s [%d: srvice_category=%d, language =%d, \ 1977 selected =%d], ", 1978 printBuf, i, p_cur[i]->service_category, p_cur[i]->language, 1979 p_cur[i]->selected); 1980 } 1981 closeResponse; 1982 1983 return 0; 1984} 1985 1986static int responseCdmaSms(Parcel &p, void *response, size_t responselen) { 1987 int num; 1988 int digitCount; 1989 int digitLimit; 1990 uint8_t uct; 1991 void* dest; 1992 1993 LOGD("Inside responseCdmaSms"); 1994 1995 if (response == NULL && responselen != 0) { 1996 LOGE("invalid response: NULL"); 1997 return RIL_ERRNO_INVALID_RESPONSE; 1998 } 1999 2000 if (responselen != sizeof(RIL_CDMA_SMS_Message)) { 2001 LOGE("invalid response length was %d expected %d", 2002 (int)responselen, (int)sizeof(RIL_CDMA_SMS_Message)); 2003 return RIL_ERRNO_INVALID_RESPONSE; 2004 } 2005 2006 RIL_CDMA_SMS_Message *p_cur = (RIL_CDMA_SMS_Message *) response; 2007 p.writeInt32(p_cur->uTeleserviceID); 2008 p.write(&(p_cur->bIsServicePresent),sizeof(uct)); 2009 p.writeInt32(p_cur->uServicecategory); 2010 p.writeInt32(p_cur->sAddress.digit_mode); 2011 p.writeInt32(p_cur->sAddress.number_mode); 2012 p.writeInt32(p_cur->sAddress.number_type); 2013 p.writeInt32(p_cur->sAddress.number_plan); 2014 p.write(&(p_cur->sAddress.number_of_digits), sizeof(uct)); 2015 digitLimit= MIN((p_cur->sAddress.number_of_digits), RIL_CDMA_SMS_ADDRESS_MAX); 2016 for(digitCount =0 ; digitCount < digitLimit; digitCount ++) { 2017 p.write(&(p_cur->sAddress.digits[digitCount]),sizeof(uct)); 2018 } 2019 2020 p.writeInt32(p_cur->sSubAddress.subaddressType); 2021 p.write(&(p_cur->sSubAddress.odd),sizeof(uct)); 2022 p.write(&(p_cur->sSubAddress.number_of_digits),sizeof(uct)); 2023 digitLimit= MIN((p_cur->sSubAddress.number_of_digits), RIL_CDMA_SMS_SUBADDRESS_MAX); 2024 for(digitCount =0 ; digitCount < digitLimit; digitCount ++) { 2025 p.write(&(p_cur->sSubAddress.digits[digitCount]),sizeof(uct)); 2026 } 2027 2028 digitLimit= MIN((p_cur->uBearerDataLen), RIL_CDMA_SMS_BEARER_DATA_MAX); 2029 p.writeInt32(p_cur->uBearerDataLen); 2030 for(digitCount =0 ; digitCount < digitLimit; digitCount ++) { 2031 p.write(&(p_cur->aBearerData[digitCount]), sizeof(uct)); 2032 } 2033 2034 startResponse; 2035 appendPrintBuf("%suTeleserviceID=%d, bIsServicePresent=%d, uServicecategory=%d, \ 2036 sAddress.digit_mode=%d, sAddress.number_mode=%d, sAddress.number_type=%d, ", 2037 printBuf, p_cur->uTeleserviceID,p_cur->bIsServicePresent,p_cur->uServicecategory, 2038 p_cur->sAddress.digit_mode, p_cur->sAddress.number_mode,p_cur->sAddress.number_type); 2039 closeResponse; 2040 2041 return 0; 2042} 2043 2044/** 2045 * A write on the wakeup fd is done just to pop us out of select() 2046 * We empty the buffer here and then ril_event will reset the timers on the 2047 * way back down 2048 */ 2049static void processWakeupCallback(int fd, short flags, void *param) { 2050 char buff[16]; 2051 int ret; 2052 2053 LOGV("processWakeupCallback"); 2054 2055 /* empty our wakeup socket out */ 2056 do { 2057 ret = read(s_fdWakeupRead, &buff, sizeof(buff)); 2058 } while (ret > 0 || (ret < 0 && errno == EINTR)); 2059} 2060 2061static void onCommandsSocketClosed() { 2062 int ret; 2063 RequestInfo *p_cur; 2064 2065 /* mark pending requests as "cancelled" so we dont report responses */ 2066 2067 ret = pthread_mutex_lock(&s_pendingRequestsMutex); 2068 assert (ret == 0); 2069 2070 p_cur = s_pendingRequests; 2071 2072 for (p_cur = s_pendingRequests 2073 ; p_cur != NULL 2074 ; p_cur = p_cur->p_next 2075 ) { 2076 p_cur->cancelled = 1; 2077 } 2078 2079 ret = pthread_mutex_unlock(&s_pendingRequestsMutex); 2080 assert (ret == 0); 2081} 2082 2083static void processCommandsCallback(int fd, short flags, void *param) { 2084 RecordStream *p_rs; 2085 void *p_record; 2086 size_t recordlen; 2087 int ret; 2088 2089 assert(fd == s_fdCommand); 2090 2091 p_rs = (RecordStream *)param; 2092 2093 for (;;) { 2094 /* loop until EAGAIN/EINTR, end of stream, or other error */ 2095 ret = record_stream_get_next(p_rs, &p_record, &recordlen); 2096 2097 if (ret == 0 && p_record == NULL) { 2098 /* end-of-stream */ 2099 break; 2100 } else if (ret < 0) { 2101 break; 2102 } else if (ret == 0) { /* && p_record != NULL */ 2103 processCommandBuffer(p_record, recordlen); 2104 } 2105 } 2106 2107 if (ret == 0 || !(errno == EAGAIN || errno == EINTR)) { 2108 /* fatal error or end-of-stream */ 2109 if (ret != 0) { 2110 LOGE("error on reading command socket errno:%d\n", errno); 2111 } else { 2112 LOGW("EOS. Closing command socket."); 2113 } 2114 2115 close(s_fdCommand); 2116 s_fdCommand = -1; 2117 2118 ril_event_del(&s_commands_event); 2119 2120 record_stream_free(p_rs); 2121 2122 /* start listening for new connections again */ 2123 rilEventAddWakeup(&s_listen_event); 2124 2125 onCommandsSocketClosed(); 2126 } 2127} 2128 2129 2130static void onNewCommandConnect() { 2131 // implicit radio state changed 2132 RIL_onUnsolicitedResponse(RIL_UNSOL_RESPONSE_RADIO_STATE_CHANGED, 2133 NULL, 0); 2134 2135 // Send last NITZ time data, in case it was missed 2136 if (s_lastNITZTimeData != NULL) { 2137 sendResponseRaw(s_lastNITZTimeData, s_lastNITZTimeDataSize); 2138 2139 free(s_lastNITZTimeData); 2140 s_lastNITZTimeData = NULL; 2141 } 2142 2143 // Get version string 2144 if (s_callbacks.getVersion != NULL) { 2145 const char *version; 2146 version = s_callbacks.getVersion(); 2147 LOGI("RIL Daemon version: %s\n", version); 2148 2149 property_set(PROPERTY_RIL_IMPL, version); 2150 } else { 2151 LOGI("RIL Daemon version: unavailable\n"); 2152 property_set(PROPERTY_RIL_IMPL, "unavailable"); 2153 } 2154 2155} 2156 2157static void listenCallback (int fd, short flags, void *param) { 2158 int ret; 2159 int err; 2160 int is_phone_socket; 2161 RecordStream *p_rs; 2162 2163 struct sockaddr_un peeraddr; 2164 socklen_t socklen = sizeof (peeraddr); 2165 2166 struct ucred creds; 2167 socklen_t szCreds = sizeof(creds); 2168 2169 struct passwd *pwd = NULL; 2170 2171 assert (s_fdCommand < 0); 2172 assert (fd == s_fdListen); 2173 2174 s_fdCommand = accept(s_fdListen, (sockaddr *) &peeraddr, &socklen); 2175 2176 if (s_fdCommand < 0 ) { 2177 LOGE("Error on accept() errno:%d", errno); 2178 /* start listening for new connections again */ 2179 rilEventAddWakeup(&s_listen_event); 2180 return; 2181 } 2182 2183 /* check the credential of the other side and only accept socket from 2184 * phone process 2185 */ 2186 errno = 0; 2187 is_phone_socket = 0; 2188 2189 err = getsockopt(s_fdCommand, SOL_SOCKET, SO_PEERCRED, &creds, &szCreds); 2190 2191 if (err == 0 && szCreds > 0) { 2192 errno = 0; 2193 pwd = getpwuid(creds.uid); 2194 if (pwd != NULL) { 2195 if (strcmp(pwd->pw_name, PHONE_PROCESS) == 0) { 2196 is_phone_socket = 1; 2197 } else { 2198 LOGE("RILD can't accept socket from process %s", pwd->pw_name); 2199 } 2200 } else { 2201 LOGE("Error on getpwuid() errno: %d", errno); 2202 } 2203 } else { 2204 LOGD("Error on getsockopt() errno: %d", errno); 2205 } 2206 2207 if ( !is_phone_socket ) { 2208 LOGE("RILD must accept socket from %s", PHONE_PROCESS); 2209 2210 close(s_fdCommand); 2211 s_fdCommand = -1; 2212 2213 onCommandsSocketClosed(); 2214 2215 /* start listening for new connections again */ 2216 rilEventAddWakeup(&s_listen_event); 2217 2218 return; 2219 } 2220 2221 ret = fcntl(s_fdCommand, F_SETFL, O_NONBLOCK); 2222 2223 if (ret < 0) { 2224 LOGE ("Error setting O_NONBLOCK errno:%d", errno); 2225 } 2226 2227 LOGI("libril: new connection"); 2228 2229 p_rs = record_stream_new(s_fdCommand, MAX_COMMAND_BYTES); 2230 2231 ril_event_set (&s_commands_event, s_fdCommand, 1, 2232 processCommandsCallback, p_rs); 2233 2234 rilEventAddWakeup (&s_commands_event); 2235 2236 onNewCommandConnect(); 2237} 2238 2239static void freeDebugCallbackArgs(int number, char **args) { 2240 for (int i = 0; i < number; i++) { 2241 if (args[i] != NULL) { 2242 free(args[i]); 2243 } 2244 } 2245 free(args); 2246} 2247 2248static void debugCallback (int fd, short flags, void *param) { 2249 int acceptFD, option; 2250 struct sockaddr_un peeraddr; 2251 socklen_t socklen = sizeof (peeraddr); 2252 int data; 2253 unsigned int qxdm_data[6]; 2254 const char *deactData[1] = {"1"}; 2255 char *actData[1]; 2256 RIL_Dial dialData; 2257 int hangupData[1] = {1}; 2258 int number; 2259 char **args; 2260 2261 acceptFD = accept (fd, (sockaddr *) &peeraddr, &socklen); 2262 2263 if (acceptFD < 0) { 2264 LOGE ("error accepting on debug port: %d\n", errno); 2265 return; 2266 } 2267 2268 if (recv(acceptFD, &number, sizeof(int), 0) != sizeof(int)) { 2269 LOGE ("error reading on socket: number of Args: \n"); 2270 return; 2271 } 2272 args = (char **) malloc(sizeof(char*) * number); 2273 2274 for (int i = 0; i < number; i++) { 2275 int len; 2276 if (recv(acceptFD, &len, sizeof(int), 0) != sizeof(int)) { 2277 LOGE ("error reading on socket: Len of Args: \n"); 2278 freeDebugCallbackArgs(i, args); 2279 return; 2280 } 2281 // +1 for null-term 2282 args[i] = (char *) malloc((sizeof(char) * len) + 1); 2283 if (recv(acceptFD, args[i], sizeof(char) * len, 0) 2284 != (int)sizeof(char) * len) { 2285 LOGE ("error reading on socket: Args[%d] \n", i); 2286 freeDebugCallbackArgs(i, args); 2287 return; 2288 } 2289 char * buf = args[i]; 2290 buf[len] = 0; 2291 } 2292 2293 switch (atoi(args[0])) { 2294 case 0: 2295 LOGI ("Connection on debug port: issuing reset."); 2296 issueLocalRequest(RIL_REQUEST_RESET_RADIO, NULL, 0); 2297 break; 2298 case 1: 2299 LOGI ("Connection on debug port: issuing radio power off."); 2300 data = 0; 2301 issueLocalRequest(RIL_REQUEST_RADIO_POWER, &data, sizeof(int)); 2302 // Close the socket 2303 close(s_fdCommand); 2304 s_fdCommand = -1; 2305 break; 2306 case 2: 2307 LOGI ("Debug port: issuing unsolicited network change."); 2308 RIL_onUnsolicitedResponse(RIL_UNSOL_RESPONSE_NETWORK_STATE_CHANGED, 2309 NULL, 0); 2310 break; 2311 case 3: 2312 LOGI ("Debug port: QXDM log enable."); 2313 qxdm_data[0] = 65536; 2314 qxdm_data[1] = 16; 2315 qxdm_data[2] = 1; 2316 qxdm_data[3] = 32; 2317 qxdm_data[4] = 0; 2318 qxdm_data[4] = 8; 2319 issueLocalRequest(RIL_REQUEST_OEM_HOOK_RAW, qxdm_data, 2320 6 * sizeof(int)); 2321 break; 2322 case 4: 2323 LOGI ("Debug port: QXDM log disable."); 2324 qxdm_data[0] = 65536; 2325 qxdm_data[1] = 16; 2326 qxdm_data[2] = 0; 2327 qxdm_data[3] = 32; 2328 qxdm_data[4] = 0; 2329 qxdm_data[4] = 8; 2330 issueLocalRequest(RIL_REQUEST_OEM_HOOK_RAW, qxdm_data, 2331 6 * sizeof(int)); 2332 break; 2333 case 5: 2334 LOGI("Debug port: Radio On"); 2335 data = 1; 2336 issueLocalRequest(RIL_REQUEST_RADIO_POWER, &data, sizeof(int)); 2337 sleep(2); 2338 // Set network selection automatic. 2339 issueLocalRequest(RIL_REQUEST_SET_NETWORK_SELECTION_AUTOMATIC, NULL, 0); 2340 break; 2341 case 6: 2342 LOGI("Debug port: Setup Data Call, Apn :%s\n", args[1]); 2343 actData[0] = args[1]; 2344 issueLocalRequest(RIL_REQUEST_SETUP_DATA_CALL, &actData, 2345 sizeof(actData)); 2346 break; 2347 case 7: 2348 LOGI("Debug port: Deactivate Data Call"); 2349 issueLocalRequest(RIL_REQUEST_DEACTIVATE_DATA_CALL, &deactData, 2350 sizeof(deactData)); 2351 break; 2352 case 8: 2353 LOGI("Debug port: Dial Call"); 2354 dialData.clir = 0; 2355 dialData.address = args[1]; 2356 issueLocalRequest(RIL_REQUEST_DIAL, &dialData, sizeof(dialData)); 2357 break; 2358 case 9: 2359 LOGI("Debug port: Answer Call"); 2360 issueLocalRequest(RIL_REQUEST_ANSWER, NULL, 0); 2361 break; 2362 case 10: 2363 LOGI("Debug port: End Call"); 2364 issueLocalRequest(RIL_REQUEST_HANGUP, &hangupData, 2365 sizeof(hangupData)); 2366 break; 2367 default: 2368 LOGE ("Invalid request"); 2369 break; 2370 } 2371 freeDebugCallbackArgs(number, args); 2372 close(acceptFD); 2373} 2374 2375 2376static void userTimerCallback (int fd, short flags, void *param) { 2377 UserCallbackInfo *p_info; 2378 2379 p_info = (UserCallbackInfo *)param; 2380 2381 p_info->p_callback(p_info->userParam); 2382 2383 2384 // FIXME generalize this...there should be a cancel mechanism 2385 if (s_last_wake_timeout_info != NULL && s_last_wake_timeout_info == p_info) { 2386 s_last_wake_timeout_info = NULL; 2387 } 2388 2389 free(p_info); 2390} 2391 2392 2393static void * 2394eventLoop(void *param) { 2395 int ret; 2396 int filedes[2]; 2397 2398 ril_event_init(); 2399 2400 pthread_mutex_lock(&s_startupMutex); 2401 2402 s_started = 1; 2403 pthread_cond_broadcast(&s_startupCond); 2404 2405 pthread_mutex_unlock(&s_startupMutex); 2406 2407 ret = pipe(filedes); 2408 2409 if (ret < 0) { 2410 LOGE("Error in pipe() errno:%d", errno); 2411 return NULL; 2412 } 2413 2414 s_fdWakeupRead = filedes[0]; 2415 s_fdWakeupWrite = filedes[1]; 2416 2417 fcntl(s_fdWakeupRead, F_SETFL, O_NONBLOCK); 2418 2419 ril_event_set (&s_wakeupfd_event, s_fdWakeupRead, true, 2420 processWakeupCallback, NULL); 2421 2422 rilEventAddWakeup (&s_wakeupfd_event); 2423 2424 // Only returns on error 2425 ril_event_loop(); 2426 LOGE ("error in event_loop_base errno:%d", errno); 2427 2428 return NULL; 2429} 2430 2431extern "C" void 2432RIL_startEventLoop(void) { 2433 int ret; 2434 pthread_attr_t attr; 2435 2436 /* spin up eventLoop thread and wait for it to get started */ 2437 s_started = 0; 2438 pthread_mutex_lock(&s_startupMutex); 2439 2440 pthread_attr_init (&attr); 2441 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); 2442 ret = pthread_create(&s_tid_dispatch, &attr, eventLoop, NULL); 2443 2444 while (s_started == 0) { 2445 pthread_cond_wait(&s_startupCond, &s_startupMutex); 2446 } 2447 2448 pthread_mutex_unlock(&s_startupMutex); 2449 2450 if (ret < 0) { 2451 LOGE("Failed to create dispatch thread errno:%d", errno); 2452 return; 2453 } 2454} 2455 2456// Used for testing purpose only. 2457extern "C" void RIL_setcallbacks (const RIL_RadioFunctions *callbacks) { 2458 memcpy(&s_callbacks, callbacks, sizeof (RIL_RadioFunctions)); 2459} 2460 2461extern "C" void 2462RIL_register (const RIL_RadioFunctions *callbacks) { 2463 int ret; 2464 int flags; 2465 2466 if (callbacks == NULL 2467 || ! (callbacks->version == RIL_VERSION || callbacks->version == 1) 2468 ) { 2469 LOGE( 2470 "RIL_register: RIL_RadioFunctions * null or invalid version" 2471 " (expected %d)", RIL_VERSION); 2472 return; 2473 } 2474 2475 if (s_registerCalled > 0) { 2476 LOGE("RIL_register has been called more than once. " 2477 "Subsequent call ignored"); 2478 return; 2479 } 2480 2481 memcpy(&s_callbacks, callbacks, sizeof (RIL_RadioFunctions)); 2482 2483 s_registerCalled = 1; 2484 2485 // Little self-check 2486 2487 for (int i = 0; i < (int)NUM_ELEMS(s_commands); i++) { 2488 assert(i == s_commands[i].requestNumber); 2489 } 2490 2491 for (int i = 0; i < (int)NUM_ELEMS(s_unsolResponses); i++) { 2492 assert(i + RIL_UNSOL_RESPONSE_BASE 2493 == s_unsolResponses[i].requestNumber); 2494 } 2495 2496 // New rild impl calls RIL_startEventLoop() first 2497 // old standalone impl wants it here. 2498 2499 if (s_started == 0) { 2500 RIL_startEventLoop(); 2501 } 2502 2503 // start listen socket 2504 2505#if 0 2506 ret = socket_local_server (SOCKET_NAME_RIL, 2507 ANDROID_SOCKET_NAMESPACE_ABSTRACT, SOCK_STREAM); 2508 2509 if (ret < 0) { 2510 LOGE("Unable to bind socket errno:%d", errno); 2511 exit (-1); 2512 } 2513 s_fdListen = ret; 2514 2515#else 2516 s_fdListen = android_get_control_socket(SOCKET_NAME_RIL); 2517 if (s_fdListen < 0) { 2518 LOGE("Failed to get socket '" SOCKET_NAME_RIL "'"); 2519 exit(-1); 2520 } 2521 2522 ret = listen(s_fdListen, 4); 2523 2524 if (ret < 0) { 2525 LOGE("Failed to listen on control socket '%d': %s", 2526 s_fdListen, strerror(errno)); 2527 exit(-1); 2528 } 2529#endif 2530 2531 2532 /* note: non-persistent so we can accept only one connection at a time */ 2533 ril_event_set (&s_listen_event, s_fdListen, false, 2534 listenCallback, NULL); 2535 2536 rilEventAddWakeup (&s_listen_event); 2537 2538#if 1 2539 // start debug interface socket 2540 2541 s_fdDebug = android_get_control_socket(SOCKET_NAME_RIL_DEBUG); 2542 if (s_fdDebug < 0) { 2543 LOGE("Failed to get socket '" SOCKET_NAME_RIL_DEBUG "' errno:%d", errno); 2544 exit(-1); 2545 } 2546 2547 ret = listen(s_fdDebug, 4); 2548 2549 if (ret < 0) { 2550 LOGE("Failed to listen on ril debug socket '%d': %s", 2551 s_fdDebug, strerror(errno)); 2552 exit(-1); 2553 } 2554 2555 ril_event_set (&s_debug_event, s_fdDebug, true, 2556 debugCallback, NULL); 2557 2558 rilEventAddWakeup (&s_debug_event); 2559#endif 2560 2561} 2562 2563static int 2564checkAndDequeueRequestInfo(struct RequestInfo *pRI) { 2565 int ret = 0; 2566 2567 if (pRI == NULL) { 2568 return 0; 2569 } 2570 2571 pthread_mutex_lock(&s_pendingRequestsMutex); 2572 2573 for(RequestInfo **ppCur = &s_pendingRequests 2574 ; *ppCur != NULL 2575 ; ppCur = &((*ppCur)->p_next) 2576 ) { 2577 if (pRI == *ppCur) { 2578 ret = 1; 2579 2580 *ppCur = (*ppCur)->p_next; 2581 break; 2582 } 2583 } 2584 2585 pthread_mutex_unlock(&s_pendingRequestsMutex); 2586 2587 return ret; 2588} 2589 2590 2591extern "C" void 2592RIL_onRequestComplete(RIL_Token t, RIL_Errno e, void *response, size_t responselen) { 2593 RequestInfo *pRI; 2594 int ret; 2595 size_t errorOffset; 2596 2597 pRI = (RequestInfo *)t; 2598 2599 if (!checkAndDequeueRequestInfo(pRI)) { 2600 LOGE ("RIL_onRequestComplete: invalid RIL_Token"); 2601 return; 2602 } 2603 2604 if (pRI->local > 0) { 2605 // Locally issued command...void only! 2606 // response does not go back up the command socket 2607 LOGD("C[locl]< %s", requestToString(pRI->pCI->requestNumber)); 2608 2609 goto done; 2610 } 2611 2612 appendPrintBuf("[%04d]< %s", 2613 pRI->token, requestToString(pRI->pCI->requestNumber)); 2614 2615 if (pRI->cancelled == 0) { 2616 Parcel p; 2617 2618 p.writeInt32 (RESPONSE_SOLICITED); 2619 p.writeInt32 (pRI->token); 2620 errorOffset = p.dataPosition(); 2621 2622 p.writeInt32 (e); 2623 2624 if (response != NULL) { 2625 // there is a response payload, no matter success or not. 2626 ret = pRI->pCI->responseFunction(p, response, responselen); 2627 2628 /* if an error occurred, rewind and mark it */ 2629 if (ret != 0) { 2630 p.setDataPosition(errorOffset); 2631 p.writeInt32 (ret); 2632 } 2633 } 2634 2635 if (e != RIL_E_SUCCESS) { 2636 appendPrintBuf("%s fails by %s", printBuf, failCauseToString(e)); 2637 } 2638 2639 if (s_fdCommand < 0) { 2640 LOGD ("RIL onRequestComplete: Command channel closed"); 2641 } 2642 sendResponse(p); 2643 } 2644 2645done: 2646 free(pRI); 2647} 2648 2649 2650static void 2651grabPartialWakeLock() { 2652 acquire_wake_lock(PARTIAL_WAKE_LOCK, ANDROID_WAKE_LOCK_NAME); 2653} 2654 2655static void 2656releaseWakeLock() { 2657 release_wake_lock(ANDROID_WAKE_LOCK_NAME); 2658} 2659 2660/** 2661 * Timer callback to put us back to sleep before the default timeout 2662 */ 2663static void 2664wakeTimeoutCallback (void *param) { 2665 // We're using "param != NULL" as a cancellation mechanism 2666 if (param == NULL) { 2667 //LOGD("wakeTimeout: releasing wake lock"); 2668 2669 releaseWakeLock(); 2670 } else { 2671 //LOGD("wakeTimeout: releasing wake lock CANCELLED"); 2672 } 2673} 2674 2675extern "C" 2676void RIL_onUnsolicitedResponse(int unsolResponse, void *data, 2677 size_t datalen) 2678{ 2679 int unsolResponseIndex; 2680 int ret; 2681 int64_t timeReceived = 0; 2682 bool shouldScheduleTimeout = false; 2683 2684 if (s_registerCalled == 0) { 2685 // Ignore RIL_onUnsolicitedResponse before RIL_register 2686 LOGW("RIL_onUnsolicitedResponse called before RIL_register"); 2687 return; 2688 } 2689 2690 unsolResponseIndex = unsolResponse - RIL_UNSOL_RESPONSE_BASE; 2691 2692 if ((unsolResponseIndex < 0) 2693 || (unsolResponseIndex >= (int32_t)NUM_ELEMS(s_unsolResponses))) { 2694 LOGE("unsupported unsolicited response code %d", unsolResponse); 2695 return; 2696 } 2697 2698 // Grab a wake lock if needed for this reponse, 2699 // as we exit we'll either release it immediately 2700 // or set a timer to release it later. 2701 switch (s_unsolResponses[unsolResponseIndex].wakeType) { 2702 case WAKE_PARTIAL: 2703 grabPartialWakeLock(); 2704 shouldScheduleTimeout = true; 2705 break; 2706 2707 case DONT_WAKE: 2708 default: 2709 // No wake lock is grabed so don't set timeout 2710 shouldScheduleTimeout = false; 2711 break; 2712 } 2713 2714 // Mark the time this was received, doing this 2715 // after grabing the wakelock incase getting 2716 // the elapsedRealTime might cause us to goto 2717 // sleep. 2718 if (unsolResponse == RIL_UNSOL_NITZ_TIME_RECEIVED) { 2719 timeReceived = elapsedRealtime(); 2720 } 2721 2722 appendPrintBuf("[UNSL]< %s", requestToString(unsolResponse)); 2723 2724 Parcel p; 2725 2726 p.writeInt32 (RESPONSE_UNSOLICITED); 2727 p.writeInt32 (unsolResponse); 2728 2729 ret = s_unsolResponses[unsolResponseIndex] 2730 .responseFunction(p, data, datalen); 2731 if (ret != 0) { 2732 // Problem with the response. Don't continue; 2733 goto error_exit; 2734 } 2735 2736 // some things get more payload 2737 switch(unsolResponse) { 2738 case RIL_UNSOL_RESPONSE_RADIO_STATE_CHANGED: 2739 p.writeInt32(s_callbacks.onStateRequest()); 2740 appendPrintBuf("%s {%s}", printBuf, 2741 radioStateToString(s_callbacks.onStateRequest())); 2742 break; 2743 2744 2745 case RIL_UNSOL_NITZ_TIME_RECEIVED: 2746 // Store the time that this was received so the 2747 // handler of this message can account for 2748 // the time it takes to arrive and process. In 2749 // particular the system has been known to sleep 2750 // before this message can be processed. 2751 p.writeInt64(timeReceived); 2752 break; 2753 } 2754 2755 ret = sendResponse(p); 2756 if (ret != 0 && unsolResponse == RIL_UNSOL_NITZ_TIME_RECEIVED) { 2757 2758 // Unfortunately, NITZ time is not poll/update like everything 2759 // else in the system. So, if the upstream client isn't connected, 2760 // keep a copy of the last NITZ response (with receive time noted 2761 // above) around so we can deliver it when it is connected 2762 2763 if (s_lastNITZTimeData != NULL) { 2764 free (s_lastNITZTimeData); 2765 s_lastNITZTimeData = NULL; 2766 } 2767 2768 s_lastNITZTimeData = malloc(p.dataSize()); 2769 s_lastNITZTimeDataSize = p.dataSize(); 2770 memcpy(s_lastNITZTimeData, p.data(), p.dataSize()); 2771 } 2772 2773 // For now, we automatically go back to sleep after TIMEVAL_WAKE_TIMEOUT 2774 // FIXME The java code should handshake here to release wake lock 2775 2776 if (shouldScheduleTimeout) { 2777 // Cancel the previous request 2778 if (s_last_wake_timeout_info != NULL) { 2779 s_last_wake_timeout_info->userParam = (void *)1; 2780 } 2781 2782 s_last_wake_timeout_info 2783 = internalRequestTimedCallback(wakeTimeoutCallback, NULL, 2784 &TIMEVAL_WAKE_TIMEOUT); 2785 } 2786 2787 // Normal exit 2788 return; 2789 2790error_exit: 2791 if (shouldScheduleTimeout) { 2792 releaseWakeLock(); 2793 } 2794} 2795 2796/** FIXME generalize this if you track UserCAllbackInfo, clear it 2797 when the callback occurs 2798*/ 2799static UserCallbackInfo * 2800internalRequestTimedCallback (RIL_TimedCallback callback, void *param, 2801 const struct timeval *relativeTime) 2802{ 2803 struct timeval myRelativeTime; 2804 UserCallbackInfo *p_info; 2805 2806 p_info = (UserCallbackInfo *) malloc (sizeof(UserCallbackInfo)); 2807 2808 p_info->p_callback = callback; 2809 p_info->userParam = param; 2810 2811 if (relativeTime == NULL) { 2812 /* treat null parameter as a 0 relative time */ 2813 memset (&myRelativeTime, 0, sizeof(myRelativeTime)); 2814 } else { 2815 /* FIXME I think event_add's tv param is really const anyway */ 2816 memcpy (&myRelativeTime, relativeTime, sizeof(myRelativeTime)); 2817 } 2818 2819 ril_event_set(&(p_info->event), -1, false, userTimerCallback, p_info); 2820 2821 ril_timer_add(&(p_info->event), &myRelativeTime); 2822 2823 triggerEvLoop(); 2824 return p_info; 2825} 2826 2827 2828extern "C" void 2829RIL_requestTimedCallback (RIL_TimedCallback callback, void *param, 2830 const struct timeval *relativeTime) { 2831 internalRequestTimedCallback (callback, param, relativeTime); 2832} 2833 2834const char * 2835failCauseToString(RIL_Errno e) { 2836 switch(e) { 2837 case RIL_E_SUCCESS: return "E_SUCCESS"; 2838 case RIL_E_RADIO_NOT_AVAILABLE: return "E_RAIDO_NOT_AVAILABLE"; 2839 case RIL_E_GENERIC_FAILURE: return "E_GENERIC_FAILURE"; 2840 case RIL_E_PASSWORD_INCORRECT: return "E_PASSWORD_INCORRECT"; 2841 case RIL_E_SIM_PIN2: return "E_SIM_PIN2"; 2842 case RIL_E_SIM_PUK2: return "E_SIM_PUK2"; 2843 case RIL_E_REQUEST_NOT_SUPPORTED: return "E_REQUEST_NOT_SUPPORTED"; 2844 case RIL_E_CANCELLED: return "E_CANCELLED"; 2845 case RIL_E_OP_NOT_ALLOWED_DURING_VOICE_CALL: return "E_OP_NOT_ALLOWED_DURING_VOICE_CALL"; 2846 case RIL_E_OP_NOT_ALLOWED_BEFORE_REG_TO_NW: return "E_OP_NOT_ALLOWED_BEFORE_REG_TO_NW"; 2847 case RIL_E_SMS_SEND_FAIL_RETRY: return "E_SMS_SEND_FAIL_RETRY"; 2848 case RIL_E_SIM_ABSENT:return "E_SIM_ABSENT"; 2849#ifdef FEATURE_MULTIMODE_ANDROID 2850 case RIL_E_SUBSCRIPTION_NOT_AVAILABLE:return "E_SUBSCRIPTION_NOT_AVAILABLE"; 2851 case RIL_E_MODE_NOT_SUPPORTED:return "E_MODE_NOT_SUPPORTED"; 2852#endif 2853 default: return "<unknown error>"; 2854 } 2855} 2856 2857const char * 2858radioStateToString(RIL_RadioState s) { 2859 switch(s) { 2860 case RADIO_STATE_OFF: return "RADIO_OFF"; 2861 case RADIO_STATE_UNAVAILABLE: return "RADIO_UNAVAILABLE"; 2862 case RADIO_STATE_SIM_NOT_READY: return "RADIO_SIM_NOT_READY"; 2863 case RADIO_STATE_SIM_LOCKED_OR_ABSENT: return "RADIO_SIM_LOCKED_OR_ABSENT"; 2864 case RADIO_STATE_SIM_READY: return "RADIO_SIM_READY"; 2865 case RADIO_STATE_RUIM_NOT_READY:return"RADIO_RUIM_NOT_READY"; 2866 case RADIO_STATE_RUIM_READY:return"RADIO_RUIM_READY"; 2867 case RADIO_STATE_RUIM_LOCKED_OR_ABSENT:return"RADIO_RUIM_LOCKED_OR_ABSENT"; 2868 case RADIO_STATE_NV_NOT_READY:return"RADIO_NV_NOT_READY"; 2869 case RADIO_STATE_NV_READY:return"RADIO_NV_READY"; 2870 default: return "<unknown state>"; 2871 } 2872} 2873 2874const char * 2875callStateToString(RIL_CallState s) { 2876 switch(s) { 2877 case RIL_CALL_ACTIVE : return "ACTIVE"; 2878 case RIL_CALL_HOLDING: return "HOLDING"; 2879 case RIL_CALL_DIALING: return "DIALING"; 2880 case RIL_CALL_ALERTING: return "ALERTING"; 2881 case RIL_CALL_INCOMING: return "INCOMING"; 2882 case RIL_CALL_WAITING: return "WAITING"; 2883 default: return "<unknown state>"; 2884 } 2885} 2886 2887const char * 2888requestToString(int request) { 2889/* 2890 cat libs/telephony/ril_commands.h \ 2891 | egrep "^ *{RIL_" \ 2892 | sed -re 's/\{RIL_([^,]+),[^,]+,([^}]+).+/case RIL_\1: return "\1";/' 2893 2894 2895 cat libs/telephony/ril_unsol_commands.h \ 2896 | egrep "^ *{RIL_" \ 2897 | sed -re 's/\{RIL_([^,]+),([^}]+).+/case RIL_\1: return "\1";/' 2898 2899*/ 2900 switch(request) { 2901 case RIL_REQUEST_GET_SIM_STATUS: return "GET_SIM_STATUS"; 2902 case RIL_REQUEST_ENTER_SIM_PIN: return "ENTER_SIM_PIN"; 2903 case RIL_REQUEST_ENTER_SIM_PUK: return "ENTER_SIM_PUK"; 2904 case RIL_REQUEST_ENTER_SIM_PIN2: return "ENTER_SIM_PIN2"; 2905 case RIL_REQUEST_ENTER_SIM_PUK2: return "ENTER_SIM_PUK2"; 2906 case RIL_REQUEST_CHANGE_SIM_PIN: return "CHANGE_SIM_PIN"; 2907 case RIL_REQUEST_CHANGE_SIM_PIN2: return "CHANGE_SIM_PIN2"; 2908 case RIL_REQUEST_ENTER_NETWORK_DEPERSONALIZATION: return "ENTER_NETWORK_DEPERSONALIZATION"; 2909 case RIL_REQUEST_GET_CURRENT_CALLS: return "GET_CURRENT_CALLS"; 2910 case RIL_REQUEST_DIAL: return "DIAL"; 2911 case RIL_REQUEST_GET_IMSI: return "GET_IMSI"; 2912 case RIL_REQUEST_HANGUP: return "HANGUP"; 2913 case RIL_REQUEST_HANGUP_WAITING_OR_BACKGROUND: return "HANGUP_WAITING_OR_BACKGROUND"; 2914 case RIL_REQUEST_HANGUP_FOREGROUND_RESUME_BACKGROUND: return "HANGUP_FOREGROUND_RESUME_BACKGROUND"; 2915 case RIL_REQUEST_SWITCH_WAITING_OR_HOLDING_AND_ACTIVE: return "SWITCH_WAITING_OR_HOLDING_AND_ACTIVE"; 2916 case RIL_REQUEST_CONFERENCE: return "CONFERENCE"; 2917 case RIL_REQUEST_UDUB: return "UDUB"; 2918 case RIL_REQUEST_LAST_CALL_FAIL_CAUSE: return "LAST_CALL_FAIL_CAUSE"; 2919 case RIL_REQUEST_SIGNAL_STRENGTH: return "SIGNAL_STRENGTH"; 2920 case RIL_REQUEST_REGISTRATION_STATE: return "REGISTRATION_STATE"; 2921 case RIL_REQUEST_GPRS_REGISTRATION_STATE: return "GPRS_REGISTRATION_STATE"; 2922 case RIL_REQUEST_OPERATOR: return "OPERATOR"; 2923 case RIL_REQUEST_RADIO_POWER: return "RADIO_POWER"; 2924 case RIL_REQUEST_DTMF: return "DTMF"; 2925 case RIL_REQUEST_SEND_SMS: return "SEND_SMS"; 2926 case RIL_REQUEST_SEND_SMS_EXPECT_MORE: return "SEND_SMS_EXPECT_MORE"; 2927 case RIL_REQUEST_SETUP_DATA_CALL: return "SETUP_DATA_CALL"; 2928 case RIL_REQUEST_SIM_IO: return "SIM_IO"; 2929 case RIL_REQUEST_SEND_USSD: return "SEND_USSD"; 2930 case RIL_REQUEST_CANCEL_USSD: return "CANCEL_USSD"; 2931 case RIL_REQUEST_GET_CLIR: return "GET_CLIR"; 2932 case RIL_REQUEST_SET_CLIR: return "SET_CLIR"; 2933 case RIL_REQUEST_QUERY_CALL_FORWARD_STATUS: return "QUERY_CALL_FORWARD_STATUS"; 2934 case RIL_REQUEST_SET_CALL_FORWARD: return "SET_CALL_FORWARD"; 2935 case RIL_REQUEST_QUERY_CALL_WAITING: return "QUERY_CALL_WAITING"; 2936 case RIL_REQUEST_SET_CALL_WAITING: return "SET_CALL_WAITING"; 2937 case RIL_REQUEST_SMS_ACKNOWLEDGE: return "SMS_ACKNOWLEDGE"; 2938 case RIL_REQUEST_GET_IMEI: return "GET_IMEI"; 2939 case RIL_REQUEST_GET_IMEISV: return "GET_IMEISV"; 2940 case RIL_REQUEST_ANSWER: return "ANSWER"; 2941 case RIL_REQUEST_DEACTIVATE_DATA_CALL: return "DEACTIVATE_DATA_CALL"; 2942 case RIL_REQUEST_QUERY_FACILITY_LOCK: return "QUERY_FACILITY_LOCK"; 2943 case RIL_REQUEST_SET_FACILITY_LOCK: return "SET_FACILITY_LOCK"; 2944 case RIL_REQUEST_CHANGE_BARRING_PASSWORD: return "CHANGE_BARRING_PASSWORD"; 2945 case RIL_REQUEST_QUERY_NETWORK_SELECTION_MODE: return "QUERY_NETWORK_SELECTION_MODE"; 2946 case RIL_REQUEST_SET_NETWORK_SELECTION_AUTOMATIC: return "SET_NETWORK_SELECTION_AUTOMATIC"; 2947 case RIL_REQUEST_SET_NETWORK_SELECTION_MANUAL: return "SET_NETWORK_SELECTION_MANUAL"; 2948 case RIL_REQUEST_QUERY_AVAILABLE_NETWORKS : return "QUERY_AVAILABLE_NETWORKS "; 2949 case RIL_REQUEST_DTMF_START: return "DTMF_START"; 2950 case RIL_REQUEST_DTMF_STOP: return "DTMF_STOP"; 2951 case RIL_REQUEST_BASEBAND_VERSION: return "BASEBAND_VERSION"; 2952 case RIL_REQUEST_SEPARATE_CONNECTION: return "SEPARATE_CONNECTION"; 2953 case RIL_REQUEST_SET_PREFERRED_NETWORK_TYPE: return "SET_PREFERRED_NETWORK_TYPE"; 2954 case RIL_REQUEST_GET_PREFERRED_NETWORK_TYPE: return "GET_PREFERRED_NETWORK_TYPE"; 2955 case RIL_REQUEST_GET_NEIGHBORING_CELL_IDS: return "GET_NEIGHBORING_CELL_IDS"; 2956 case RIL_REQUEST_SET_MUTE: return "SET_MUTE"; 2957 case RIL_REQUEST_GET_MUTE: return "GET_MUTE"; 2958 case RIL_REQUEST_QUERY_CLIP: return "QUERY_CLIP"; 2959 case RIL_REQUEST_LAST_DATA_CALL_FAIL_CAUSE: return "LAST_DATA_CALL_FAIL_CAUSE"; 2960 case RIL_REQUEST_DATA_CALL_LIST: return "DATA_CALL_LIST"; 2961 case RIL_REQUEST_RESET_RADIO: return "RESET_RADIO"; 2962 case RIL_REQUEST_OEM_HOOK_RAW: return "OEM_HOOK_RAW"; 2963 case RIL_REQUEST_OEM_HOOK_STRINGS: return "OEM_HOOK_STRINGS"; 2964 case RIL_REQUEST_SET_BAND_MODE: return "SET_BAND_MODE"; 2965 case RIL_REQUEST_QUERY_AVAILABLE_BAND_MODE: return "QUERY_AVAILABLE_BAND_MODE"; 2966 case RIL_REQUEST_STK_GET_PROFILE: return "STK_GET_PROFILE"; 2967 case RIL_REQUEST_STK_SET_PROFILE: return "STK_SET_PROFILE"; 2968 case RIL_REQUEST_STK_SEND_ENVELOPE_COMMAND: return "STK_SEND_ENVELOPE_COMMAND"; 2969 case RIL_REQUEST_STK_SEND_TERMINAL_RESPONSE: return "STK_SEND_TERMINAL_RESPONSE"; 2970 case RIL_REQUEST_STK_HANDLE_CALL_SETUP_REQUESTED_FROM_SIM: return "STK_HANDLE_CALL_SETUP_REQUESTED_FROM_SIM"; 2971 case RIL_REQUEST_SCREEN_STATE: return "SCREEN_STATE"; 2972 case RIL_REQUEST_EXPLICIT_CALL_TRANSFER: return "EXPLICIT_CALL_TRANSFER"; 2973 case RIL_REQUEST_SET_LOCATION_UPDATES: return "SET_LOCATION_UPDATES"; 2974 case RIL_REQUEST_CDMA_SET_SUBSCRIPTION:return"CDMA_SET_SUBSCRIPTION"; 2975 case RIL_REQUEST_CDMA_SET_ROAMING_PREFERENCE:return"CDMA_SET_ROAMING_PREFERENCE"; 2976 case RIL_REQUEST_CDMA_QUERY_ROAMING_PREFERENCE:return"CDMA_QUERY_ROAMING_PREFERENCE"; 2977 case RIL_REQUEST_SET_TTY_MODE:return"SET_TTY_MODE"; 2978 case RIL_REQUEST_QUERY_TTY_MODE:return"QUERY_TTY_MODE"; 2979 case RIL_REQUEST_CDMA_SET_PREFERRED_VOICE_PRIVACY_MODE:return"CDMA_SET_PREFERRED_VOICE_PRIVACY_MODE"; 2980 case RIL_REQUEST_CDMA_QUERY_PREFERRED_VOICE_PRIVACY_MODE:return"CDMA_QUERY_PREFERRED_VOICE_PRIVACY_MODE"; 2981 case RIL_REQUEST_CDMA_FLASH:return"CDMA_FLASH"; 2982 case RIL_REQUEST_CDMA_BURST_DTMF:return"CDMA_BURST_DTMF"; 2983 case RIL_REQUEST_CDMA_SEND_SMS:return"CDMA_SEND_SMS"; 2984 case RIL_REQUEST_CDMA_SMS_ACKNOWLEDGE:return"CDMA_SMS_ACKNOWLEDGE"; 2985 case RIL_REQUEST_GSM_GET_BROADCAST_SMS_CONFIG:return"GSM_GET_BROADCAST_SMS_CONFIG"; 2986 case RIL_REQUEST_GSM_SET_BROADCAST_SMS_CONFIG:return"GSM_SET_BROADCAST_SMS_CONFIG"; 2987 case RIL_REQUEST_CDMA_GET_BROADCAST_SMS_CONFIG:return "CDMA_GET_BROADCAST_SMS_CONFIG"; 2988 case RIL_REQUEST_CDMA_SET_BROADCAST_SMS_CONFIG:return "CDMA_SET_BROADCAST_SMS_CONFIG"; 2989 case RIL_REQUEST_CDMA_SMS_BROADCAST_ACTIVATION:return "CDMA_SMS_BROADCAST_ACTIVATION"; 2990 case RIL_REQUEST_CDMA_VALIDATE_AND_WRITE_AKEY: return"CDMA_VALIDATE_AND_WRITE_AKEY"; 2991 case RIL_REQUEST_CDMA_SUBSCRIPTION: return"CDMA_SUBSCRIPTION"; 2992 case RIL_REQUEST_CDMA_WRITE_SMS_TO_RUIM: return "CDMA_WRITE_SMS_TO_RUIM"; 2993 case RIL_REQUEST_CDMA_DELETE_SMS_ON_RUIM: return "CDMA_DELETE_SMS_ON_RUIM"; 2994 case RIL_REQUEST_DEVICE_IDENTITY: return "DEVICE_IDENTITY"; 2995 case RIL_REQUEST_EXIT_EMERGENCY_CALLBACK_MODE: return "EXIT_EMERGENCY_CALLBACK_MODE"; 2996 case RIL_REQUEST_GET_SMSC_ADDRESS: return "GET_SMSC_ADDRESS"; 2997 case RIL_REQUEST_SET_SMSC_ADDRESS: return "SET_SMSC_ADDRESS"; 2998 case RIL_REQUEST_REPORT_SMS_MEMORY_STATUS: return "REPORT_SMS_MEMORY_STATUS"; 2999 case RIL_UNSOL_RESPONSE_RADIO_STATE_CHANGED: return "UNSOL_RESPONSE_RADIO_STATE_CHANGED"; 3000 case RIL_UNSOL_RESPONSE_CALL_STATE_CHANGED: return "UNSOL_RESPONSE_CALL_STATE_CHANGED"; 3001 case RIL_UNSOL_RESPONSE_NETWORK_STATE_CHANGED: return "UNSOL_RESPONSE_NETWORK_STATE_CHANGED"; 3002 case RIL_UNSOL_RESPONSE_NEW_SMS: return "UNSOL_RESPONSE_NEW_SMS"; 3003 case RIL_UNSOL_RESPONSE_NEW_SMS_STATUS_REPORT: return "UNSOL_RESPONSE_NEW_SMS_STATUS_REPORT"; 3004 case RIL_UNSOL_RESPONSE_NEW_SMS_ON_SIM: return "UNSOL_RESPONSE_NEW_SMS_ON_SIM"; 3005 case RIL_UNSOL_ON_USSD: return "UNSOL_ON_USSD"; 3006 case RIL_UNSOL_ON_USSD_REQUEST: return "UNSOL_ON_USSD_REQUEST(obsolete)"; 3007 case RIL_UNSOL_NITZ_TIME_RECEIVED: return "UNSOL_NITZ_TIME_RECEIVED"; 3008 case RIL_UNSOL_SIGNAL_STRENGTH: return "UNSOL_SIGNAL_STRENGTH"; 3009 case RIL_UNSOL_STK_SESSION_END: return "UNSOL_STK_SESSION_END"; 3010 case RIL_UNSOL_STK_PROACTIVE_COMMAND: return "UNSOL_STK_PROACTIVE_COMMAND"; 3011 case RIL_UNSOL_STK_EVENT_NOTIFY: return "UNSOL_STK_EVENT_NOTIFY"; 3012 case RIL_UNSOL_STK_CALL_SETUP: return "UNSOL_STK_CALL_SETUP"; 3013 case RIL_UNSOL_SIM_SMS_STORAGE_FULL: return "UNSOL_SIM_SMS_STORAGE_FUL"; 3014 case RIL_UNSOL_SIM_REFRESH: return "UNSOL_SIM_REFRESH"; 3015 case RIL_UNSOL_DATA_CALL_LIST_CHANGED: return "UNSOL_DATA_CALL_LIST_CHANGED"; 3016 case RIL_UNSOL_CALL_RING: return "UNSOL_CALL_RING"; 3017 case RIL_UNSOL_RESPONSE_SIM_STATUS_CHANGED: return "UNSOL_RESPONSE_SIM_STATUS_CHANGED"; 3018 case RIL_UNSOL_RESPONSE_CDMA_NEW_SMS: return "UNSOL_NEW_CDMA_SMS"; 3019 case RIL_UNSOL_RESPONSE_NEW_BROADCAST_SMS: return "UNSOL_NEW_BROADCAST_SMS"; 3020 case RIL_UNSOL_CDMA_RUIM_SMS_STORAGE_FULL: return "UNSOL_CDMA_RUIM_SMS_STORAGE_FULL"; 3021 case RIL_UNSOL_RESTRICTED_STATE_CHANGED: return "UNSOL_RESTRICTED_STATE_CHANGED"; 3022 case RIL_UNSOL_ENTER_EMERGENCY_CALLBACK_MODE: return "UNSOL_ENTER_EMERGENCY_CALLBACK_MODE"; 3023 case RIL_UNSOL_CDMA_CALL_WAITING: return "UNSOL_CDMA_CALL_WAITING"; 3024 case RIL_UNSOL_CDMA_OTA_PROVISION_STATUS: return "UNSOL_CDMA_OTA_PROVISION_STATUS"; 3025 case RIL_UNSOL_CDMA_INFO_REC: return "UNSOL_CDMA_INFO_REC"; 3026 case RIL_UNSOL_OEM_HOOK_RAW: return "UNSOL_OEM_HOOK_RAW"; 3027 case RIL_UNSOL_RINGBACK_TONE: return "UNSOL_RINGBACK_TONE"; 3028 default: return "<unknown request>"; 3029 } 3030} 3031 3032} /* namespace android */ 3033