libril: ril.cpp

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