ril_service.cpp revision 758ee46f08d307e4b6750889cf49105a82525bec
1/*
2 * Copyright (c) 2016 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#define LOG_TAG "RILC"
18
19#include <android/hardware/radio/1.0/IRadio.h>
20#include <android/hardware/radio/deprecated/1.0/IOemHook.h>
21
22#include <hwbinder/IPCThreadState.h>
23#include <hwbinder/ProcessState.h>
24#include <ril_service.h>
25#include <hidl/HidlTransportSupport.h>
26#include <utils/SystemClock.h>
27#include <inttypes.h>
28
29#define INVALID_HEX_CHAR 16
30
31// Enable verbose logging
32#define VDBG 0
33
34using namespace android::hardware::radio::V1_0;
35using namespace android::hardware::radio::deprecated::V1_0;
36using ::android::hardware::configureRpcThreadpool;
37using ::android::hardware::joinRpcThreadpool;
38using ::android::hardware::Return;
39using ::android::hardware::hidl_string;
40using ::android::hardware::hidl_vec;
41using ::android::hardware::hidl_array;
42using ::android::hardware::Void;
43using android::CommandInfo;
44using android::RequestInfo;
45using android::requestToString;
46using android::sp;
47
48#define BOOL_TO_INT(x) (x ? 1 : 0)
49#define ATOI_NULL_HANDLED(x) (x ? atoi(x) : -1)
50#define ATOI_NULL_HANDLED_DEF(x, defaultVal) (x ? atoi(x) : defaultVal)
51
52#if defined(ANDROID_MULTI_SIM)
53#define CALL_ONREQUEST(a, b, c, d, e) \
54        s_vendorFunctions->onRequest((a), (b), (c), (d), ((RIL_SOCKET_ID)(e)))
55#define CALL_ONSTATEREQUEST(a) s_vendorFunctions->onStateRequest((RIL_SOCKET_ID)(a))
56#else
57#define CALL_ONREQUEST(a, b, c, d, e) s_vendorFunctions->onRequest((a), (b), (c), (d))
58#define CALL_ONSTATEREQUEST(a) s_vendorFunctions->onStateRequest()
59#endif
60
61RIL_RadioFunctions *s_vendorFunctions = NULL;
62static CommandInfo *s_commands;
63
64struct RadioImpl;
65struct OemHookImpl;
66
67#if (SIM_COUNT >= 2)
68sp<RadioImpl> radioService[SIM_COUNT];
69sp<OemHookImpl> oemHookService[SIM_COUNT];
70// counter used for synchronization. It is incremented every time response callbacks are updated.
71volatile int32_t mCounterRadio[SIM_COUNT];
72volatile int32_t mCounterOemHook[SIM_COUNT];
73#else
74sp<RadioImpl> radioService[1];
75sp<OemHookImpl> oemHookService[1];
76// counter used for synchronization. It is incremented every time response callbacks are updated.
77volatile int32_t mCounterRadio[1];
78volatile int32_t mCounterOemHook[1];
79#endif
80
81static pthread_rwlock_t radioServiceRwlock = PTHREAD_RWLOCK_INITIALIZER;
82
83#if (SIM_COUNT >= 2)
84static pthread_rwlock_t radioServiceRwlock2 = PTHREAD_RWLOCK_INITIALIZER;
85#if (SIM_COUNT >= 3)
86static pthread_rwlock_t radioServiceRwlock3 = PTHREAD_RWLOCK_INITIALIZER;
87#if (SIM_COUNT >= 4)
88static pthread_rwlock_t radioServiceRwlock4 = PTHREAD_RWLOCK_INITIALIZER;
89#endif
90#endif
91#endif
92
93void convertRilHardwareConfigListToHal(void *response, size_t responseLen,
94        hidl_vec<HardwareConfig>& records);
95
96void convertRilRadioCapabilityToHal(void *response, size_t responseLen, RadioCapability& rc);
97
98void convertRilLceDataInfoToHal(void *response, size_t responseLen, LceDataInfo& lce);
99
100void convertRilSignalStrengthToHal(void *response, size_t responseLen,
101        SignalStrength& signalStrength);
102
103void convertRilDataCallToHal(RIL_Data_Call_Response_v11 *dcResponse,
104        SetupDataCallResult& dcResult);
105
106void convertRilDataCallListToHal(void *response, size_t responseLen,
107        hidl_vec<SetupDataCallResult>& dcResultList);
108
109void convertRilCellInfoListToHal(void *response, size_t responseLen, hidl_vec<CellInfo>& records);
110
111struct RadioImpl : public IRadio {
112    int32_t mSlotId;
113    sp<IRadioResponse> mRadioResponse;
114    sp<IRadioIndication> mRadioIndication;
115
116    Return<void> setResponseFunctions(
117            const ::android::sp<IRadioResponse>& radioResponse,
118            const ::android::sp<IRadioIndication>& radioIndication);
119
120    Return<void> getIccCardStatus(int32_t serial);
121
122    Return<void> supplyIccPinForApp(int32_t serial, const hidl_string& pin,
123            const hidl_string& aid);
124
125    Return<void> supplyIccPukForApp(int32_t serial, const hidl_string& puk,
126            const hidl_string& pin, const hidl_string& aid);
127
128    Return<void> supplyIccPin2ForApp(int32_t serial,
129            const hidl_string& pin2,
130            const hidl_string& aid);
131
132    Return<void> supplyIccPuk2ForApp(int32_t serial, const hidl_string& puk2,
133            const hidl_string& pin2, const hidl_string& aid);
134
135    Return<void> changeIccPinForApp(int32_t serial, const hidl_string& oldPin,
136            const hidl_string& newPin, const hidl_string& aid);
137
138    Return<void> changeIccPin2ForApp(int32_t serial, const hidl_string& oldPin2,
139            const hidl_string& newPin2, const hidl_string& aid);
140
141    Return<void> supplyNetworkDepersonalization(int32_t serial, const hidl_string& netPin);
142
143    Return<void> getCurrentCalls(int32_t serial);
144
145    Return<void> dial(int32_t serial, const Dial& dialInfo);
146
147    Return<void> getImsiForApp(int32_t serial,
148            const ::android::hardware::hidl_string& aid);
149
150    Return<void> hangup(int32_t serial, int32_t gsmIndex);
151
152    Return<void> hangupWaitingOrBackground(int32_t serial);
153
154    Return<void> hangupForegroundResumeBackground(int32_t serial);
155
156    Return<void> switchWaitingOrHoldingAndActive(int32_t serial);
157
158    Return<void> conference(int32_t serial);
159
160    Return<void> rejectCall(int32_t serial);
161
162    Return<void> getLastCallFailCause(int32_t serial);
163
164    Return<void> getSignalStrength(int32_t serial);
165
166    Return<void> getVoiceRegistrationState(int32_t serial);
167
168    Return<void> getDataRegistrationState(int32_t serial);
169
170    Return<void> getOperator(int32_t serial);
171
172    Return<void> setRadioPower(int32_t serial, bool on);
173
174    Return<void> sendDtmf(int32_t serial,
175            const ::android::hardware::hidl_string& s);
176
177    Return<void> sendSms(int32_t serial, const GsmSmsMessage& message);
178
179    Return<void> sendSMSExpectMore(int32_t serial, const GsmSmsMessage& message);
180
181    Return<void> setupDataCall(int32_t serial,
182            RadioTechnology radioTechnology,
183            const DataProfileInfo& profileInfo,
184            bool modemCognitive,
185            bool roamingAllowed,
186            bool isRoaming);
187
188    Return<void> iccIOForApp(int32_t serial,
189            const IccIo& iccIo);
190
191    Return<void> sendUssd(int32_t serial,
192            const ::android::hardware::hidl_string& ussd);
193
194    Return<void> cancelPendingUssd(int32_t serial);
195
196    Return<void> getClir(int32_t serial);
197
198    Return<void> setClir(int32_t serial, int32_t status);
199
200    Return<void> getCallForwardStatus(int32_t serial,
201            const CallForwardInfo& callInfo);
202
203    Return<void> setCallForward(int32_t serial,
204            const CallForwardInfo& callInfo);
205
206    Return<void> getCallWaiting(int32_t serial, int32_t serviceClass);
207
208    Return<void> setCallWaiting(int32_t serial, bool enable, int32_t serviceClass);
209
210    Return<void> acknowledgeLastIncomingGsmSms(int32_t serial,
211            bool success, SmsAcknowledgeFailCause cause);
212
213    Return<void> acceptCall(int32_t serial);
214
215    Return<void> deactivateDataCall(int32_t serial,
216            int32_t cid, bool reasonRadioShutDown);
217
218    Return<void> getFacilityLockForApp(int32_t serial,
219            const ::android::hardware::hidl_string& facility,
220            const ::android::hardware::hidl_string& password,
221            int32_t serviceClass,
222            const ::android::hardware::hidl_string& appId);
223
224    Return<void> setFacilityLockForApp(int32_t serial,
225            const ::android::hardware::hidl_string& facility,
226            bool lockState,
227            const ::android::hardware::hidl_string& password,
228            int32_t serviceClass,
229            const ::android::hardware::hidl_string& appId);
230
231    Return<void> setBarringPassword(int32_t serial,
232            const ::android::hardware::hidl_string& facility,
233            const ::android::hardware::hidl_string& oldPassword,
234            const ::android::hardware::hidl_string& newPassword);
235
236    Return<void> getNetworkSelectionMode(int32_t serial);
237
238    Return<void> setNetworkSelectionModeAutomatic(int32_t serial);
239
240    Return<void> setNetworkSelectionModeManual(int32_t serial,
241            const ::android::hardware::hidl_string& operatorNumeric);
242
243    Return<void> getAvailableNetworks(int32_t serial);
244
245    Return<void> startDtmf(int32_t serial,
246            const ::android::hardware::hidl_string& s);
247
248    Return<void> stopDtmf(int32_t serial);
249
250    Return<void> getBasebandVersion(int32_t serial);
251
252    Return<void> separateConnection(int32_t serial, int32_t gsmIndex);
253
254    Return<void> setMute(int32_t serial, bool enable);
255
256    Return<void> getMute(int32_t serial);
257
258    Return<void> getClip(int32_t serial);
259
260    Return<void> getDataCallList(int32_t serial);
261
262    Return<void> setSuppServiceNotifications(int32_t serial, bool enable);
263
264    Return<void> writeSmsToSim(int32_t serial,
265            const SmsWriteArgs& smsWriteArgs);
266
267    Return<void> deleteSmsOnSim(int32_t serial, int32_t index);
268
269    Return<void> setBandMode(int32_t serial, RadioBandMode mode);
270
271    Return<void> getAvailableBandModes(int32_t serial);
272
273    Return<void> sendEnvelope(int32_t serial,
274            const ::android::hardware::hidl_string& command);
275
276    Return<void> sendTerminalResponseToSim(int32_t serial,
277            const ::android::hardware::hidl_string& commandResponse);
278
279    Return<void> handleStkCallSetupRequestFromSim(int32_t serial, bool accept);
280
281    Return<void> explicitCallTransfer(int32_t serial);
282
283    Return<void> setPreferredNetworkType(int32_t serial, PreferredNetworkType nwType);
284
285    Return<void> getPreferredNetworkType(int32_t serial);
286
287    Return<void> getNeighboringCids(int32_t serial);
288
289    Return<void> setLocationUpdates(int32_t serial, bool enable);
290
291    Return<void> setCdmaSubscriptionSource(int32_t serial,
292            CdmaSubscriptionSource cdmaSub);
293
294    Return<void> setCdmaRoamingPreference(int32_t serial, CdmaRoamingType type);
295
296    Return<void> getCdmaRoamingPreference(int32_t serial);
297
298    Return<void> setTTYMode(int32_t serial, TtyMode mode);
299
300    Return<void> getTTYMode(int32_t serial);
301
302    Return<void> setPreferredVoicePrivacy(int32_t serial, bool enable);
303
304    Return<void> getPreferredVoicePrivacy(int32_t serial);
305
306    Return<void> sendCDMAFeatureCode(int32_t serial,
307            const ::android::hardware::hidl_string& featureCode);
308
309    Return<void> sendBurstDtmf(int32_t serial,
310            const ::android::hardware::hidl_string& dtmf,
311            int32_t on,
312            int32_t off);
313
314    Return<void> sendCdmaSms(int32_t serial, const CdmaSmsMessage& sms);
315
316    Return<void> acknowledgeLastIncomingCdmaSms(int32_t serial,
317            const CdmaSmsAck& smsAck);
318
319    Return<void> getGsmBroadcastConfig(int32_t serial);
320
321    Return<void> setGsmBroadcastConfig(int32_t serial,
322            const hidl_vec<GsmBroadcastSmsConfigInfo>& configInfo);
323
324    Return<void> setGsmBroadcastActivation(int32_t serial, bool activate);
325
326    Return<void> getCdmaBroadcastConfig(int32_t serial);
327
328    Return<void> setCdmaBroadcastConfig(int32_t serial,
329            const hidl_vec<CdmaBroadcastSmsConfigInfo>& configInfo);
330
331    Return<void> setCdmaBroadcastActivation(int32_t serial, bool activate);
332
333    Return<void> getCDMASubscription(int32_t serial);
334
335    Return<void> writeSmsToRuim(int32_t serial, const CdmaSmsWriteArgs& cdmaSms);
336
337    Return<void> deleteSmsOnRuim(int32_t serial, int32_t index);
338
339    Return<void> getDeviceIdentity(int32_t serial);
340
341    Return<void> exitEmergencyCallbackMode(int32_t serial);
342
343    Return<void> getSmscAddress(int32_t serial);
344
345    Return<void> setSmscAddress(int32_t serial,
346            const ::android::hardware::hidl_string& smsc);
347
348    Return<void> reportSmsMemoryStatus(int32_t serial, bool available);
349
350    Return<void> reportStkServiceIsRunning(int32_t serial);
351
352    Return<void> getCdmaSubscriptionSource(int32_t serial);
353
354    Return<void> requestIsimAuthentication(int32_t serial,
355            const ::android::hardware::hidl_string& challenge);
356
357    Return<void> acknowledgeIncomingGsmSmsWithPdu(int32_t serial,
358            bool success,
359            const ::android::hardware::hidl_string& ackPdu);
360
361    Return<void> sendEnvelopeWithStatus(int32_t serial,
362            const ::android::hardware::hidl_string& contents);
363
364    Return<void> getVoiceRadioTechnology(int32_t serial);
365
366    Return<void> getCellInfoList(int32_t serial);
367
368    Return<void> setCellInfoListRate(int32_t serial, int32_t rate);
369
370    Return<void> setInitialAttachApn(int32_t serial, const DataProfileInfo& dataProfileInfo,
371            bool modemCognitive, bool isRoaming);
372
373    Return<void> getImsRegistrationState(int32_t serial);
374
375    Return<void> sendImsSms(int32_t serial, const ImsSmsMessage& message);
376
377    Return<void> iccTransmitApduBasicChannel(int32_t serial, const SimApdu& message);
378
379    Return<void> iccOpenLogicalChannel(int32_t serial,
380            const ::android::hardware::hidl_string& aid, int32_t p2);
381
382    Return<void> iccCloseLogicalChannel(int32_t serial, int32_t channelId);
383
384    Return<void> iccTransmitApduLogicalChannel(int32_t serial, const SimApdu& message);
385
386    Return<void> nvReadItem(int32_t serial, NvItem itemId);
387
388    Return<void> nvWriteItem(int32_t serial, const NvWriteItem& item);
389
390    Return<void> nvWriteCdmaPrl(int32_t serial,
391            const ::android::hardware::hidl_vec<uint8_t>& prl);
392
393    Return<void> nvResetConfig(int32_t serial, ResetNvType resetType);
394
395    Return<void> setUiccSubscription(int32_t serial, const SelectUiccSub& uiccSub);
396
397    Return<void> setDataAllowed(int32_t serial, bool allow);
398
399    Return<void> getHardwareConfig(int32_t serial);
400
401    Return<void> requestIccSimAuthentication(int32_t serial,
402            int32_t authContext,
403            const ::android::hardware::hidl_string& authData,
404            const ::android::hardware::hidl_string& aid);
405
406    Return<void> setDataProfile(int32_t serial,
407            const ::android::hardware::hidl_vec<DataProfileInfo>& profiles, bool isRoaming);
408
409    Return<void> requestShutdown(int32_t serial);
410
411    Return<void> getRadioCapability(int32_t serial);
412
413    Return<void> setRadioCapability(int32_t serial, const RadioCapability& rc);
414
415    Return<void> startLceService(int32_t serial, int32_t reportInterval, bool pullMode);
416
417    Return<void> stopLceService(int32_t serial);
418
419    Return<void> pullLceData(int32_t serial);
420
421    Return<void> getModemActivityInfo(int32_t serial);
422
423    Return<void> setAllowedCarriers(int32_t serial,
424            bool allAllowed,
425            const CarrierRestrictions& carriers);
426
427    Return<void> getAllowedCarriers(int32_t serial);
428
429    Return<void> sendDeviceState(int32_t serial, DeviceStateType deviceStateType, bool state);
430
431    Return<void> setIndicationFilter(int32_t serial, int32_t indicationFilter);
432
433    Return<void> setSimCardPower(int32_t serial, bool powerUp);
434
435    Return<void> responseAcknowledgement();
436
437    void checkReturnStatus(Return<void>& ret);
438};
439
440struct OemHookImpl : public IOemHook {
441    int32_t mSlotId;
442    sp<IOemHookResponse> mOemHookResponse;
443    sp<IOemHookIndication> mOemHookIndication;
444
445    Return<void> setResponseFunctions(
446            const ::android::sp<IOemHookResponse>& oemHookResponse,
447            const ::android::sp<IOemHookIndication>& oemHookIndication);
448
449    Return<void> sendRequestRaw(int32_t serial,
450            const ::android::hardware::hidl_vec<uint8_t>& data);
451
452    Return<void> sendRequestStrings(int32_t serial,
453            const ::android::hardware::hidl_vec<::android::hardware::hidl_string>& data);
454};
455
456void memsetAndFreeStrings(int numPointers, ...) {
457    va_list ap;
458    va_start(ap, numPointers);
459    for (int i = 0; i < numPointers; i++) {
460        char *ptr = va_arg(ap, char *);
461        if (ptr) {
462#ifdef MEMSET_FREED
463            // TODO: Should pass in the maximum length of the string
464            memsetString(ptr);
465#endif
466            free(ptr);
467        }
468    }
469    va_end(ap);
470}
471
472void sendErrorResponse(RequestInfo *pRI, RIL_Errno err) {
473    pRI->pCI->responseFunction((int) pRI->socket_id,
474            (int) RadioResponseType::SOLICITED, pRI->token, err, NULL, 0);
475}
476
477/**
478 * Copies over src to dest. If memory allocation fails, responseFunction() is called for the
479 * request with error RIL_E_NO_MEMORY.
480 * Returns true on success, and false on failure.
481 */
482bool copyHidlStringToRil(char **dest, const hidl_string &src, RequestInfo *pRI) {
483    size_t len = src.size();
484    if (len == 0) {
485        *dest = NULL;
486        return true;
487    }
488    *dest = (char *) calloc(len + 1, sizeof(char));
489    if (*dest == NULL) {
490        RLOGE("Memory allocation failed for request %s", requestToString(pRI->pCI->requestNumber));
491        sendErrorResponse(pRI, RIL_E_NO_MEMORY);
492        return false;
493    }
494    strncpy(*dest, src.c_str(), len + 1);
495    return true;
496}
497
498hidl_string convertCharPtrToHidlString(const char *ptr) {
499    hidl_string ret;
500    if (ptr != NULL) {
501        // TODO: replace this with strnlen
502        ret.setToExternal(ptr, strlen(ptr));
503    }
504    return ret;
505}
506
507bool dispatchVoid(int serial, int slotId, int request) {
508    RequestInfo *pRI = android::addRequestToList(serial, slotId, request);
509    if (pRI == NULL) {
510        return false;
511    }
512    CALL_ONREQUEST(request, NULL, 0, pRI, slotId);
513    return true;
514}
515
516bool dispatchString(int serial, int slotId, int request, const char * str) {
517    RequestInfo *pRI = android::addRequestToList(serial, slotId, request);
518    if (pRI == NULL) {
519        return false;
520    }
521
522    char *pString;
523    if (!copyHidlStringToRil(&pString, str, pRI)) {
524        return false;
525    }
526
527    CALL_ONREQUEST(request, pString, sizeof(char *), pRI, slotId);
528
529    memsetAndFreeStrings(1, pString);
530    return true;
531}
532
533bool dispatchStrings(int serial, int slotId, int request, int countStrings, ...) {
534    RequestInfo *pRI = android::addRequestToList(serial, slotId, request);
535    if (pRI == NULL) {
536        return false;
537    }
538
539    char **pStrings;
540    pStrings = (char **)calloc(countStrings, sizeof(char *));
541    if (pStrings == NULL) {
542        RLOGE("Memory allocation failed for request %s", requestToString(request));
543        sendErrorResponse(pRI, RIL_E_NO_MEMORY);
544        return false;
545    }
546    va_list ap;
547    va_start(ap, countStrings);
548    for (int i = 0; i < countStrings; i++) {
549        const char* str = va_arg(ap, const char *);
550        if (!copyHidlStringToRil(&pStrings[i], hidl_string(str), pRI)) {
551            va_end(ap);
552            for (int j = 0; j < i; j++) {
553                memsetAndFreeStrings(1, pStrings[j]);
554            }
555            free(pStrings);
556            return false;
557        }
558    }
559    va_end(ap);
560
561    CALL_ONREQUEST(request, pStrings, countStrings * sizeof(char *), pRI, slotId);
562
563    if (pStrings != NULL) {
564        for (int i = 0 ; i < countStrings ; i++) {
565            memsetAndFreeStrings(1, pStrings[i]);
566        }
567
568#ifdef MEMSET_FREED
569        memset(pStrings, 0, countStrings * sizeof(char *));
570#endif
571        free(pStrings);
572    }
573    return true;
574}
575
576bool dispatchStrings(int serial, int slotId, int request, const hidl_vec<hidl_string>& data) {
577    RequestInfo *pRI = android::addRequestToList(serial, slotId, request);
578    if (pRI == NULL) {
579        return false;
580    }
581
582    int countStrings = data.size();
583    char **pStrings;
584    pStrings = (char **)calloc(countStrings, sizeof(char *));
585    if (pStrings == NULL) {
586        RLOGE("Memory allocation failed for request %s", requestToString(request));
587        sendErrorResponse(pRI, RIL_E_NO_MEMORY);
588        return false;
589    }
590
591    for (int i = 0; i < countStrings; i++) {
592        if (!copyHidlStringToRil(&pStrings[i], data[i], pRI)) {
593            for (int j = 0; j < i; j++) {
594                memsetAndFreeStrings(1, pStrings[j]);
595            }
596            free(pStrings);
597            return false;
598        }
599    }
600
601    CALL_ONREQUEST(request, pStrings, countStrings * sizeof(char *), pRI, slotId);
602
603    if (pStrings != NULL) {
604        for (int i = 0 ; i < countStrings ; i++) {
605            memsetAndFreeStrings(1, pStrings[i]);
606        }
607
608#ifdef MEMSET_FREED
609        memset(pStrings, 0, countStrings * sizeof(char *));
610#endif
611        free(pStrings);
612    }
613    return true;
614}
615
616bool dispatchInts(int serial, int slotId, int request, int countInts, ...) {
617    RequestInfo *pRI = android::addRequestToList(serial, slotId, request);
618    if (pRI == NULL) {
619        return false;
620    }
621
622    int *pInts = (int *)calloc(countInts, sizeof(int));
623
624    if (pInts == NULL) {
625        RLOGE("Memory allocation failed for request %s", requestToString(request));
626        sendErrorResponse(pRI, RIL_E_NO_MEMORY);
627        return false;
628    }
629    va_list ap;
630    va_start(ap, countInts);
631    for (int i = 0; i < countInts; i++) {
632        pInts[i] = va_arg(ap, int);
633    }
634    va_end(ap);
635
636    CALL_ONREQUEST(request, pInts, countInts * sizeof(int), pRI, slotId);
637
638    if (pInts != NULL) {
639#ifdef MEMSET_FREED
640        memset(pInts, 0, countInts * sizeof(int));
641#endif
642        free(pInts);
643    }
644    return true;
645}
646
647bool dispatchCallForwardStatus(int serial, int slotId, int request,
648                              const CallForwardInfo& callInfo) {
649    RequestInfo *pRI = android::addRequestToList(serial, slotId, request);
650    if (pRI == NULL) {
651        return false;
652    }
653
654    RIL_CallForwardInfo cf;
655    cf.status = (int) callInfo.status;
656    cf.reason = callInfo.reason;
657    cf.serviceClass = callInfo.serviceClass;
658    cf.toa = callInfo.toa;
659    cf.timeSeconds = callInfo.timeSeconds;
660
661    if (!copyHidlStringToRil(&cf.number, callInfo.number, pRI)) {
662        return false;
663    }
664
665    CALL_ONREQUEST(request, &cf, sizeof(cf), pRI, slotId);
666
667    memsetAndFreeStrings(1, cf.number);
668
669    return true;
670}
671
672bool dispatchRaw(int serial, int slotId, int request, const hidl_vec<uint8_t>& rawBytes) {
673    RequestInfo *pRI = android::addRequestToList(serial, slotId, request);
674    if (pRI == NULL) {
675        return false;
676    }
677
678    const uint8_t *uData = rawBytes.data();
679
680    CALL_ONREQUEST(request, (void *) uData, rawBytes.size(), pRI, slotId);
681
682    return true;
683}
684
685bool dispatchIccApdu(int serial, int slotId, int request, const SimApdu& message) {
686    RequestInfo *pRI = android::addRequestToList(serial, slotId, request);
687    if (pRI == NULL) {
688        return false;
689    }
690
691    RIL_SIM_APDU apdu = {};
692
693    apdu.sessionid = message.sessionId;
694    apdu.cla = message.cla;
695    apdu.instruction = message.instruction;
696    apdu.p1 = message.p1;
697    apdu.p2 = message.p2;
698    apdu.p3 = message.p3;
699
700    if (!copyHidlStringToRil(&apdu.data, message.data, pRI)) {
701        return false;
702    }
703
704    CALL_ONREQUEST(request, &apdu, sizeof(apdu), pRI, slotId);
705
706    memsetAndFreeStrings(1, apdu.data);
707
708    return true;
709}
710
711void checkReturnStatus(int32_t slotId, Return<void>& ret, bool isRadioService) {
712    if (ret.isOk() == false) {
713        RLOGE("checkReturnStatus: unable to call response/indication callback");
714        // Remote process hosting the callbacks must be dead. Reset the callback objects;
715        // there's no other recovery to be done here. When the client process is back up, it will
716        // call setResponseFunctions()
717
718        // Caller should already hold rdlock, release that first
719        // note the current counter to avoid overwriting updates made by another thread before
720        // write lock is acquired.
721        int counter = isRadioService ? mCounterRadio[slotId] : mCounterOemHook[slotId];
722        pthread_rwlock_t *radioServiceRwlockPtr = radio::getRadioServiceRwlock(slotId);
723        int ret = pthread_rwlock_unlock(radioServiceRwlockPtr);
724        assert(ret == 0);
725
726        // acquire wrlock
727        ret = pthread_rwlock_wrlock(radioServiceRwlockPtr);
728        assert(ret == 0);
729
730        // make sure the counter value has not changed
731        if (counter == (isRadioService ? mCounterRadio[slotId] : mCounterOemHook[slotId])) {
732            if (isRadioService) {
733                radioService[slotId]->mRadioResponse = NULL;
734                radioService[slotId]->mRadioIndication = NULL;
735            } else {
736                oemHookService[slotId]->mOemHookResponse = NULL;
737                oemHookService[slotId]->mOemHookIndication = NULL;
738            }
739            isRadioService ? mCounterRadio[slotId]++ : mCounterOemHook[slotId]++;
740        } else {
741            RLOGE("checkReturnStatus: not resetting responseFunctions as they likely "
742                    "got updated on another thread");
743        }
744
745        // release wrlock
746        ret = pthread_rwlock_unlock(radioServiceRwlockPtr);
747        assert(ret == 0);
748
749        // Reacquire rdlock
750        ret = pthread_rwlock_rdlock(radioServiceRwlockPtr);
751        assert(ret == 0);
752    }
753}
754
755void RadioImpl::checkReturnStatus(Return<void>& ret) {
756    ::checkReturnStatus(mSlotId, ret, true);
757}
758
759Return<void> RadioImpl::setResponseFunctions(
760        const ::android::sp<IRadioResponse>& radioResponseParam,
761        const ::android::sp<IRadioIndication>& radioIndicationParam) {
762    RLOGD("setResponseFunctions");
763
764    pthread_rwlock_t *radioServiceRwlockPtr = radio::getRadioServiceRwlock(mSlotId);
765    int ret = pthread_rwlock_wrlock(radioServiceRwlockPtr);
766    assert(ret == 0);
767
768    mRadioResponse = radioResponseParam;
769    mRadioIndication = radioIndicationParam;
770    mCounterRadio[mSlotId]++;
771
772    ret = pthread_rwlock_unlock(radioServiceRwlockPtr);
773    assert(ret == 0);
774
775    // client is connected. Send initial indications.
776    android::onNewCommandConnect((RIL_SOCKET_ID) mSlotId);
777
778    return Void();
779}
780
781Return<void> RadioImpl::getIccCardStatus(int32_t serial) {
782#if VDBG
783    RLOGD("getIccCardStatus: serial %d", serial);
784#endif
785    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_SIM_STATUS);
786    return Void();
787}
788
789Return<void> RadioImpl::supplyIccPinForApp(int32_t serial, const hidl_string& pin,
790        const hidl_string& aid) {
791#if VDBG
792    RLOGD("supplyIccPinForApp: serial %d", serial);
793#endif
794    dispatchStrings(serial, mSlotId, RIL_REQUEST_ENTER_SIM_PIN,
795            2, pin.c_str(), aid.c_str());
796    return Void();
797}
798
799Return<void> RadioImpl::supplyIccPukForApp(int32_t serial, const hidl_string& puk,
800                                           const hidl_string& pin, const hidl_string& aid) {
801#if VDBG
802    RLOGD("supplyIccPukForApp: serial %d", serial);
803#endif
804    dispatchStrings(serial, mSlotId, RIL_REQUEST_ENTER_SIM_PUK,
805            3, puk.c_str(), pin.c_str(), aid.c_str());
806    return Void();
807}
808
809Return<void> RadioImpl::supplyIccPin2ForApp(int32_t serial, const hidl_string& pin2,
810                                            const hidl_string& aid) {
811#if VDBG
812    RLOGD("supplyIccPin2ForApp: serial %d", serial);
813#endif
814    dispatchStrings(serial, mSlotId, RIL_REQUEST_ENTER_SIM_PIN2,
815            2, pin2.c_str(), aid.c_str());
816    return Void();
817}
818
819Return<void> RadioImpl::supplyIccPuk2ForApp(int32_t serial, const hidl_string& puk2,
820                                            const hidl_string& pin2, const hidl_string& aid) {
821#if VDBG
822    RLOGD("supplyIccPuk2ForApp: serial %d", serial);
823#endif
824    dispatchStrings(serial, mSlotId, RIL_REQUEST_ENTER_SIM_PUK2,
825            3, puk2.c_str(), pin2.c_str(), aid.c_str());
826    return Void();
827}
828
829Return<void> RadioImpl::changeIccPinForApp(int32_t serial, const hidl_string& oldPin,
830                                           const hidl_string& newPin, const hidl_string& aid) {
831#if VDBG
832    RLOGD("changeIccPinForApp: serial %d", serial);
833#endif
834    dispatchStrings(serial, mSlotId, RIL_REQUEST_CHANGE_SIM_PIN,
835            3, oldPin.c_str(), newPin.c_str(), aid.c_str());
836    return Void();
837}
838
839Return<void> RadioImpl::changeIccPin2ForApp(int32_t serial, const hidl_string& oldPin2,
840                                            const hidl_string& newPin2, const hidl_string& aid) {
841#if VDBG
842    RLOGD("changeIccPin2ForApp: serial %d", serial);
843#endif
844    dispatchStrings(serial, mSlotId, RIL_REQUEST_CHANGE_SIM_PIN2,
845            3, oldPin2.c_str(), newPin2.c_str(), aid.c_str());
846    return Void();
847}
848
849Return<void> RadioImpl::supplyNetworkDepersonalization(int32_t serial,
850                                                       const hidl_string& netPin) {
851#if VDBG
852    RLOGD("supplyNetworkDepersonalization: serial %d", serial);
853#endif
854    dispatchStrings(serial, mSlotId, RIL_REQUEST_ENTER_NETWORK_DEPERSONALIZATION,
855            1, netPin.c_str());
856    return Void();
857}
858
859Return<void> RadioImpl::getCurrentCalls(int32_t serial) {
860#if VDBG
861    RLOGD("getCurrentCalls: serial %d", serial);
862#endif
863    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_CURRENT_CALLS);
864    return Void();
865}
866
867Return<void> RadioImpl::dial(int32_t serial, const Dial& dialInfo) {
868#if VDBG
869    RLOGD("dial: serial %d", serial);
870#endif
871    RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_DIAL);
872    if (pRI == NULL) {
873        return Void();
874    }
875    RIL_Dial dial = {};
876    RIL_UUS_Info uusInfo = {};
877    int32_t sizeOfDial = sizeof(dial);
878
879    if (!copyHidlStringToRil(&dial.address, dialInfo.address, pRI)) {
880        return Void();
881    }
882    dial.clir = (int) dialInfo.clir;
883
884    if (dialInfo.uusInfo.size() != 0) {
885        uusInfo.uusType = (RIL_UUS_Type) dialInfo.uusInfo[0].uusType;
886        uusInfo.uusDcs = (RIL_UUS_DCS) dialInfo.uusInfo[0].uusDcs;
887
888        if (dialInfo.uusInfo[0].uusData.size() == 0) {
889            uusInfo.uusData = NULL;
890            uusInfo.uusLength = 0;
891        } else {
892            if (!copyHidlStringToRil(&uusInfo.uusData, dialInfo.uusInfo[0].uusData, pRI)) {
893                memsetAndFreeStrings(1, dial.address);
894                return Void();
895            }
896            uusInfo.uusLength = dialInfo.uusInfo[0].uusData.size();
897        }
898
899        dial.uusInfo = &uusInfo;
900    }
901
902    CALL_ONREQUEST(RIL_REQUEST_DIAL, &dial, sizeOfDial, pRI, mSlotId);
903
904    memsetAndFreeStrings(2, dial.address, uusInfo.uusData);
905
906    return Void();
907}
908
909Return<void> RadioImpl::getImsiForApp(int32_t serial, const hidl_string& aid) {
910#if VDBG
911    RLOGD("getImsiForApp: serial %d", serial);
912#endif
913    dispatchStrings(serial, mSlotId, RIL_REQUEST_GET_IMSI,
914            1, aid.c_str());
915    return Void();
916}
917
918Return<void> RadioImpl::hangup(int32_t serial, int32_t gsmIndex) {
919#if VDBG
920    RLOGD("hangup: serial %d", serial);
921#endif
922    dispatchInts(serial, mSlotId, RIL_REQUEST_HANGUP, 1, gsmIndex);
923    return Void();
924}
925
926Return<void> RadioImpl::hangupWaitingOrBackground(int32_t serial) {
927#if VDBG
928    RLOGD("hangupWaitingOrBackground: serial %d", serial);
929#endif
930    dispatchVoid(serial, mSlotId, RIL_REQUEST_HANGUP_WAITING_OR_BACKGROUND);
931    return Void();
932}
933
934Return<void> RadioImpl::hangupForegroundResumeBackground(int32_t serial) {
935#if VDBG
936    RLOGD("hangupForegroundResumeBackground: serial %d", serial);
937#endif
938    dispatchVoid(serial, mSlotId, RIL_REQUEST_HANGUP_FOREGROUND_RESUME_BACKGROUND);
939    return Void();
940}
941
942Return<void> RadioImpl::switchWaitingOrHoldingAndActive(int32_t serial) {
943#if VDBG
944    RLOGD("switchWaitingOrHoldingAndActive: serial %d", serial);
945#endif
946    dispatchVoid(serial, mSlotId, RIL_REQUEST_SWITCH_WAITING_OR_HOLDING_AND_ACTIVE);
947    return Void();
948}
949
950Return<void> RadioImpl::conference(int32_t serial) {
951#if VDBG
952    RLOGD("conference: serial %d", serial);
953#endif
954    dispatchVoid(serial, mSlotId, RIL_REQUEST_CONFERENCE);
955    return Void();
956}
957
958Return<void> RadioImpl::rejectCall(int32_t serial) {
959#if VDBG
960    RLOGD("rejectCall: serial %d", serial);
961#endif
962    dispatchVoid(serial, mSlotId, RIL_REQUEST_UDUB);
963    return Void();
964}
965
966Return<void> RadioImpl::getLastCallFailCause(int32_t serial) {
967#if VDBG
968    RLOGD("getLastCallFailCause: serial %d", serial);
969#endif
970    dispatchVoid(serial, mSlotId, RIL_REQUEST_LAST_CALL_FAIL_CAUSE);
971    return Void();
972}
973
974Return<void> RadioImpl::getSignalStrength(int32_t serial) {
975#if VDBG
976    RLOGD("getSignalStrength: serial %d", serial);
977#endif
978    dispatchVoid(serial, mSlotId, RIL_REQUEST_SIGNAL_STRENGTH);
979    return Void();
980}
981
982Return<void> RadioImpl::getVoiceRegistrationState(int32_t serial) {
983#if VDBG
984    RLOGD("getVoiceRegistrationState: serial %d", serial);
985#endif
986    dispatchVoid(serial, mSlotId, RIL_REQUEST_VOICE_REGISTRATION_STATE);
987    return Void();
988}
989
990Return<void> RadioImpl::getDataRegistrationState(int32_t serial) {
991#if VDBG
992    RLOGD("getDataRegistrationState: serial %d", serial);
993#endif
994    dispatchVoid(serial, mSlotId, RIL_REQUEST_DATA_REGISTRATION_STATE);
995    return Void();
996}
997
998Return<void> RadioImpl::getOperator(int32_t serial) {
999#if VDBG
1000    RLOGD("getOperator: serial %d", serial);
1001#endif
1002    dispatchVoid(serial, mSlotId, RIL_REQUEST_OPERATOR);
1003    return Void();
1004}
1005
1006Return<void> RadioImpl::setRadioPower(int32_t serial, bool on) {
1007    RLOGD("setRadioPower: serial %d on %d", serial, on);
1008    dispatchInts(serial, mSlotId, RIL_REQUEST_RADIO_POWER, 1, BOOL_TO_INT(on));
1009    return Void();
1010}
1011
1012Return<void> RadioImpl::sendDtmf(int32_t serial, const hidl_string& s) {
1013#if VDBG
1014    RLOGD("sendDtmf: serial %d", serial);
1015#endif
1016    dispatchString(serial, mSlotId, RIL_REQUEST_DTMF, s.c_str());
1017    return Void();
1018}
1019
1020Return<void> RadioImpl::sendSms(int32_t serial, const GsmSmsMessage& message) {
1021#if VDBG
1022    RLOGD("sendSms: serial %d", serial);
1023#endif
1024    dispatchStrings(serial, mSlotId, RIL_REQUEST_SEND_SMS,
1025            2, message.smscPdu.c_str(), message.pdu.c_str());
1026    return Void();
1027}
1028
1029Return<void> RadioImpl::sendSMSExpectMore(int32_t serial, const GsmSmsMessage& message) {
1030#if VDBG
1031    RLOGD("sendSMSExpectMore: serial %d", serial);
1032#endif
1033    dispatchStrings(serial, mSlotId, RIL_REQUEST_SEND_SMS_EXPECT_MORE,
1034            2, message.smscPdu.c_str(), message.pdu.c_str());
1035    return Void();
1036}
1037
1038static bool convertMvnoTypeToString(MvnoType type, char *&str) {
1039    switch (type) {
1040        case MvnoType::IMSI:
1041            str = (char *)"imsi";
1042            return true;
1043        case MvnoType::GID:
1044            str = (char *)"gid";
1045            return true;
1046        case MvnoType::SPN:
1047            str = (char *)"spn";
1048            return true;
1049        case MvnoType::NONE:
1050            str = (char *)"";
1051            return true;
1052    }
1053    return false;
1054}
1055
1056Return<void> RadioImpl::setupDataCall(int32_t serial, RadioTechnology radioTechnology,
1057                                      const DataProfileInfo& dataProfileInfo, bool modemCognitive,
1058                                      bool roamingAllowed, bool isRoaming) {
1059
1060#if VDBG
1061    RLOGD("setupDataCall: serial %d", serial);
1062#endif
1063
1064    if (s_vendorFunctions->version >= 4 && s_vendorFunctions->version <= 14) {
1065        const hidl_string &protocol =
1066                (isRoaming ? dataProfileInfo.roamingProtocol : dataProfileInfo.protocol);
1067        dispatchStrings(serial, mSlotId, RIL_REQUEST_SETUP_DATA_CALL, 7,
1068            std::to_string((int) radioTechnology + 2).c_str(),
1069            std::to_string((int) dataProfileInfo.profileId).c_str(),
1070            dataProfileInfo.apn.c_str(),
1071            dataProfileInfo.user.c_str(),
1072            dataProfileInfo.password.c_str(),
1073            std::to_string((int) dataProfileInfo.authType).c_str(),
1074            protocol.c_str());
1075    } else if (s_vendorFunctions->version >= 15) {
1076        char *mvnoTypeStr = NULL;
1077        if (!convertMvnoTypeToString(dataProfileInfo.mvnoType, mvnoTypeStr)) {
1078            RequestInfo *pRI = android::addRequestToList(serial, mSlotId,
1079                    RIL_REQUEST_SETUP_DATA_CALL);
1080            if (pRI != NULL) {
1081                sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS);
1082            }
1083            return Void();
1084        }
1085        dispatchStrings(serial, mSlotId, RIL_REQUEST_SETUP_DATA_CALL, 15,
1086            std::to_string((int) radioTechnology + 2).c_str(),
1087            std::to_string((int) dataProfileInfo.profileId).c_str(),
1088            dataProfileInfo.apn.c_str(),
1089            dataProfileInfo.user.c_str(),
1090            dataProfileInfo.password.c_str(),
1091            std::to_string((int) dataProfileInfo.authType).c_str(),
1092            dataProfileInfo.protocol.c_str(),
1093            dataProfileInfo.roamingProtocol.c_str(),
1094            std::to_string(dataProfileInfo.supportedApnTypesBitmap).c_str(),
1095            std::to_string(dataProfileInfo.bearerBitmap).c_str(),
1096            modemCognitive ? "1" : "0",
1097            std::to_string(dataProfileInfo.mtu).c_str(),
1098            mvnoTypeStr,
1099            dataProfileInfo.mvnoMatchData.c_str(),
1100            roamingAllowed ? "1" : "0");
1101    } else {
1102        RLOGE("Unsupported RIL version %d, min version expected 4", s_vendorFunctions->version);
1103        RequestInfo *pRI = android::addRequestToList(serial, mSlotId,
1104                RIL_REQUEST_SETUP_DATA_CALL);
1105        if (pRI != NULL) {
1106            sendErrorResponse(pRI, RIL_E_REQUEST_NOT_SUPPORTED);
1107        }
1108    }
1109    return Void();
1110}
1111
1112Return<void> RadioImpl::iccIOForApp(int32_t serial, const IccIo& iccIo) {
1113#if VDBG
1114    RLOGD("iccIOForApp: serial %d", serial);
1115#endif
1116    RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_SIM_IO);
1117    if (pRI == NULL) {
1118        return Void();
1119    }
1120
1121    RIL_SIM_IO_v6 rilIccIo = {};
1122    rilIccIo.command = iccIo.command;
1123    rilIccIo.fileid = iccIo.fileId;
1124    if (!copyHidlStringToRil(&rilIccIo.path, iccIo.path, pRI)) {
1125        return Void();
1126    }
1127
1128    rilIccIo.p1 = iccIo.p1;
1129    rilIccIo.p2 = iccIo.p2;
1130    rilIccIo.p3 = iccIo.p3;
1131
1132    if (!copyHidlStringToRil(&rilIccIo.data, iccIo.data, pRI)) {
1133        memsetAndFreeStrings(1, rilIccIo.path);
1134        return Void();
1135    }
1136
1137    if (!copyHidlStringToRil(&rilIccIo.pin2, iccIo.pin2, pRI)) {
1138        memsetAndFreeStrings(2, rilIccIo.path, rilIccIo.data);
1139        return Void();
1140    }
1141
1142    if (!copyHidlStringToRil(&rilIccIo.aidPtr, iccIo.aid, pRI)) {
1143        memsetAndFreeStrings(3, rilIccIo.path, rilIccIo.data, rilIccIo.pin2);
1144        return Void();
1145    }
1146
1147    CALL_ONREQUEST(RIL_REQUEST_SIM_IO, &rilIccIo, sizeof(rilIccIo), pRI, mSlotId);
1148
1149    memsetAndFreeStrings(4, rilIccIo.path, rilIccIo.data, rilIccIo.pin2, rilIccIo.aidPtr);
1150
1151    return Void();
1152}
1153
1154Return<void> RadioImpl::sendUssd(int32_t serial, const hidl_string& ussd) {
1155#if VDBG
1156    RLOGD("sendUssd: serial %d", serial);
1157#endif
1158    dispatchString(serial, mSlotId, RIL_REQUEST_SEND_USSD, ussd.c_str());
1159    return Void();
1160}
1161
1162Return<void> RadioImpl::cancelPendingUssd(int32_t serial) {
1163#if VDBG
1164    RLOGD("cancelPendingUssd: serial %d", serial);
1165#endif
1166    dispatchVoid(serial, mSlotId, RIL_REQUEST_CANCEL_USSD);
1167    return Void();
1168}
1169
1170Return<void> RadioImpl::getClir(int32_t serial) {
1171#if VDBG
1172    RLOGD("getClir: serial %d", serial);
1173#endif
1174    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_CLIR);
1175    return Void();
1176}
1177
1178Return<void> RadioImpl::setClir(int32_t serial, int32_t status) {
1179#if VDBG
1180    RLOGD("setClir: serial %d", serial);
1181#endif
1182    dispatchInts(serial, mSlotId, RIL_REQUEST_SET_CLIR, 1, status);
1183    return Void();
1184}
1185
1186Return<void> RadioImpl::getCallForwardStatus(int32_t serial, const CallForwardInfo& callInfo) {
1187#if VDBG
1188    RLOGD("getCallForwardStatus: serial %d", serial);
1189#endif
1190    dispatchCallForwardStatus(serial, mSlotId, RIL_REQUEST_QUERY_CALL_FORWARD_STATUS,
1191            callInfo);
1192    return Void();
1193}
1194
1195Return<void> RadioImpl::setCallForward(int32_t serial, const CallForwardInfo& callInfo) {
1196#if VDBG
1197    RLOGD("setCallForward: serial %d", serial);
1198#endif
1199    dispatchCallForwardStatus(serial, mSlotId, RIL_REQUEST_SET_CALL_FORWARD,
1200            callInfo);
1201    return Void();
1202}
1203
1204Return<void> RadioImpl::getCallWaiting(int32_t serial, int32_t serviceClass) {
1205#if VDBG
1206    RLOGD("getCallWaiting: serial %d", serial);
1207#endif
1208    dispatchInts(serial, mSlotId, RIL_REQUEST_QUERY_CALL_WAITING, 1, serviceClass);
1209    return Void();
1210}
1211
1212Return<void> RadioImpl::setCallWaiting(int32_t serial, bool enable, int32_t serviceClass) {
1213#if VDBG
1214    RLOGD("setCallWaiting: serial %d", serial);
1215#endif
1216    dispatchInts(serial, mSlotId, RIL_REQUEST_SET_CALL_WAITING, 2, BOOL_TO_INT(enable),
1217            serviceClass);
1218    return Void();
1219}
1220
1221Return<void> RadioImpl::acknowledgeLastIncomingGsmSms(int32_t serial,
1222                                                      bool success, SmsAcknowledgeFailCause cause) {
1223#if VDBG
1224    RLOGD("acknowledgeLastIncomingGsmSms: serial %d", serial);
1225#endif
1226    dispatchInts(serial, mSlotId, RIL_REQUEST_SMS_ACKNOWLEDGE, 2, BOOL_TO_INT(success),
1227            cause);
1228    return Void();
1229}
1230
1231Return<void> RadioImpl::acceptCall(int32_t serial) {
1232#if VDBG
1233    RLOGD("acceptCall: serial %d", serial);
1234#endif
1235    dispatchVoid(serial, mSlotId, RIL_REQUEST_ANSWER);
1236    return Void();
1237}
1238
1239Return<void> RadioImpl::deactivateDataCall(int32_t serial,
1240                                           int32_t cid, bool reasonRadioShutDown) {
1241#if VDBG
1242    RLOGD("deactivateDataCall: serial %d", serial);
1243#endif
1244    dispatchStrings(serial, mSlotId, RIL_REQUEST_DEACTIVATE_DATA_CALL,
1245            2, (std::to_string(cid)).c_str(), reasonRadioShutDown ? "1" : "0");
1246    return Void();
1247}
1248
1249Return<void> RadioImpl::getFacilityLockForApp(int32_t serial, const hidl_string& facility,
1250                                              const hidl_string& password, int32_t serviceClass,
1251                                              const hidl_string& appId) {
1252#if VDBG
1253    RLOGD("getFacilityLockForApp: serial %d", serial);
1254#endif
1255    dispatchStrings(serial, mSlotId, RIL_REQUEST_QUERY_FACILITY_LOCK,
1256            4, facility.c_str(), password.c_str(),
1257            (std::to_string(serviceClass)).c_str(), appId.c_str());
1258    return Void();
1259}
1260
1261Return<void> RadioImpl::setFacilityLockForApp(int32_t serial, const hidl_string& facility,
1262                                              bool lockState, const hidl_string& password,
1263                                              int32_t serviceClass, const hidl_string& appId) {
1264#if VDBG
1265    RLOGD("setFacilityLockForApp: serial %d", serial);
1266#endif
1267    dispatchStrings(serial, mSlotId, RIL_REQUEST_SET_FACILITY_LOCK,
1268            5, facility.c_str(), lockState ? "1" : "0", password.c_str(),
1269            (std::to_string(serviceClass)).c_str(), appId.c_str() );
1270    return Void();
1271}
1272
1273Return<void> RadioImpl::setBarringPassword(int32_t serial, const hidl_string& facility,
1274                                           const hidl_string& oldPassword,
1275                                           const hidl_string& newPassword) {
1276#if VDBG
1277    RLOGD("setBarringPassword: serial %d", serial);
1278#endif
1279    dispatchStrings(serial, mSlotId, RIL_REQUEST_CHANGE_BARRING_PASSWORD,
1280            3, facility.c_str(), oldPassword.c_str(), newPassword.c_str());
1281    return Void();
1282}
1283
1284Return<void> RadioImpl::getNetworkSelectionMode(int32_t serial) {
1285#if VDBG
1286    RLOGD("getNetworkSelectionMode: serial %d", serial);
1287#endif
1288    dispatchVoid(serial, mSlotId, RIL_REQUEST_QUERY_NETWORK_SELECTION_MODE);
1289    return Void();
1290}
1291
1292Return<void> RadioImpl::setNetworkSelectionModeAutomatic(int32_t serial) {
1293#if VDBG
1294    RLOGD("setNetworkSelectionModeAutomatic: serial %d", serial);
1295#endif
1296    dispatchVoid(serial, mSlotId, RIL_REQUEST_SET_NETWORK_SELECTION_AUTOMATIC);
1297    return Void();
1298}
1299
1300Return<void> RadioImpl::setNetworkSelectionModeManual(int32_t serial,
1301                                                      const hidl_string& operatorNumeric) {
1302#if VDBG
1303    RLOGD("setNetworkSelectionModeManual: serial %d", serial);
1304#endif
1305    dispatchString(serial, mSlotId, RIL_REQUEST_SET_NETWORK_SELECTION_MANUAL,
1306            operatorNumeric.c_str());
1307    return Void();
1308}
1309
1310Return<void> RadioImpl::getAvailableNetworks(int32_t serial) {
1311#if VDBG
1312    RLOGD("getAvailableNetworks: serial %d", serial);
1313#endif
1314    dispatchVoid(serial, mSlotId, RIL_REQUEST_QUERY_AVAILABLE_NETWORKS);
1315    return Void();
1316}
1317
1318Return<void> RadioImpl::startDtmf(int32_t serial, const hidl_string& s) {
1319#if VDBG
1320    RLOGD("startDtmf: serial %d", serial);
1321#endif
1322    dispatchString(serial, mSlotId, RIL_REQUEST_DTMF_START,
1323            s.c_str());
1324    return Void();
1325}
1326
1327Return<void> RadioImpl::stopDtmf(int32_t serial) {
1328#if VDBG
1329    RLOGD("stopDtmf: serial %d", serial);
1330#endif
1331    dispatchVoid(serial, mSlotId, RIL_REQUEST_DTMF_STOP);
1332    return Void();
1333}
1334
1335Return<void> RadioImpl::getBasebandVersion(int32_t serial) {
1336#if VDBG
1337    RLOGD("getBasebandVersion: serial %d", serial);
1338#endif
1339    dispatchVoid(serial, mSlotId, RIL_REQUEST_BASEBAND_VERSION);
1340    return Void();
1341}
1342
1343Return<void> RadioImpl::separateConnection(int32_t serial, int32_t gsmIndex) {
1344#if VDBG
1345    RLOGD("separateConnection: serial %d", serial);
1346#endif
1347    dispatchInts(serial, mSlotId, RIL_REQUEST_SEPARATE_CONNECTION, 1, gsmIndex);
1348    return Void();
1349}
1350
1351Return<void> RadioImpl::setMute(int32_t serial, bool enable) {
1352#if VDBG
1353    RLOGD("setMute: serial %d", serial);
1354#endif
1355    dispatchInts(serial, mSlotId, RIL_REQUEST_SET_MUTE, 1, BOOL_TO_INT(enable));
1356    return Void();
1357}
1358
1359Return<void> RadioImpl::getMute(int32_t serial) {
1360#if VDBG
1361    RLOGD("getMute: serial %d", serial);
1362#endif
1363    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_MUTE);
1364    return Void();
1365}
1366
1367Return<void> RadioImpl::getClip(int32_t serial) {
1368#if VDBG
1369    RLOGD("getClip: serial %d", serial);
1370#endif
1371    dispatchVoid(serial, mSlotId, RIL_REQUEST_QUERY_CLIP);
1372    return Void();
1373}
1374
1375Return<void> RadioImpl::getDataCallList(int32_t serial) {
1376#if VDBG
1377    RLOGD("getDataCallList: serial %d", serial);
1378#endif
1379    dispatchVoid(serial, mSlotId, RIL_REQUEST_DATA_CALL_LIST);
1380    return Void();
1381}
1382
1383Return<void> RadioImpl::setSuppServiceNotifications(int32_t serial, bool enable) {
1384#if VDBG
1385    RLOGD("setSuppServiceNotifications: serial %d", serial);
1386#endif
1387    dispatchInts(serial, mSlotId, RIL_REQUEST_SET_SUPP_SVC_NOTIFICATION, 1,
1388            BOOL_TO_INT(enable));
1389    return Void();
1390}
1391
1392Return<void> RadioImpl::writeSmsToSim(int32_t serial, const SmsWriteArgs& smsWriteArgs) {
1393#if VDBG
1394    RLOGD("writeSmsToSim: serial %d", serial);
1395#endif
1396    RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_WRITE_SMS_TO_SIM);
1397    if (pRI == NULL) {
1398        return Void();
1399    }
1400
1401    RIL_SMS_WriteArgs args;
1402    args.status = (int) smsWriteArgs.status;
1403
1404    int len;
1405    if (!copyHidlStringToRil(&args.pdu, smsWriteArgs.pdu, pRI)) {
1406        return Void();
1407    }
1408
1409    if (!copyHidlStringToRil(&args.smsc, smsWriteArgs.smsc, pRI)) {
1410        memsetAndFreeStrings(1, args.pdu);
1411        return Void();
1412    }
1413
1414    CALL_ONREQUEST(RIL_REQUEST_WRITE_SMS_TO_SIM, &args, sizeof(args), pRI, mSlotId);
1415
1416    memsetAndFreeStrings(2, args.smsc, args.pdu);
1417
1418    return Void();
1419}
1420
1421Return<void> RadioImpl::deleteSmsOnSim(int32_t serial, int32_t index) {
1422#if VDBG
1423    RLOGD("deleteSmsOnSim: serial %d", serial);
1424#endif
1425    dispatchInts(serial, mSlotId, RIL_REQUEST_DELETE_SMS_ON_SIM, 1, index);
1426    return Void();
1427}
1428
1429Return<void> RadioImpl::setBandMode(int32_t serial, RadioBandMode mode) {
1430#if VDBG
1431    RLOGD("setBandMode: serial %d", serial);
1432#endif
1433    dispatchInts(serial, mSlotId, RIL_REQUEST_SET_BAND_MODE, 1, mode);
1434    return Void();
1435}
1436
1437Return<void> RadioImpl::getAvailableBandModes(int32_t serial) {
1438#if VDBG
1439    RLOGD("getAvailableBandModes: serial %d", serial);
1440#endif
1441    dispatchVoid(serial, mSlotId, RIL_REQUEST_QUERY_AVAILABLE_BAND_MODE);
1442    return Void();
1443}
1444
1445Return<void> RadioImpl::sendEnvelope(int32_t serial, const hidl_string& command) {
1446#if VDBG
1447    RLOGD("sendEnvelope: serial %d", serial);
1448#endif
1449    dispatchString(serial, mSlotId, RIL_REQUEST_STK_SEND_ENVELOPE_COMMAND,
1450            command.c_str());
1451    return Void();
1452}
1453
1454Return<void> RadioImpl::sendTerminalResponseToSim(int32_t serial,
1455                                                  const hidl_string& commandResponse) {
1456#if VDBG
1457    RLOGD("sendTerminalResponseToSim: serial %d", serial);
1458#endif
1459    dispatchString(serial, mSlotId, RIL_REQUEST_STK_SEND_TERMINAL_RESPONSE,
1460            commandResponse.c_str());
1461    return Void();
1462}
1463
1464Return<void> RadioImpl::handleStkCallSetupRequestFromSim(int32_t serial, bool accept) {
1465#if VDBG
1466    RLOGD("handleStkCallSetupRequestFromSim: serial %d", serial);
1467#endif
1468    dispatchInts(serial, mSlotId, RIL_REQUEST_STK_HANDLE_CALL_SETUP_REQUESTED_FROM_SIM,
1469            1, BOOL_TO_INT(accept));
1470    return Void();
1471}
1472
1473Return<void> RadioImpl::explicitCallTransfer(int32_t serial) {
1474#if VDBG
1475    RLOGD("explicitCallTransfer: serial %d", serial);
1476#endif
1477    dispatchVoid(serial, mSlotId, RIL_REQUEST_EXPLICIT_CALL_TRANSFER);
1478    return Void();
1479}
1480
1481Return<void> RadioImpl::setPreferredNetworkType(int32_t serial, PreferredNetworkType nwType) {
1482#if VDBG
1483    RLOGD("setPreferredNetworkType: serial %d", serial);
1484#endif
1485    dispatchInts(serial, mSlotId, RIL_REQUEST_SET_PREFERRED_NETWORK_TYPE, 1, nwType);
1486    return Void();
1487}
1488
1489Return<void> RadioImpl::getPreferredNetworkType(int32_t serial) {
1490#if VDBG
1491    RLOGD("getPreferredNetworkType: serial %d", serial);
1492#endif
1493    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_PREFERRED_NETWORK_TYPE);
1494    return Void();
1495}
1496
1497Return<void> RadioImpl::getNeighboringCids(int32_t serial) {
1498#if VDBG
1499    RLOGD("getNeighboringCids: serial %d", serial);
1500#endif
1501    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_NEIGHBORING_CELL_IDS);
1502    return Void();
1503}
1504
1505Return<void> RadioImpl::setLocationUpdates(int32_t serial, bool enable) {
1506#if VDBG
1507    RLOGD("setLocationUpdates: serial %d", serial);
1508#endif
1509    dispatchInts(serial, mSlotId, RIL_REQUEST_SET_LOCATION_UPDATES, 1, BOOL_TO_INT(enable));
1510    return Void();
1511}
1512
1513Return<void> RadioImpl::setCdmaSubscriptionSource(int32_t serial, CdmaSubscriptionSource cdmaSub) {
1514#if VDBG
1515    RLOGD("setCdmaSubscriptionSource: serial %d", serial);
1516#endif
1517    dispatchInts(serial, mSlotId, RIL_REQUEST_CDMA_SET_SUBSCRIPTION_SOURCE, 1, cdmaSub);
1518    return Void();
1519}
1520
1521Return<void> RadioImpl::setCdmaRoamingPreference(int32_t serial, CdmaRoamingType type) {
1522#if VDBG
1523    RLOGD("setCdmaRoamingPreference: serial %d", serial);
1524#endif
1525    dispatchInts(serial, mSlotId, RIL_REQUEST_CDMA_SET_ROAMING_PREFERENCE, 1, type);
1526    return Void();
1527}
1528
1529Return<void> RadioImpl::getCdmaRoamingPreference(int32_t serial) {
1530#if VDBG
1531    RLOGD("getCdmaRoamingPreference: serial %d", serial);
1532#endif
1533    dispatchVoid(serial, mSlotId, RIL_REQUEST_CDMA_QUERY_ROAMING_PREFERENCE);
1534    return Void();
1535}
1536
1537Return<void> RadioImpl::setTTYMode(int32_t serial, TtyMode mode) {
1538#if VDBG
1539    RLOGD("setTTYMode: serial %d", serial);
1540#endif
1541    dispatchInts(serial, mSlotId, RIL_REQUEST_SET_TTY_MODE, 1, mode);
1542    return Void();
1543}
1544
1545Return<void> RadioImpl::getTTYMode(int32_t serial) {
1546#if VDBG
1547    RLOGD("getTTYMode: serial %d", serial);
1548#endif
1549    dispatchVoid(serial, mSlotId, RIL_REQUEST_QUERY_TTY_MODE);
1550    return Void();
1551}
1552
1553Return<void> RadioImpl::setPreferredVoicePrivacy(int32_t serial, bool enable) {
1554#if VDBG
1555    RLOGD("setPreferredVoicePrivacy: serial %d", serial);
1556#endif
1557    dispatchInts(serial, mSlotId, RIL_REQUEST_CDMA_SET_PREFERRED_VOICE_PRIVACY_MODE,
1558            1, BOOL_TO_INT(enable));
1559    return Void();
1560}
1561
1562Return<void> RadioImpl::getPreferredVoicePrivacy(int32_t serial) {
1563#if VDBG
1564    RLOGD("getPreferredVoicePrivacy: serial %d", serial);
1565#endif
1566    dispatchVoid(serial, mSlotId, RIL_REQUEST_CDMA_QUERY_PREFERRED_VOICE_PRIVACY_MODE);
1567    return Void();
1568}
1569
1570Return<void> RadioImpl::sendCDMAFeatureCode(int32_t serial, const hidl_string& featureCode) {
1571#if VDBG
1572    RLOGD("sendCDMAFeatureCode: serial %d", serial);
1573#endif
1574    dispatchString(serial, mSlotId, RIL_REQUEST_CDMA_FLASH,
1575            featureCode.c_str());
1576    return Void();
1577}
1578
1579Return<void> RadioImpl::sendBurstDtmf(int32_t serial, const hidl_string& dtmf, int32_t on,
1580                                      int32_t off) {
1581#if VDBG
1582    RLOGD("sendBurstDtmf: serial %d", serial);
1583#endif
1584    dispatchStrings(serial, mSlotId, RIL_REQUEST_CDMA_BURST_DTMF,
1585            3, dtmf.c_str(), (std::to_string(on)).c_str(),
1586            (std::to_string(off)).c_str());
1587    return Void();
1588}
1589
1590void constructCdmaSms(RIL_CDMA_SMS_Message &rcsm, const CdmaSmsMessage& sms) {
1591    rcsm.uTeleserviceID = sms.teleserviceId;
1592    rcsm.bIsServicePresent = BOOL_TO_INT(sms.isServicePresent);
1593    rcsm.uServicecategory = sms.serviceCategory;
1594    rcsm.sAddress.digit_mode = (RIL_CDMA_SMS_DigitMode) sms.address.digitMode;
1595    rcsm.sAddress.number_mode = (RIL_CDMA_SMS_NumberMode) sms.address.numberMode;
1596    rcsm.sAddress.number_type = (RIL_CDMA_SMS_NumberType) sms.address.numberType;
1597    rcsm.sAddress.number_plan = (RIL_CDMA_SMS_NumberPlan) sms.address.numberPlan;
1598
1599    rcsm.sAddress.number_of_digits = sms.address.digits.size();
1600    int digitLimit= MIN((rcsm.sAddress.number_of_digits), RIL_CDMA_SMS_ADDRESS_MAX);
1601    for (int i = 0; i < digitLimit; i++) {
1602        rcsm.sAddress.digits[i] = sms.address.digits[i];
1603    }
1604
1605    rcsm.sSubAddress.subaddressType = (RIL_CDMA_SMS_SubaddressType) sms.subAddress.subaddressType;
1606    rcsm.sSubAddress.odd = BOOL_TO_INT(sms.subAddress.odd);
1607
1608    rcsm.sSubAddress.number_of_digits = sms.subAddress.digits.size();
1609    digitLimit= MIN((rcsm.sSubAddress.number_of_digits), RIL_CDMA_SMS_SUBADDRESS_MAX);
1610    for (int i = 0; i < digitLimit; i++) {
1611        rcsm.sSubAddress.digits[i] = sms.subAddress.digits[i];
1612    }
1613
1614    rcsm.uBearerDataLen = sms.bearerData.size();
1615    digitLimit= MIN((rcsm.uBearerDataLen), RIL_CDMA_SMS_BEARER_DATA_MAX);
1616    for (int i = 0; i < digitLimit; i++) {
1617        rcsm.aBearerData[i] = sms.bearerData[i];
1618    }
1619}
1620
1621Return<void> RadioImpl::sendCdmaSms(int32_t serial, const CdmaSmsMessage& sms) {
1622#if VDBG
1623    RLOGD("sendCdmaSms: serial %d", serial);
1624#endif
1625    RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_CDMA_SEND_SMS);
1626    if (pRI == NULL) {
1627        return Void();
1628    }
1629
1630    RIL_CDMA_SMS_Message rcsm = {};
1631    constructCdmaSms(rcsm, sms);
1632
1633    CALL_ONREQUEST(pRI->pCI->requestNumber, &rcsm, sizeof(rcsm), pRI, mSlotId);
1634    return Void();
1635}
1636
1637Return<void> RadioImpl::acknowledgeLastIncomingCdmaSms(int32_t serial, const CdmaSmsAck& smsAck) {
1638#if VDBG
1639    RLOGD("acknowledgeLastIncomingCdmaSms: serial %d", serial);
1640#endif
1641    RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_CDMA_SMS_ACKNOWLEDGE);
1642    if (pRI == NULL) {
1643        return Void();
1644    }
1645
1646    RIL_CDMA_SMS_Ack rcsa = {};
1647
1648    rcsa.uErrorClass = (RIL_CDMA_SMS_ErrorClass) smsAck.errorClass;
1649    rcsa.uSMSCauseCode = smsAck.smsCauseCode;
1650
1651    CALL_ONREQUEST(pRI->pCI->requestNumber, &rcsa, sizeof(rcsa), pRI, mSlotId);
1652    return Void();
1653}
1654
1655Return<void> RadioImpl::getGsmBroadcastConfig(int32_t serial) {
1656#if VDBG
1657    RLOGD("getGsmBroadcastConfig: serial %d", serial);
1658#endif
1659    dispatchVoid(serial, mSlotId, RIL_REQUEST_GSM_GET_BROADCAST_SMS_CONFIG);
1660    return Void();
1661}
1662
1663Return<void> RadioImpl::setGsmBroadcastConfig(int32_t serial,
1664                                              const hidl_vec<GsmBroadcastSmsConfigInfo>&
1665                                              configInfo) {
1666#if VDBG
1667    RLOGD("setGsmBroadcastConfig: serial %d", serial);
1668#endif
1669    RequestInfo *pRI = android::addRequestToList(serial, mSlotId,
1670            RIL_REQUEST_GSM_SET_BROADCAST_SMS_CONFIG);
1671    if (pRI == NULL) {
1672        return Void();
1673    }
1674
1675    int num = configInfo.size();
1676    RIL_GSM_BroadcastSmsConfigInfo gsmBci[num];
1677    RIL_GSM_BroadcastSmsConfigInfo *gsmBciPtrs[num];
1678
1679    for (int i = 0 ; i < num ; i++ ) {
1680        gsmBciPtrs[i] = &gsmBci[i];
1681        gsmBci[i].fromServiceId = configInfo[i].fromServiceId;
1682        gsmBci[i].toServiceId = configInfo[i].toServiceId;
1683        gsmBci[i].fromCodeScheme = configInfo[i].fromCodeScheme;
1684        gsmBci[i].toCodeScheme = configInfo[i].toCodeScheme;
1685        gsmBci[i].selected = BOOL_TO_INT(configInfo[i].selected);
1686    }
1687
1688    CALL_ONREQUEST(pRI->pCI->requestNumber, gsmBciPtrs,
1689            num * sizeof(RIL_GSM_BroadcastSmsConfigInfo *), pRI, mSlotId);
1690    return Void();
1691}
1692
1693Return<void> RadioImpl::setGsmBroadcastActivation(int32_t serial, bool activate) {
1694#if VDBG
1695    RLOGD("setGsmBroadcastActivation: serial %d", serial);
1696#endif
1697    dispatchInts(serial, mSlotId, RIL_REQUEST_GSM_SMS_BROADCAST_ACTIVATION,
1698            1, BOOL_TO_INT(!activate));
1699    return Void();
1700}
1701
1702Return<void> RadioImpl::getCdmaBroadcastConfig(int32_t serial) {
1703#if VDBG
1704    RLOGD("getCdmaBroadcastConfig: serial %d", serial);
1705#endif
1706    dispatchVoid(serial, mSlotId, RIL_REQUEST_CDMA_GET_BROADCAST_SMS_CONFIG);
1707    return Void();
1708}
1709
1710Return<void> RadioImpl::setCdmaBroadcastConfig(int32_t serial,
1711                                               const hidl_vec<CdmaBroadcastSmsConfigInfo>&
1712                                               configInfo) {
1713#if VDBG
1714    RLOGD("setCdmaBroadcastConfig: serial %d", serial);
1715#endif
1716    RequestInfo *pRI = android::addRequestToList(serial, mSlotId,
1717            RIL_REQUEST_CDMA_SET_BROADCAST_SMS_CONFIG);
1718    if (pRI == NULL) {
1719        return Void();
1720    }
1721
1722    int num = configInfo.size();
1723    RIL_CDMA_BroadcastSmsConfigInfo cdmaBci[num];
1724    RIL_CDMA_BroadcastSmsConfigInfo *cdmaBciPtrs[num];
1725
1726    for (int i = 0 ; i < num ; i++ ) {
1727        cdmaBciPtrs[i] = &cdmaBci[i];
1728        cdmaBci[i].service_category = configInfo[i].serviceCategory;
1729        cdmaBci[i].language = configInfo[i].language;
1730        cdmaBci[i].selected = BOOL_TO_INT(configInfo[i].selected);
1731    }
1732
1733    CALL_ONREQUEST(pRI->pCI->requestNumber, cdmaBciPtrs,
1734            num * sizeof(RIL_CDMA_BroadcastSmsConfigInfo *), pRI, mSlotId);
1735    return Void();
1736}
1737
1738Return<void> RadioImpl::setCdmaBroadcastActivation(int32_t serial, bool activate) {
1739#if VDBG
1740    RLOGD("setCdmaBroadcastActivation: serial %d", serial);
1741#endif
1742    dispatchInts(serial, mSlotId, RIL_REQUEST_CDMA_SMS_BROADCAST_ACTIVATION,
1743            1, BOOL_TO_INT(!activate));
1744    return Void();
1745}
1746
1747Return<void> RadioImpl::getCDMASubscription(int32_t serial) {
1748#if VDBG
1749    RLOGD("getCDMASubscription: serial %d", serial);
1750#endif
1751    dispatchVoid(serial, mSlotId, RIL_REQUEST_CDMA_SUBSCRIPTION);
1752    return Void();
1753}
1754
1755Return<void> RadioImpl::writeSmsToRuim(int32_t serial, const CdmaSmsWriteArgs& cdmaSms) {
1756#if VDBG
1757    RLOGD("writeSmsToRuim: serial %d", serial);
1758#endif
1759    RequestInfo *pRI = android::addRequestToList(serial, mSlotId,
1760            RIL_REQUEST_CDMA_WRITE_SMS_TO_RUIM);
1761    if (pRI == NULL) {
1762        return Void();
1763    }
1764
1765    RIL_CDMA_SMS_WriteArgs rcsw = {};
1766    rcsw.status = (int) cdmaSms.status;
1767    constructCdmaSms(rcsw.message, cdmaSms.message);
1768
1769    CALL_ONREQUEST(pRI->pCI->requestNumber, &rcsw, sizeof(rcsw), pRI, mSlotId);
1770    return Void();
1771}
1772
1773Return<void> RadioImpl::deleteSmsOnRuim(int32_t serial, int32_t index) {
1774#if VDBG
1775    RLOGD("deleteSmsOnRuim: serial %d", serial);
1776#endif
1777    dispatchInts(serial, mSlotId, RIL_REQUEST_CDMA_DELETE_SMS_ON_RUIM, 1, index);
1778    return Void();
1779}
1780
1781Return<void> RadioImpl::getDeviceIdentity(int32_t serial) {
1782#if VDBG
1783    RLOGD("getDeviceIdentity: serial %d", serial);
1784#endif
1785    dispatchVoid(serial, mSlotId, RIL_REQUEST_DEVICE_IDENTITY);
1786    return Void();
1787}
1788
1789Return<void> RadioImpl::exitEmergencyCallbackMode(int32_t serial) {
1790#if VDBG
1791    RLOGD("exitEmergencyCallbackMode: serial %d", serial);
1792#endif
1793    dispatchVoid(serial, mSlotId, RIL_REQUEST_EXIT_EMERGENCY_CALLBACK_MODE);
1794    return Void();
1795}
1796
1797Return<void> RadioImpl::getSmscAddress(int32_t serial) {
1798#if VDBG
1799    RLOGD("getSmscAddress: serial %d", serial);
1800#endif
1801    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_SMSC_ADDRESS);
1802    return Void();
1803}
1804
1805Return<void> RadioImpl::setSmscAddress(int32_t serial, const hidl_string& smsc) {
1806#if VDBG
1807    RLOGD("setSmscAddress: serial %d", serial);
1808#endif
1809    dispatchString(serial, mSlotId, RIL_REQUEST_SET_SMSC_ADDRESS,
1810            smsc.c_str());
1811    return Void();
1812}
1813
1814Return<void> RadioImpl::reportSmsMemoryStatus(int32_t serial, bool available) {
1815#if VDBG
1816    RLOGD("reportSmsMemoryStatus: serial %d", serial);
1817#endif
1818    dispatchInts(serial, mSlotId, RIL_REQUEST_REPORT_SMS_MEMORY_STATUS, 1,
1819            BOOL_TO_INT(available));
1820    return Void();
1821}
1822
1823Return<void> RadioImpl::reportStkServiceIsRunning(int32_t serial) {
1824#if VDBG
1825    RLOGD("reportStkServiceIsRunning: serial %d", serial);
1826#endif
1827    dispatchVoid(serial, mSlotId, RIL_REQUEST_REPORT_STK_SERVICE_IS_RUNNING);
1828    return Void();
1829}
1830
1831Return<void> RadioImpl::getCdmaSubscriptionSource(int32_t serial) {
1832#if VDBG
1833    RLOGD("getCdmaSubscriptionSource: serial %d", serial);
1834#endif
1835    dispatchVoid(serial, mSlotId, RIL_REQUEST_CDMA_GET_SUBSCRIPTION_SOURCE);
1836    return Void();
1837}
1838
1839Return<void> RadioImpl::requestIsimAuthentication(int32_t serial, const hidl_string& challenge) {
1840#if VDBG
1841    RLOGD("requestIsimAuthentication: serial %d", serial);
1842#endif
1843    dispatchString(serial, mSlotId, RIL_REQUEST_ISIM_AUTHENTICATION,
1844            challenge.c_str());
1845    return Void();
1846}
1847
1848Return<void> RadioImpl::acknowledgeIncomingGsmSmsWithPdu(int32_t serial, bool success,
1849                                                         const hidl_string& ackPdu) {
1850#if VDBG
1851    RLOGD("acknowledgeIncomingGsmSmsWithPdu: serial %d", serial);
1852#endif
1853    dispatchStrings(serial, mSlotId, RIL_REQUEST_ACKNOWLEDGE_INCOMING_GSM_SMS_WITH_PDU,
1854            2, success ? "1" : "0", ackPdu.c_str());
1855    return Void();
1856}
1857
1858Return<void> RadioImpl::sendEnvelopeWithStatus(int32_t serial, const hidl_string& contents) {
1859#if VDBG
1860    RLOGD("sendEnvelopeWithStatus: serial %d", serial);
1861#endif
1862    dispatchString(serial, mSlotId, RIL_REQUEST_STK_SEND_ENVELOPE_WITH_STATUS,
1863            contents.c_str());
1864    return Void();
1865}
1866
1867Return<void> RadioImpl::getVoiceRadioTechnology(int32_t serial) {
1868#if VDBG
1869    RLOGD("getVoiceRadioTechnology: serial %d", serial);
1870#endif
1871    dispatchVoid(serial, mSlotId, RIL_REQUEST_VOICE_RADIO_TECH);
1872    return Void();
1873}
1874
1875Return<void> RadioImpl::getCellInfoList(int32_t serial) {
1876#if VDBG
1877    RLOGD("getCellInfoList: serial %d", serial);
1878#endif
1879    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_CELL_INFO_LIST);
1880    return Void();
1881}
1882
1883Return<void> RadioImpl::setCellInfoListRate(int32_t serial, int32_t rate) {
1884#if VDBG
1885    RLOGD("setCellInfoListRate: serial %d", serial);
1886#endif
1887    dispatchInts(serial, mSlotId, RIL_REQUEST_SET_UNSOL_CELL_INFO_LIST_RATE, 1, rate);
1888    return Void();
1889}
1890
1891Return<void> RadioImpl::setInitialAttachApn(int32_t serial, const DataProfileInfo& dataProfileInfo,
1892                                            bool modemCognitive, bool isRoaming) {
1893#if VDBG
1894    RLOGD("setInitialAttachApn: serial %d", serial);
1895#endif
1896    RequestInfo *pRI = android::addRequestToList(serial, mSlotId,
1897            RIL_REQUEST_SET_INITIAL_ATTACH_APN);
1898    if (pRI == NULL) {
1899        return Void();
1900    }
1901
1902    if (s_vendorFunctions->version <= 14) {
1903        RIL_InitialAttachApn iaa = {};
1904
1905        if (!copyHidlStringToRil(&iaa.apn, dataProfileInfo.apn, pRI)) {
1906            return Void();
1907        }
1908
1909        const hidl_string &protocol =
1910                (isRoaming ? dataProfileInfo.roamingProtocol : dataProfileInfo.protocol);
1911
1912        if (!copyHidlStringToRil(&iaa.protocol, protocol, pRI)) {
1913            memsetAndFreeStrings(1, iaa.apn);
1914            return Void();
1915        }
1916        iaa.authtype = (int) dataProfileInfo.authType;
1917        if (!copyHidlStringToRil(&iaa.username, dataProfileInfo.user, pRI)) {
1918            memsetAndFreeStrings(2, iaa.apn, iaa.protocol);
1919            return Void();
1920        }
1921        if (!copyHidlStringToRil(&iaa.password, dataProfileInfo.password, pRI)) {
1922            memsetAndFreeStrings(3, iaa.apn, iaa.protocol, iaa.username);
1923            return Void();
1924        }
1925
1926        CALL_ONREQUEST(RIL_REQUEST_SET_INITIAL_ATTACH_APN, &iaa, sizeof(iaa), pRI, mSlotId);
1927
1928        memsetAndFreeStrings(4, iaa.apn, iaa.protocol, iaa.username, iaa.password);
1929    } else {
1930        RIL_InitialAttachApn_v15 iaa = {};
1931
1932        if (!copyHidlStringToRil(&iaa.apn, dataProfileInfo.apn, pRI)) {
1933            return Void();
1934        }
1935        if (!copyHidlStringToRil(&iaa.protocol, dataProfileInfo.protocol, pRI)) {
1936            memsetAndFreeStrings(1, iaa.apn);
1937            return Void();
1938        }
1939        if (!copyHidlStringToRil(&iaa.roamingProtocol, dataProfileInfo.roamingProtocol, pRI)) {
1940            memsetAndFreeStrings(2, iaa.apn, iaa.protocol);
1941            return Void();
1942        }
1943        iaa.authtype = (int) dataProfileInfo.authType;
1944        if (!copyHidlStringToRil(&iaa.username, dataProfileInfo.user, pRI)) {
1945            memsetAndFreeStrings(3, iaa.apn, iaa.protocol, iaa.roamingProtocol);
1946            return Void();
1947        }
1948        if (!copyHidlStringToRil(&iaa.password, dataProfileInfo.password, pRI)) {
1949            memsetAndFreeStrings(4, iaa.apn, iaa.protocol, iaa.roamingProtocol, iaa.username);
1950            return Void();
1951        }
1952        iaa.supportedTypesBitmask = dataProfileInfo.supportedApnTypesBitmap;
1953        iaa.bearerBitmask = dataProfileInfo.bearerBitmap;
1954        iaa.modemCognitive = BOOL_TO_INT(modemCognitive);
1955        iaa.mtu = dataProfileInfo.mtu;
1956
1957        if (!convertMvnoTypeToString(dataProfileInfo.mvnoType, iaa.mvnoType)) {
1958            sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS);
1959            memsetAndFreeStrings(5, iaa.apn, iaa.protocol, iaa.roamingProtocol, iaa.username,
1960                    iaa.password);
1961            return Void();
1962        }
1963
1964        if (!copyHidlStringToRil(&iaa.mvnoMatchData, dataProfileInfo.mvnoMatchData, pRI)) {
1965            memsetAndFreeStrings(5, iaa.apn, iaa.protocol, iaa.roamingProtocol, iaa.username,
1966                    iaa.password);
1967            return Void();
1968        }
1969
1970        CALL_ONREQUEST(RIL_REQUEST_SET_INITIAL_ATTACH_APN, &iaa, sizeof(iaa), pRI, mSlotId);
1971
1972        memsetAndFreeStrings(6, iaa.apn, iaa.protocol, iaa.roamingProtocol, iaa.username,
1973                iaa.password, iaa.mvnoMatchData);
1974    }
1975
1976    return Void();
1977}
1978
1979Return<void> RadioImpl::getImsRegistrationState(int32_t serial) {
1980#if VDBG
1981    RLOGD("getImsRegistrationState: serial %d", serial);
1982#endif
1983    dispatchVoid(serial, mSlotId, RIL_REQUEST_IMS_REGISTRATION_STATE);
1984    return Void();
1985}
1986
1987bool dispatchImsGsmSms(const ImsSmsMessage& message, RequestInfo *pRI) {
1988    RIL_IMS_SMS_Message rism = {};
1989    char **pStrings;
1990    int countStrings = 2;
1991    int dataLen = sizeof(char *) * countStrings;
1992
1993    rism.tech = RADIO_TECH_3GPP;
1994    rism.retry = BOOL_TO_INT(message.retry);
1995    rism.messageRef = message.messageRef;
1996
1997    if (message.gsmMessage.size() != 1) {
1998        RLOGE("dispatchImsGsmSms: Invalid len %s", requestToString(pRI->pCI->requestNumber));
1999        sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS);
2000        return false;
2001    }
2002
2003    pStrings = (char **)calloc(countStrings, sizeof(char *));
2004    if (pStrings == NULL) {
2005        RLOGE("dispatchImsGsmSms: Memory allocation failed for request %s",
2006                requestToString(pRI->pCI->requestNumber));
2007        sendErrorResponse(pRI, RIL_E_NO_MEMORY);
2008        return false;
2009    }
2010
2011    if (!copyHidlStringToRil(&pStrings[0], message.gsmMessage[0].smscPdu, pRI)) {
2012#ifdef MEMSET_FREED
2013        memset(pStrings, 0, datalen);
2014#endif
2015        free(pStrings);
2016        return false;
2017    }
2018
2019    if (!copyHidlStringToRil(&pStrings[1], message.gsmMessage[0].pdu, pRI)) {
2020        memsetAndFreeStrings(1, pStrings[0]);
2021#ifdef MEMSET_FREED
2022        memset(pStrings, 0, datalen);
2023#endif
2024        free(pStrings);
2025        return false;
2026    }
2027
2028    rism.message.gsmMessage = pStrings;
2029    CALL_ONREQUEST(pRI->pCI->requestNumber, &rism, sizeof(RIL_RadioTechnologyFamily) +
2030            sizeof(uint8_t) + sizeof(int32_t) + dataLen, pRI, pRI->socket_id);
2031
2032    for (int i = 0 ; i < countStrings ; i++) {
2033        memsetAndFreeStrings(1, pStrings[i]);
2034    }
2035
2036#ifdef MEMSET_FREED
2037    memset(pStrings, 0, datalen);
2038#endif
2039    free(pStrings);
2040
2041    return true;
2042}
2043
2044bool dispatchImsCdmaSms(const ImsSmsMessage& message, RequestInfo *pRI) {
2045    RIL_IMS_SMS_Message rism = {};
2046    RIL_CDMA_SMS_Message rcsm = {};
2047
2048    if (message.cdmaMessage.size() != 1) {
2049        RLOGE("dispatchImsCdmaSms: Invalid len %s", requestToString(pRI->pCI->requestNumber));
2050        sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS);
2051        return false;
2052    }
2053
2054    rism.tech = RADIO_TECH_3GPP2;
2055    rism.retry = BOOL_TO_INT(message.retry);
2056    rism.messageRef = message.messageRef;
2057    rism.message.cdmaMessage = &rcsm;
2058
2059    constructCdmaSms(rcsm, message.cdmaMessage[0]);
2060
2061    CALL_ONREQUEST(pRI->pCI->requestNumber, &rism, sizeof(RIL_RadioTechnologyFamily) +
2062            sizeof(uint8_t) + sizeof(int32_t) + sizeof(rcsm), pRI, pRI->socket_id);
2063
2064    return true;
2065}
2066
2067Return<void> RadioImpl::sendImsSms(int32_t serial, const ImsSmsMessage& message) {
2068#if VDBG
2069    RLOGD("sendImsSms: serial %d", serial);
2070#endif
2071    RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_IMS_SEND_SMS);
2072    if (pRI == NULL) {
2073        return Void();
2074    }
2075
2076    RIL_RadioTechnologyFamily format = (RIL_RadioTechnologyFamily) message.tech;
2077
2078    if (RADIO_TECH_3GPP == format) {
2079        dispatchImsGsmSms(message, pRI);
2080    } else if (RADIO_TECH_3GPP2 == format) {
2081        dispatchImsCdmaSms(message, pRI);
2082    } else {
2083        RLOGE("sendImsSms: Invalid radio tech %s",
2084                requestToString(pRI->pCI->requestNumber));
2085        sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS);
2086    }
2087    return Void();
2088}
2089
2090Return<void> RadioImpl::iccTransmitApduBasicChannel(int32_t serial, const SimApdu& message) {
2091#if VDBG
2092    RLOGD("iccTransmitApduBasicChannel: serial %d", serial);
2093#endif
2094    dispatchIccApdu(serial, mSlotId, RIL_REQUEST_SIM_TRANSMIT_APDU_BASIC, message);
2095    return Void();
2096}
2097
2098Return<void> RadioImpl::iccOpenLogicalChannel(int32_t serial, const hidl_string& aid, int32_t p2) {
2099#if VDBG
2100    RLOGD("iccOpenLogicalChannel: serial %d", serial);
2101#endif
2102    if (s_vendorFunctions->version < 15) {
2103        dispatchString(serial, mSlotId, RIL_REQUEST_SIM_OPEN_CHANNEL, aid.c_str());
2104    } else {
2105        RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_SIM_OPEN_CHANNEL);
2106        if (pRI == NULL) {
2107            return Void();
2108        }
2109
2110        RIL_OpenChannelParams params = {};
2111
2112        params.p2 = p2;
2113
2114        if (!copyHidlStringToRil(&params.aidPtr, aid, pRI)) {
2115            return Void();
2116        }
2117
2118        CALL_ONREQUEST(pRI->pCI->requestNumber, &params, sizeof(params), pRI, mSlotId);
2119
2120        memsetAndFreeStrings(1, params.aidPtr);
2121    }
2122    return Void();
2123}
2124
2125Return<void> RadioImpl::iccCloseLogicalChannel(int32_t serial, int32_t channelId) {
2126#if VDBG
2127    RLOGD("iccCloseLogicalChannel: serial %d", serial);
2128#endif
2129    dispatchInts(serial, mSlotId, RIL_REQUEST_SIM_CLOSE_CHANNEL, 1, channelId);
2130    return Void();
2131}
2132
2133Return<void> RadioImpl::iccTransmitApduLogicalChannel(int32_t serial, const SimApdu& message) {
2134#if VDBG
2135    RLOGD("iccTransmitApduLogicalChannel: serial %d", serial);
2136#endif
2137    dispatchIccApdu(serial, mSlotId, RIL_REQUEST_SIM_TRANSMIT_APDU_CHANNEL, message);
2138    return Void();
2139}
2140
2141Return<void> RadioImpl::nvReadItem(int32_t serial, NvItem itemId) {
2142#if VDBG
2143    RLOGD("nvReadItem: serial %d", serial);
2144#endif
2145    RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_NV_READ_ITEM);
2146    if (pRI == NULL) {
2147        return Void();
2148    }
2149
2150    RIL_NV_ReadItem nvri = {};
2151    nvri.itemID = (RIL_NV_Item) itemId;
2152
2153    CALL_ONREQUEST(pRI->pCI->requestNumber, &nvri, sizeof(nvri), pRI, mSlotId);
2154    return Void();
2155}
2156
2157Return<void> RadioImpl::nvWriteItem(int32_t serial, const NvWriteItem& item) {
2158#if VDBG
2159    RLOGD("nvWriteItem: serial %d", serial);
2160#endif
2161    RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_NV_WRITE_ITEM);
2162    if (pRI == NULL) {
2163        return Void();
2164    }
2165
2166    RIL_NV_WriteItem nvwi = {};
2167
2168    nvwi.itemID = (RIL_NV_Item) item.itemId;
2169
2170    if (!copyHidlStringToRil(&nvwi.value, item.value, pRI)) {
2171        return Void();
2172    }
2173
2174    CALL_ONREQUEST(pRI->pCI->requestNumber, &nvwi, sizeof(nvwi), pRI, mSlotId);
2175
2176    memsetAndFreeStrings(1, nvwi.value);
2177    return Void();
2178}
2179
2180Return<void> RadioImpl::nvWriteCdmaPrl(int32_t serial, const hidl_vec<uint8_t>& prl) {
2181#if VDBG
2182    RLOGD("nvWriteCdmaPrl: serial %d", serial);
2183#endif
2184    dispatchRaw(serial, mSlotId, RIL_REQUEST_NV_WRITE_CDMA_PRL, prl);
2185    return Void();
2186}
2187
2188Return<void> RadioImpl::nvResetConfig(int32_t serial, ResetNvType resetType) {
2189    int rilResetType = -1;
2190#if VDBG
2191    RLOGD("nvResetConfig: serial %d", serial);
2192#endif
2193    /* Convert ResetNvType to RIL.h values
2194     * RIL_REQUEST_NV_RESET_CONFIG
2195     * 1 - reload all NV items
2196     * 2 - erase NV reset (SCRTN)
2197     * 3 - factory reset (RTN)
2198     */
2199    switch(resetType) {
2200      case ResetNvType::RELOAD:
2201        rilResetType = 1;
2202        break;
2203      case ResetNvType::ERASE:
2204        rilResetType = 2;
2205        break;
2206      case ResetNvType::FACTORY_RESET:
2207        rilResetType = 3;
2208        break;
2209    }
2210    dispatchInts(serial, mSlotId, RIL_REQUEST_NV_RESET_CONFIG, 1, rilResetType);
2211    return Void();
2212}
2213
2214Return<void> RadioImpl::setUiccSubscription(int32_t serial, const SelectUiccSub& uiccSub) {
2215#if VDBG
2216    RLOGD("setUiccSubscription: serial %d", serial);
2217#endif
2218    RequestInfo *pRI = android::addRequestToList(serial, mSlotId,
2219            RIL_REQUEST_SET_UICC_SUBSCRIPTION);
2220    if (pRI == NULL) {
2221        return Void();
2222    }
2223
2224    RIL_SelectUiccSub rilUiccSub = {};
2225
2226    rilUiccSub.slot = uiccSub.slot;
2227    rilUiccSub.app_index = uiccSub.appIndex;
2228    rilUiccSub.sub_type = (RIL_SubscriptionType) uiccSub.subType;
2229    rilUiccSub.act_status = (RIL_UiccSubActStatus) uiccSub.actStatus;
2230
2231    CALL_ONREQUEST(pRI->pCI->requestNumber, &rilUiccSub, sizeof(rilUiccSub), pRI, mSlotId);
2232    return Void();
2233}
2234
2235Return<void> RadioImpl::setDataAllowed(int32_t serial, bool allow) {
2236#if VDBG
2237    RLOGD("setDataAllowed: serial %d", serial);
2238#endif
2239    dispatchInts(serial, mSlotId, RIL_REQUEST_ALLOW_DATA, 1, BOOL_TO_INT(allow));
2240    return Void();
2241}
2242
2243Return<void> RadioImpl::getHardwareConfig(int32_t serial) {
2244#if VDBG
2245    RLOGD("getHardwareConfig: serial %d", serial);
2246#endif
2247    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_HARDWARE_CONFIG);
2248    return Void();
2249}
2250
2251Return<void> RadioImpl::requestIccSimAuthentication(int32_t serial, int32_t authContext,
2252        const hidl_string& authData, const hidl_string& aid) {
2253#if VDBG
2254    RLOGD("requestIccSimAuthentication: serial %d", serial);
2255#endif
2256    RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_SIM_AUTHENTICATION);
2257    if (pRI == NULL) {
2258        return Void();
2259    }
2260
2261    RIL_SimAuthentication pf = {};
2262
2263    pf.authContext = authContext;
2264
2265    int len;
2266    if (!copyHidlStringToRil(&pf.authData, authData, pRI)) {
2267        return Void();
2268    }
2269
2270    if (!copyHidlStringToRil(&pf.aid, aid, pRI)) {
2271        memsetAndFreeStrings(1, pf.authData);
2272        return Void();
2273    }
2274
2275    CALL_ONREQUEST(pRI->pCI->requestNumber, &pf, sizeof(pf), pRI, mSlotId);
2276
2277    memsetAndFreeStrings(2, pf.authData, pf.aid);
2278    return Void();
2279}
2280
2281/**
2282 * @param numProfiles number of data profile
2283 * @param dataProfiles the pointer to the actual data profiles. The acceptable type is
2284          RIL_DataProfileInfo or RIL_DataProfileInfo_v15.
2285 * @param dataProfilePtrs the pointer to the pointers that point to each data profile structure
2286 * @param numfields number of string-type member in the data profile structure
2287 * @param ... the variadic parameters are pointers to each string-type member
2288 **/
2289template <typename T>
2290void freeSetDataProfileData(int numProfiles, T *dataProfiles, T **dataProfilePtrs,
2291                            int numfields, ...) {
2292    va_list args;
2293    va_start(args, numfields);
2294
2295    // Iterate through each string-type field that need to be free.
2296    for (int i = 0; i < numfields; i++) {
2297        // Iterate through each data profile and free that specific string-type field.
2298        // The type 'char *T::*' is a type of pointer to a 'char *' member inside T structure.
2299        char *T::*ptr = va_arg(args, char *T::*);
2300        for (int j = 0; j < numProfiles; j++) {
2301            memsetAndFreeStrings(1, dataProfiles[j].*ptr);
2302        }
2303    }
2304
2305    va_end(args);
2306
2307#ifdef MEMSET_FREED
2308    memset(dataProfiles, 0, numProfiles * sizeof(T));
2309    memset(dataProfilePtrs, 0, numProfiles * sizeof(T *));
2310#endif
2311    free(dataProfiles);
2312    free(dataProfilePtrs);
2313}
2314
2315Return<void> RadioImpl::setDataProfile(int32_t serial, const hidl_vec<DataProfileInfo>& profiles,
2316                                       bool isRoaming) {
2317#if VDBG
2318    RLOGD("setDataProfile: serial %d", serial);
2319#endif
2320    RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_SET_DATA_PROFILE);
2321    if (pRI == NULL) {
2322        return Void();
2323    }
2324
2325    size_t num = profiles.size();
2326    bool success = false;
2327
2328    if (s_vendorFunctions->version <= 14) {
2329
2330        RIL_DataProfileInfo *dataProfiles =
2331            (RIL_DataProfileInfo *) calloc(num, sizeof(RIL_DataProfileInfo));
2332
2333        if (dataProfiles == NULL) {
2334            RLOGE("Memory allocation failed for request %s",
2335                    requestToString(pRI->pCI->requestNumber));
2336            sendErrorResponse(pRI, RIL_E_NO_MEMORY);
2337            return Void();
2338        }
2339
2340        RIL_DataProfileInfo **dataProfilePtrs =
2341            (RIL_DataProfileInfo **) calloc(num, sizeof(RIL_DataProfileInfo *));
2342        if (dataProfilePtrs == NULL) {
2343            RLOGE("Memory allocation failed for request %s",
2344                    requestToString(pRI->pCI->requestNumber));
2345            free(dataProfiles);
2346            sendErrorResponse(pRI, RIL_E_NO_MEMORY);
2347            return Void();
2348        }
2349
2350        for (size_t i = 0; i < num; i++) {
2351            dataProfilePtrs[i] = &dataProfiles[i];
2352
2353            success = copyHidlStringToRil(&dataProfiles[i].apn, profiles[i].apn, pRI);
2354
2355            const hidl_string &protocol =
2356                    (isRoaming ? profiles[i].roamingProtocol : profiles[i].protocol);
2357
2358            if (success && !copyHidlStringToRil(&dataProfiles[i].protocol, protocol, pRI)) {
2359                success = false;
2360            }
2361
2362            if (success && !copyHidlStringToRil(&dataProfiles[i].user, profiles[i].user, pRI)) {
2363                success = false;
2364            }
2365            if (success && !copyHidlStringToRil(&dataProfiles[i].password, profiles[i].password,
2366                    pRI)) {
2367                success = false;
2368            }
2369
2370            if (!success) {
2371                freeSetDataProfileData(num, dataProfiles, dataProfilePtrs, 4,
2372                    &RIL_DataProfileInfo::apn, &RIL_DataProfileInfo::protocol,
2373                    &RIL_DataProfileInfo::user, &RIL_DataProfileInfo::password);
2374                return Void();
2375            }
2376
2377            dataProfiles[i].profileId = (RIL_DataProfile) profiles[i].profileId;
2378            dataProfiles[i].authType = (int) profiles[i].authType;
2379            dataProfiles[i].type = (int) profiles[i].type;
2380            dataProfiles[i].maxConnsTime = profiles[i].maxConnsTime;
2381            dataProfiles[i].maxConns = profiles[i].maxConns;
2382            dataProfiles[i].waitTime = profiles[i].waitTime;
2383            dataProfiles[i].enabled = BOOL_TO_INT(profiles[i].enabled);
2384        }
2385
2386        CALL_ONREQUEST(RIL_REQUEST_SET_DATA_PROFILE, dataProfilePtrs,
2387                num * sizeof(RIL_DataProfileInfo *), pRI, mSlotId);
2388
2389        freeSetDataProfileData(num, dataProfiles, dataProfilePtrs, 4,
2390                &RIL_DataProfileInfo::apn, &RIL_DataProfileInfo::protocol,
2391                &RIL_DataProfileInfo::user, &RIL_DataProfileInfo::password);
2392    } else {
2393        RIL_DataProfileInfo_v15 *dataProfiles =
2394            (RIL_DataProfileInfo_v15 *) calloc(num, sizeof(RIL_DataProfileInfo_v15));
2395
2396        if (dataProfiles == NULL) {
2397            RLOGE("Memory allocation failed for request %s",
2398                    requestToString(pRI->pCI->requestNumber));
2399            sendErrorResponse(pRI, RIL_E_NO_MEMORY);
2400            return Void();
2401        }
2402
2403        RIL_DataProfileInfo_v15 **dataProfilePtrs =
2404            (RIL_DataProfileInfo_v15 **) calloc(num, sizeof(RIL_DataProfileInfo_v15 *));
2405        if (dataProfilePtrs == NULL) {
2406            RLOGE("Memory allocation failed for request %s",
2407                    requestToString(pRI->pCI->requestNumber));
2408            free(dataProfiles);
2409            sendErrorResponse(pRI, RIL_E_NO_MEMORY);
2410            return Void();
2411        }
2412
2413        for (size_t i = 0; i < num; i++) {
2414            dataProfilePtrs[i] = &dataProfiles[i];
2415
2416            success = copyHidlStringToRil(&dataProfiles[i].apn, profiles[i].apn, pRI);
2417            if (success && !copyHidlStringToRil(&dataProfiles[i].protocol, profiles[i].protocol,
2418                    pRI)) {
2419                success = false;
2420            }
2421            if (success && !copyHidlStringToRil(&dataProfiles[i].roamingProtocol,
2422                    profiles[i].roamingProtocol, pRI)) {
2423                success = false;
2424            }
2425            if (success && !copyHidlStringToRil(&dataProfiles[i].user, profiles[i].user, pRI)) {
2426                success = false;
2427            }
2428            if (success && !copyHidlStringToRil(&dataProfiles[i].password, profiles[i].password,
2429                    pRI)) {
2430                success = false;
2431            }
2432
2433            if (success && !copyHidlStringToRil(&dataProfiles[i].mvnoMatchData,
2434                    profiles[i].mvnoMatchData, pRI)) {
2435                success = false;
2436            }
2437
2438            if (success && !convertMvnoTypeToString(profiles[i].mvnoType,
2439                    dataProfiles[i].mvnoType)) {
2440                sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS);
2441                success = false;
2442            }
2443
2444            if (!success) {
2445                freeSetDataProfileData(num, dataProfiles, dataProfilePtrs, 6,
2446                    &RIL_DataProfileInfo_v15::apn, &RIL_DataProfileInfo_v15::protocol,
2447                    &RIL_DataProfileInfo_v15::roamingProtocol, &RIL_DataProfileInfo_v15::user,
2448                    &RIL_DataProfileInfo_v15::password, &RIL_DataProfileInfo_v15::mvnoMatchData);
2449                return Void();
2450            }
2451
2452            dataProfiles[i].profileId = (RIL_DataProfile) profiles[i].profileId;
2453            dataProfiles[i].authType = (int) profiles[i].authType;
2454            dataProfiles[i].type = (int) profiles[i].type;
2455            dataProfiles[i].maxConnsTime = profiles[i].maxConnsTime;
2456            dataProfiles[i].maxConns = profiles[i].maxConns;
2457            dataProfiles[i].waitTime = profiles[i].waitTime;
2458            dataProfiles[i].enabled = BOOL_TO_INT(profiles[i].enabled);
2459            dataProfiles[i].supportedTypesBitmask = profiles[i].supportedApnTypesBitmap;
2460            dataProfiles[i].bearerBitmask = profiles[i].bearerBitmap;
2461            dataProfiles[i].mtu = profiles[i].mtu;
2462        }
2463
2464        CALL_ONREQUEST(RIL_REQUEST_SET_DATA_PROFILE, dataProfilePtrs,
2465                num * sizeof(RIL_DataProfileInfo_v15 *), pRI, mSlotId);
2466
2467        freeSetDataProfileData(num, dataProfiles, dataProfilePtrs, 6,
2468                &RIL_DataProfileInfo_v15::apn, &RIL_DataProfileInfo_v15::protocol,
2469                &RIL_DataProfileInfo_v15::roamingProtocol, &RIL_DataProfileInfo_v15::user,
2470                &RIL_DataProfileInfo_v15::password, &RIL_DataProfileInfo_v15::mvnoMatchData);
2471    }
2472
2473    return Void();
2474}
2475
2476Return<void> RadioImpl::requestShutdown(int32_t serial) {
2477#if VDBG
2478    RLOGD("requestShutdown: serial %d", serial);
2479#endif
2480    dispatchVoid(serial, mSlotId, RIL_REQUEST_SHUTDOWN);
2481    return Void();
2482}
2483
2484Return<void> RadioImpl::getRadioCapability(int32_t serial) {
2485#if VDBG
2486    RLOGD("getRadioCapability: serial %d", serial);
2487#endif
2488    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_RADIO_CAPABILITY);
2489    return Void();
2490}
2491
2492Return<void> RadioImpl::setRadioCapability(int32_t serial, const RadioCapability& rc) {
2493#if VDBG
2494    RLOGD("setRadioCapability: serial %d", serial);
2495#endif
2496    RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_SET_RADIO_CAPABILITY);
2497    if (pRI == NULL) {
2498        return Void();
2499    }
2500
2501    RIL_RadioCapability rilRc = {};
2502
2503    // TODO : set rilRc.version using HIDL version ?
2504    rilRc.session = rc.session;
2505    rilRc.phase = (int) rc.phase;
2506    rilRc.rat = (int) rc.raf;
2507    rilRc.status = (int) rc.status;
2508    strncpy(rilRc.logicalModemUuid, rc.logicalModemUuid.c_str(), MAX_UUID_LENGTH);
2509
2510    CALL_ONREQUEST(pRI->pCI->requestNumber, &rilRc, sizeof(rilRc), pRI, mSlotId);
2511
2512    return Void();
2513}
2514
2515Return<void> RadioImpl::startLceService(int32_t serial, int32_t reportInterval, bool pullMode) {
2516#if VDBG
2517    RLOGD("startLceService: serial %d", serial);
2518#endif
2519    dispatchInts(serial, mSlotId, RIL_REQUEST_START_LCE, 2, reportInterval,
2520            BOOL_TO_INT(pullMode));
2521    return Void();
2522}
2523
2524Return<void> RadioImpl::stopLceService(int32_t serial) {
2525#if VDBG
2526    RLOGD("stopLceService: serial %d", serial);
2527#endif
2528    dispatchVoid(serial, mSlotId, RIL_REQUEST_STOP_LCE);
2529    return Void();
2530}
2531
2532Return<void> RadioImpl::pullLceData(int32_t serial) {
2533#if VDBG
2534    RLOGD("pullLceData: serial %d", serial);
2535#endif
2536    dispatchVoid(serial, mSlotId, RIL_REQUEST_PULL_LCEDATA);
2537    return Void();
2538}
2539
2540Return<void> RadioImpl::getModemActivityInfo(int32_t serial) {
2541#if VDBG
2542    RLOGD("getModemActivityInfo: serial %d", serial);
2543#endif
2544    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_ACTIVITY_INFO);
2545    return Void();
2546}
2547
2548Return<void> RadioImpl::setAllowedCarriers(int32_t serial, bool allAllowed,
2549                                           const CarrierRestrictions& carriers) {
2550#if VDBG
2551    RLOGD("setAllowedCarriers: serial %d", serial);
2552#endif
2553    RequestInfo *pRI = android::addRequestToList(serial, mSlotId,
2554            RIL_REQUEST_SET_CARRIER_RESTRICTIONS);
2555    if (pRI == NULL) {
2556        return Void();
2557    }
2558
2559    RIL_CarrierRestrictions cr = {};
2560    RIL_Carrier *allowedCarriers = NULL;
2561    RIL_Carrier *excludedCarriers = NULL;
2562
2563    cr.len_allowed_carriers = carriers.allowedCarriers.size();
2564    allowedCarriers = (RIL_Carrier *)calloc(cr.len_allowed_carriers, sizeof(RIL_Carrier));
2565    if (allowedCarriers == NULL) {
2566        RLOGE("setAllowedCarriers: Memory allocation failed for request %s",
2567                requestToString(pRI->pCI->requestNumber));
2568        sendErrorResponse(pRI, RIL_E_NO_MEMORY);
2569        return Void();
2570    }
2571    cr.allowed_carriers = allowedCarriers;
2572
2573    cr.len_excluded_carriers = carriers.excludedCarriers.size();
2574    excludedCarriers = (RIL_Carrier *)calloc(cr.len_excluded_carriers, sizeof(RIL_Carrier));
2575    if (excludedCarriers == NULL) {
2576        RLOGE("setAllowedCarriers: Memory allocation failed for request %s",
2577                requestToString(pRI->pCI->requestNumber));
2578        sendErrorResponse(pRI, RIL_E_NO_MEMORY);
2579#ifdef MEMSET_FREED
2580        memset(allowedCarriers, 0, cr.len_allowed_carriers * sizeof(RIL_Carrier));
2581#endif
2582        free(allowedCarriers);
2583        return Void();
2584    }
2585    cr.excluded_carriers = excludedCarriers;
2586
2587    for (int i = 0; i < cr.len_allowed_carriers; i++) {
2588        allowedCarriers[i].mcc = carriers.allowedCarriers[i].mcc.c_str();
2589        allowedCarriers[i].mnc = carriers.allowedCarriers[i].mnc.c_str();
2590        allowedCarriers[i].match_type = (RIL_CarrierMatchType) carriers.allowedCarriers[i].matchType;
2591        allowedCarriers[i].match_data = carriers.allowedCarriers[i].matchData.c_str();
2592    }
2593
2594    for (int i = 0; i < cr.len_excluded_carriers; i++) {
2595        excludedCarriers[i].mcc = carriers.excludedCarriers[i].mcc.c_str();
2596        excludedCarriers[i].mnc = carriers.excludedCarriers[i].mnc.c_str();
2597        excludedCarriers[i].match_type =
2598                (RIL_CarrierMatchType) carriers.excludedCarriers[i].matchType;
2599        excludedCarriers[i].match_data = carriers.excludedCarriers[i].matchData.c_str();
2600    }
2601
2602    CALL_ONREQUEST(pRI->pCI->requestNumber, &cr, sizeof(RIL_CarrierRestrictions), pRI, mSlotId);
2603
2604#ifdef MEMSET_FREED
2605    memset(allowedCarriers, 0, cr.len_allowed_carriers * sizeof(RIL_Carrier));
2606    memset(excludedCarriers, 0, cr.len_excluded_carriers * sizeof(RIL_Carrier));
2607#endif
2608    free(allowedCarriers);
2609    free(excludedCarriers);
2610    return Void();
2611}
2612
2613Return<void> RadioImpl::getAllowedCarriers(int32_t serial) {
2614#if VDBG
2615    RLOGD("getAllowedCarriers: serial %d", serial);
2616#endif
2617    dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_CARRIER_RESTRICTIONS);
2618    return Void();
2619}
2620
2621Return<void> RadioImpl::sendDeviceState(int32_t serial, DeviceStateType deviceStateType,
2622                                        bool state) {
2623#if VDBG
2624    RLOGD("sendDeviceState: serial %d", serial);
2625#endif
2626    if (s_vendorFunctions->version < 15) {
2627        if (deviceStateType ==  DeviceStateType::LOW_DATA_EXPECTED) {
2628            RLOGD("sendDeviceState: calling screen state %d", BOOL_TO_INT(!state));
2629            dispatchInts(serial, mSlotId, RIL_REQUEST_SCREEN_STATE, 1, BOOL_TO_INT(!state));
2630        } else {
2631            RequestInfo *pRI = android::addRequestToList(serial, mSlotId,
2632                    RIL_REQUEST_SEND_DEVICE_STATE);
2633            sendErrorResponse(pRI, RIL_E_REQUEST_NOT_SUPPORTED);
2634        }
2635        return Void();
2636    }
2637    dispatchInts(serial, mSlotId, RIL_REQUEST_SEND_DEVICE_STATE, 2, (int) deviceStateType,
2638            BOOL_TO_INT(state));
2639    return Void();
2640}
2641
2642Return<void> RadioImpl::setIndicationFilter(int32_t serial, int32_t indicationFilter) {
2643#if VDBG
2644    RLOGD("setIndicationFilter: serial %d", serial);
2645#endif
2646    if (s_vendorFunctions->version < 15) {
2647        RequestInfo *pRI = android::addRequestToList(serial, mSlotId,
2648                RIL_REQUEST_SET_UNSOLICITED_RESPONSE_FILTER);
2649        sendErrorResponse(pRI, RIL_E_REQUEST_NOT_SUPPORTED);
2650        return Void();
2651    }
2652    dispatchInts(serial, mSlotId, RIL_REQUEST_SET_UNSOLICITED_RESPONSE_FILTER, 1, indicationFilter);
2653    return Void();
2654}
2655
2656Return<void> RadioImpl::setSimCardPower(int32_t serial, bool powerUp) {
2657#if VDBG
2658    RLOGD("setSimCardPower: serial %d", serial);
2659#endif
2660    dispatchInts(serial, mSlotId, RIL_REQUEST_SET_SIM_CARD_POWER, 1, BOOL_TO_INT(powerUp));
2661    return Void();
2662}
2663
2664Return<void> RadioImpl::responseAcknowledgement() {
2665    android::releaseWakeLock();
2666    return Void();
2667}
2668
2669Return<void> OemHookImpl::setResponseFunctions(
2670        const ::android::sp<IOemHookResponse>& oemHookResponseParam,
2671        const ::android::sp<IOemHookIndication>& oemHookIndicationParam) {
2672#if VDBG
2673    RLOGD("OemHookImpl::setResponseFunctions");
2674#endif
2675
2676    pthread_rwlock_t *radioServiceRwlockPtr = radio::getRadioServiceRwlock(mSlotId);
2677    int ret = pthread_rwlock_wrlock(radioServiceRwlockPtr);
2678    assert(ret == 0);
2679
2680    mOemHookResponse = oemHookResponseParam;
2681    mOemHookIndication = oemHookIndicationParam;
2682    mCounterOemHook[mSlotId]++;
2683
2684    ret = pthread_rwlock_unlock(radioServiceRwlockPtr);
2685    assert(ret == 0);
2686
2687    return Void();
2688}
2689
2690Return<void> OemHookImpl::sendRequestRaw(int32_t serial, const hidl_vec<uint8_t>& data) {
2691#if VDBG
2692    RLOGD("OemHookImpl::sendRequestRaw: serial %d", serial);
2693#endif
2694    dispatchRaw(serial, mSlotId, RIL_REQUEST_OEM_HOOK_RAW, data);
2695    return Void();
2696}
2697
2698Return<void> OemHookImpl::sendRequestStrings(int32_t serial,
2699        const hidl_vec<hidl_string>& data) {
2700#if VDBG
2701    RLOGD("OemHookImpl::sendRequestStrings: serial %d", serial);
2702#endif
2703    dispatchStrings(serial, mSlotId, RIL_REQUEST_OEM_HOOK_STRINGS, data);
2704    return Void();
2705}
2706
2707/***************************************************************************************************
2708 * RESPONSE FUNCTIONS
2709 * Functions above are used for requests going from framework to vendor code. The ones below are
2710 * responses for those requests coming back from the vendor code.
2711 **************************************************************************************************/
2712
2713void radio::acknowledgeRequest(int slotId, int serial) {
2714    if (radioService[slotId]->mRadioResponse != NULL) {
2715        Return<void> retStatus = radioService[slotId]->mRadioResponse->acknowledgeRequest(serial);
2716        radioService[slotId]->checkReturnStatus(retStatus);
2717    } else {
2718        RLOGE("acknowledgeRequest: radioService[%d]->mRadioResponse == NULL", slotId);
2719    }
2720}
2721
2722void populateResponseInfo(RadioResponseInfo& responseInfo, int serial, int responseType,
2723                         RIL_Errno e) {
2724    responseInfo.serial = serial;
2725    switch (responseType) {
2726        case RESPONSE_SOLICITED:
2727            responseInfo.type = RadioResponseType::SOLICITED;
2728            break;
2729        case RESPONSE_SOLICITED_ACK_EXP:
2730            responseInfo.type = RadioResponseType::SOLICITED_ACK_EXP;
2731            break;
2732    }
2733    responseInfo.error = (RadioError) e;
2734}
2735
2736int responseIntOrEmpty(RadioResponseInfo& responseInfo, int serial, int responseType, RIL_Errno e,
2737               void *response, size_t responseLen) {
2738    populateResponseInfo(responseInfo, serial, responseType, e);
2739    int ret = -1;
2740
2741    if (response == NULL && responseLen == 0) {
2742        // Earlier RILs did not send a response for some cases although the interface
2743        // expected an integer as response. Do not return error if response is empty. Instead
2744        // Return -1 in those cases to maintain backward compatibility.
2745    } else if (response == NULL || responseLen != sizeof(int)) {
2746        RLOGE("responseIntOrEmpty: Invalid response");
2747        if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
2748    } else {
2749        int *p_int = (int *) response;
2750        ret = p_int[0];
2751    }
2752    return ret;
2753}
2754
2755int responseInt(RadioResponseInfo& responseInfo, int serial, int responseType, RIL_Errno e,
2756               void *response, size_t responseLen) {
2757    populateResponseInfo(responseInfo, serial, responseType, e);
2758    int ret = -1;
2759
2760    if (response == NULL || responseLen != sizeof(int)) {
2761        RLOGE("responseInt: Invalid response");
2762        if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
2763    } else {
2764        int *p_int = (int *) response;
2765        ret = p_int[0];
2766    }
2767    return ret;
2768}
2769
2770int radio::getIccCardStatusResponse(int slotId,
2771                                   int responseType, int serial, RIL_Errno e,
2772                                   void *response, size_t responseLen) {
2773    if (radioService[slotId]->mRadioResponse != NULL) {
2774        RadioResponseInfo responseInfo = {};
2775        populateResponseInfo(responseInfo, serial, responseType, e);
2776        CardStatus cardStatus = {};
2777        if (response == NULL || responseLen != sizeof(RIL_CardStatus_v6)) {
2778            RLOGE("getIccCardStatusResponse: Invalid response");
2779            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
2780        } else {
2781            RIL_CardStatus_v6 *p_cur = ((RIL_CardStatus_v6 *) response);
2782            cardStatus.cardState = (CardState) p_cur->card_state;
2783            cardStatus.universalPinState = (PinState) p_cur->universal_pin_state;
2784            cardStatus.gsmUmtsSubscriptionAppIndex = p_cur->gsm_umts_subscription_app_index;
2785            cardStatus.cdmaSubscriptionAppIndex = p_cur->cdma_subscription_app_index;
2786            cardStatus.imsSubscriptionAppIndex = p_cur->ims_subscription_app_index;
2787
2788            RIL_AppStatus *rilAppStatus = p_cur->applications;
2789            cardStatus.applications.resize(p_cur->num_applications);
2790            AppStatus *appStatus = cardStatus.applications.data();
2791#if VDBG
2792            RLOGD("getIccCardStatusResponse: num_applications %d", p_cur->num_applications);
2793#endif
2794            for (int i = 0; i < p_cur->num_applications; i++) {
2795                appStatus[i].appType = (AppType) rilAppStatus[i].app_type;
2796                appStatus[i].appState = (AppState) rilAppStatus[i].app_state;
2797                appStatus[i].persoSubstate = (PersoSubstate) rilAppStatus[i].perso_substate;
2798                appStatus[i].aidPtr = convertCharPtrToHidlString(rilAppStatus[i].aid_ptr);
2799                appStatus[i].appLabelPtr = convertCharPtrToHidlString(
2800                        rilAppStatus[i].app_label_ptr);
2801                appStatus[i].pin1Replaced = rilAppStatus[i].pin1_replaced;
2802                appStatus[i].pin1 = (PinState) rilAppStatus[i].pin1;
2803                appStatus[i].pin2 = (PinState) rilAppStatus[i].pin2;
2804            }
2805        }
2806
2807        Return<void> retStatus = radioService[slotId]->mRadioResponse->
2808                getIccCardStatusResponse(responseInfo, cardStatus);
2809        radioService[slotId]->checkReturnStatus(retStatus);
2810    } else {
2811        RLOGE("getIccCardStatusResponse: radioService[%d]->mRadioResponse == NULL", slotId);
2812    }
2813
2814    return 0;
2815}
2816
2817int radio::supplyIccPinForAppResponse(int slotId,
2818                                     int responseType, int serial, RIL_Errno e,
2819                                     void *response, size_t responseLen) {
2820#if VDBG
2821    RLOGD("supplyIccPinForAppResponse: serial %d", serial);
2822#endif
2823
2824    if (radioService[slotId]->mRadioResponse != NULL) {
2825        RadioResponseInfo responseInfo = {};
2826        int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen);
2827        Return<void> retStatus = radioService[slotId]->mRadioResponse->
2828                supplyIccPinForAppResponse(responseInfo, ret);
2829        RLOGE("supplyIccPinForAppResponse: amit ret %d", ret);
2830        radioService[slotId]->checkReturnStatus(retStatus);
2831    } else {
2832        RLOGE("supplyIccPinForAppResponse: radioService[%d]->mRadioResponse == NULL",
2833                slotId);
2834    }
2835
2836    return 0;
2837}
2838
2839int radio::supplyIccPukForAppResponse(int slotId,
2840                                     int responseType, int serial, RIL_Errno e,
2841                                     void *response, size_t responseLen) {
2842#if VDBG
2843    RLOGD("supplyIccPukForAppResponse: serial %d", serial);
2844#endif
2845
2846    if (radioService[slotId]->mRadioResponse != NULL) {
2847        RadioResponseInfo responseInfo = {};
2848        int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen);
2849        Return<void> retStatus = radioService[slotId]->mRadioResponse->supplyIccPukForAppResponse(
2850                responseInfo, ret);
2851        radioService[slotId]->checkReturnStatus(retStatus);
2852    } else {
2853        RLOGE("supplyIccPukForAppResponse: radioService[%d]->mRadioResponse == NULL",
2854                slotId);
2855    }
2856
2857    return 0;
2858}
2859
2860int radio::supplyIccPin2ForAppResponse(int slotId,
2861                                      int responseType, int serial, RIL_Errno e,
2862                                      void *response, size_t responseLen) {
2863#if VDBG
2864    RLOGD("supplyIccPin2ForAppResponse: serial %d", serial);
2865#endif
2866
2867    if (radioService[slotId]->mRadioResponse != NULL) {
2868        RadioResponseInfo responseInfo = {};
2869        int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen);
2870        Return<void> retStatus = radioService[slotId]->mRadioResponse->
2871                supplyIccPin2ForAppResponse(responseInfo, ret);
2872        radioService[slotId]->checkReturnStatus(retStatus);
2873    } else {
2874        RLOGE("supplyIccPin2ForAppResponse: radioService[%d]->mRadioResponse == NULL",
2875                slotId);
2876    }
2877
2878    return 0;
2879}
2880
2881int radio::supplyIccPuk2ForAppResponse(int slotId,
2882                                      int responseType, int serial, RIL_Errno e,
2883                                      void *response, size_t responseLen) {
2884#if VDBG
2885    RLOGD("supplyIccPuk2ForAppResponse: serial %d", serial);
2886#endif
2887
2888    if (radioService[slotId]->mRadioResponse != NULL) {
2889        RadioResponseInfo responseInfo = {};
2890        int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen);
2891        Return<void> retStatus = radioService[slotId]->mRadioResponse->
2892                supplyIccPuk2ForAppResponse(responseInfo, ret);
2893        radioService[slotId]->checkReturnStatus(retStatus);
2894    } else {
2895        RLOGE("supplyIccPuk2ForAppResponse: radioService[%d]->mRadioResponse == NULL",
2896                slotId);
2897    }
2898
2899    return 0;
2900}
2901
2902int radio::changeIccPinForAppResponse(int slotId,
2903                                     int responseType, int serial, RIL_Errno e,
2904                                     void *response, size_t responseLen) {
2905#if VDBG
2906    RLOGD("changeIccPinForAppResponse: serial %d", serial);
2907#endif
2908
2909    if (radioService[slotId]->mRadioResponse != NULL) {
2910        RadioResponseInfo responseInfo = {};
2911        int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen);
2912        Return<void> retStatus = radioService[slotId]->mRadioResponse->
2913                changeIccPinForAppResponse(responseInfo, ret);
2914        radioService[slotId]->checkReturnStatus(retStatus);
2915    } else {
2916        RLOGE("changeIccPinForAppResponse: radioService[%d]->mRadioResponse == NULL",
2917                slotId);
2918    }
2919
2920    return 0;
2921}
2922
2923int radio::changeIccPin2ForAppResponse(int slotId,
2924                                      int responseType, int serial, RIL_Errno e,
2925                                      void *response, size_t responseLen) {
2926#if VDBG
2927    RLOGD("changeIccPin2ForAppResponse: serial %d", serial);
2928#endif
2929
2930    if (radioService[slotId]->mRadioResponse != NULL) {
2931        RadioResponseInfo responseInfo = {};
2932        int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen);
2933        Return<void> retStatus = radioService[slotId]->mRadioResponse->
2934                changeIccPin2ForAppResponse(responseInfo, ret);
2935        radioService[slotId]->checkReturnStatus(retStatus);
2936    } else {
2937        RLOGE("changeIccPin2ForAppResponse: radioService[%d]->mRadioResponse == NULL",
2938                slotId);
2939    }
2940
2941    return 0;
2942}
2943
2944int radio::supplyNetworkDepersonalizationResponse(int slotId,
2945                                                 int responseType, int serial, RIL_Errno e,
2946                                                 void *response, size_t responseLen) {
2947#if VDBG
2948    RLOGD("supplyNetworkDepersonalizationResponse: serial %d", serial);
2949#endif
2950
2951    if (radioService[slotId]->mRadioResponse != NULL) {
2952        RadioResponseInfo responseInfo = {};
2953        int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen);
2954        Return<void> retStatus = radioService[slotId]->mRadioResponse->
2955                supplyNetworkDepersonalizationResponse(responseInfo, ret);
2956        radioService[slotId]->checkReturnStatus(retStatus);
2957    } else {
2958        RLOGE("supplyNetworkDepersonalizationResponse: radioService[%d]->mRadioResponse == "
2959                "NULL", slotId);
2960    }
2961
2962    return 0;
2963}
2964
2965int radio::getCurrentCallsResponse(int slotId,
2966                                  int responseType, int serial, RIL_Errno e,
2967                                  void *response, size_t responseLen) {
2968#if VDBG
2969    RLOGD("getCurrentCallsResponse: serial %d", serial);
2970#endif
2971
2972    if (radioService[slotId]->mRadioResponse != NULL) {
2973        RadioResponseInfo responseInfo = {};
2974        populateResponseInfo(responseInfo, serial, responseType, e);
2975
2976        hidl_vec<Call> calls;
2977        if (response == NULL || (responseLen % sizeof(RIL_Call *)) != 0) {
2978            RLOGE("getCurrentCallsResponse: Invalid response");
2979            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
2980        } else {
2981            int num = responseLen / sizeof(RIL_Call *);
2982            calls.resize(num);
2983
2984            for (int i = 0 ; i < num ; i++) {
2985                RIL_Call *p_cur = ((RIL_Call **) response)[i];
2986                /* each call info */
2987                calls[i].state = (CallState) p_cur->state;
2988                calls[i].index = p_cur->index;
2989                calls[i].toa = p_cur->toa;
2990                calls[i].isMpty = p_cur->isMpty;
2991                calls[i].isMT = p_cur->isMT;
2992                calls[i].als = p_cur->als;
2993                calls[i].isVoice = p_cur->isVoice;
2994                calls[i].isVoicePrivacy = p_cur->isVoicePrivacy;
2995                calls[i].number = convertCharPtrToHidlString(p_cur->number);
2996                calls[i].numberPresentation = (CallPresentation) p_cur->numberPresentation;
2997                calls[i].name = convertCharPtrToHidlString(p_cur->name);
2998                calls[i].namePresentation = (CallPresentation) p_cur->namePresentation;
2999                if (p_cur->uusInfo != NULL && p_cur->uusInfo->uusData != NULL) {
3000                    RIL_UUS_Info *uusInfo = p_cur->uusInfo;
3001                    calls[i].uusInfo[0].uusType = (UusType) uusInfo->uusType;
3002                    calls[i].uusInfo[0].uusDcs = (UusDcs) uusInfo->uusDcs;
3003                    // convert uusInfo->uusData to a null-terminated string
3004                    char *nullTermStr = strndup(uusInfo->uusData, uusInfo->uusLength);
3005                    calls[i].uusInfo[0].uusData = nullTermStr;
3006                    free(nullTermStr);
3007                }
3008            }
3009        }
3010
3011        Return<void> retStatus = radioService[slotId]->mRadioResponse->
3012                getCurrentCallsResponse(responseInfo, calls);
3013        radioService[slotId]->checkReturnStatus(retStatus);
3014    } else {
3015        RLOGE("getCurrentCallsResponse: radioService[%d]->mRadioResponse == NULL", slotId);
3016    }
3017
3018    return 0;
3019}
3020
3021int radio::dialResponse(int slotId,
3022                       int responseType, int serial, RIL_Errno e, void *response,
3023                       size_t responseLen) {
3024#if VDBG
3025    RLOGD("dialResponse: serial %d", serial);
3026#endif
3027
3028    if (radioService[slotId]->mRadioResponse != NULL) {
3029        RadioResponseInfo responseInfo = {};
3030        populateResponseInfo(responseInfo, serial, responseType, e);
3031        Return<void> retStatus = radioService[slotId]->mRadioResponse->dialResponse(responseInfo);
3032        radioService[slotId]->checkReturnStatus(retStatus);
3033    } else {
3034        RLOGE("dialResponse: radioService[%d]->mRadioResponse == NULL", slotId);
3035    }
3036
3037    return 0;
3038}
3039
3040int radio::getIMSIForAppResponse(int slotId,
3041                                int responseType, int serial, RIL_Errno e, void *response,
3042                                size_t responseLen) {
3043#if VDBG
3044    RLOGD("getIMSIForAppResponse: serial %d", serial);
3045#endif
3046
3047    if (radioService[slotId]->mRadioResponse != NULL) {
3048        RadioResponseInfo responseInfo = {};
3049        populateResponseInfo(responseInfo, serial, responseType, e);
3050        Return<void> retStatus = radioService[slotId]->mRadioResponse->getIMSIForAppResponse(
3051                responseInfo, convertCharPtrToHidlString((char *) response));
3052        radioService[slotId]->checkReturnStatus(retStatus);
3053    } else {
3054        RLOGE("getIMSIForAppResponse: radioService[%d]->mRadioResponse == NULL",
3055                slotId);
3056    }
3057
3058    return 0;
3059}
3060
3061int radio::hangupConnectionResponse(int slotId,
3062                                   int responseType, int serial, RIL_Errno e,
3063                                   void *response, size_t responseLen) {
3064#if VDBG
3065    RLOGD("hangupConnectionResponse: serial %d", serial);
3066#endif
3067
3068    if (radioService[slotId]->mRadioResponse != NULL) {
3069        RadioResponseInfo responseInfo = {};
3070        populateResponseInfo(responseInfo, serial, responseType, e);
3071        Return<void> retStatus = radioService[slotId]->mRadioResponse->hangupConnectionResponse(
3072                responseInfo);
3073        radioService[slotId]->checkReturnStatus(retStatus);
3074    } else {
3075        RLOGE("hangupConnectionResponse: radioService[%d]->mRadioResponse == NULL",
3076                slotId);
3077    }
3078
3079    return 0;
3080}
3081
3082int radio::hangupWaitingOrBackgroundResponse(int slotId,
3083                                            int responseType, int serial, RIL_Errno e,
3084                                            void *response, size_t responseLen) {
3085#if VDBG
3086    RLOGD("hangupWaitingOrBackgroundResponse: serial %d", serial);
3087#endif
3088
3089    if (radioService[slotId]->mRadioResponse != NULL) {
3090        RadioResponseInfo responseInfo = {};
3091        populateResponseInfo(responseInfo, serial, responseType, e);
3092        Return<void> retStatus =
3093                radioService[slotId]->mRadioResponse->hangupWaitingOrBackgroundResponse(
3094                responseInfo);
3095        radioService[slotId]->checkReturnStatus(retStatus);
3096    } else {
3097        RLOGE("hangupWaitingOrBackgroundResponse: radioService[%d]->mRadioResponse == NULL",
3098                slotId);
3099    }
3100
3101    return 0;
3102}
3103
3104int radio::hangupForegroundResumeBackgroundResponse(int slotId, int responseType, int serial,
3105                                                    RIL_Errno e, void *response,
3106                                                    size_t responseLen) {
3107#if VDBG
3108    RLOGD("hangupWaitingOrBackgroundResponse: serial %d", serial);
3109#endif
3110
3111    if (radioService[slotId]->mRadioResponse != NULL) {
3112        RadioResponseInfo responseInfo = {};
3113        populateResponseInfo(responseInfo, serial, responseType, e);
3114        Return<void> retStatus =
3115                radioService[slotId]->mRadioResponse->hangupWaitingOrBackgroundResponse(
3116                responseInfo);
3117        radioService[slotId]->checkReturnStatus(retStatus);
3118    } else {
3119        RLOGE("hangupWaitingOrBackgroundResponse: radioService[%d]->mRadioResponse == NULL",
3120                slotId);
3121    }
3122
3123    return 0;
3124}
3125
3126int radio::switchWaitingOrHoldingAndActiveResponse(int slotId, int responseType, int serial,
3127                                                   RIL_Errno e, void *response,
3128                                                   size_t responseLen) {
3129#if VDBG
3130    RLOGD("switchWaitingOrHoldingAndActiveResponse: serial %d", serial);
3131#endif
3132
3133    if (radioService[slotId]->mRadioResponse != NULL) {
3134        RadioResponseInfo responseInfo = {};
3135        populateResponseInfo(responseInfo, serial, responseType, e);
3136        Return<void> retStatus =
3137                radioService[slotId]->mRadioResponse->switchWaitingOrHoldingAndActiveResponse(
3138                responseInfo);
3139        radioService[slotId]->checkReturnStatus(retStatus);
3140    } else {
3141        RLOGE("switchWaitingOrHoldingAndActiveResponse: radioService[%d]->mRadioResponse "
3142                "== NULL", slotId);
3143    }
3144
3145    return 0;
3146}
3147
3148int radio::conferenceResponse(int slotId, int responseType,
3149                             int serial, RIL_Errno e, void *response, size_t responseLen) {
3150#if VDBG
3151    RLOGD("conferenceResponse: serial %d", serial);
3152#endif
3153
3154    if (radioService[slotId]->mRadioResponse != NULL) {
3155        RadioResponseInfo responseInfo = {};
3156        populateResponseInfo(responseInfo, serial, responseType, e);
3157        Return<void> retStatus = radioService[slotId]->mRadioResponse->conferenceResponse(
3158                responseInfo);
3159        radioService[slotId]->checkReturnStatus(retStatus);
3160    } else {
3161        RLOGE("conferenceResponse: radioService[%d]->mRadioResponse == NULL",
3162                slotId);
3163    }
3164
3165    return 0;
3166}
3167
3168int radio::rejectCallResponse(int slotId, int responseType,
3169                             int serial, RIL_Errno e, void *response, size_t responseLen) {
3170#if VDBG
3171    RLOGD("rejectCallResponse: serial %d", serial);
3172#endif
3173
3174    if (radioService[slotId]->mRadioResponse != NULL) {
3175        RadioResponseInfo responseInfo = {};
3176        populateResponseInfo(responseInfo, serial, responseType, e);
3177        Return<void> retStatus = radioService[slotId]->mRadioResponse->rejectCallResponse(
3178                responseInfo);
3179        radioService[slotId]->checkReturnStatus(retStatus);
3180    } else {
3181        RLOGE("rejectCallResponse: radioService[%d]->mRadioResponse == NULL",
3182                slotId);
3183    }
3184
3185    return 0;
3186}
3187
3188int radio::getLastCallFailCauseResponse(int slotId,
3189                                       int responseType, int serial, RIL_Errno e, void *response,
3190                                       size_t responseLen) {
3191#if VDBG
3192    RLOGD("getLastCallFailCauseResponse: serial %d", serial);
3193#endif
3194
3195    if (radioService[slotId]->mRadioResponse != NULL) {
3196        RadioResponseInfo responseInfo = {};
3197        populateResponseInfo(responseInfo, serial, responseType, e);
3198
3199        LastCallFailCauseInfo info = {};
3200        info.vendorCause = hidl_string();
3201        if (response == NULL) {
3202            RLOGE("getCurrentCallsResponse Invalid response: NULL");
3203            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3204        } else if (responseLen == sizeof(int)) {
3205            int *pInt = (int *) response;
3206            info.causeCode = (LastCallFailCause) pInt[0];
3207        } else if (responseLen == sizeof(RIL_LastCallFailCauseInfo))  {
3208            RIL_LastCallFailCauseInfo *pFailCauseInfo = (RIL_LastCallFailCauseInfo *) response;
3209            info.causeCode = (LastCallFailCause) pFailCauseInfo->cause_code;
3210            info.vendorCause = convertCharPtrToHidlString(pFailCauseInfo->vendor_cause);
3211        } else {
3212            RLOGE("getCurrentCallsResponse Invalid response: NULL");
3213            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3214        }
3215
3216        Return<void> retStatus = radioService[slotId]->mRadioResponse->getLastCallFailCauseResponse(
3217                responseInfo, info);
3218        radioService[slotId]->checkReturnStatus(retStatus);
3219    } else {
3220        RLOGE("getLastCallFailCauseResponse: radioService[%d]->mRadioResponse == NULL",
3221                slotId);
3222    }
3223
3224    return 0;
3225}
3226
3227int radio::getSignalStrengthResponse(int slotId,
3228                                     int responseType, int serial, RIL_Errno e,
3229                                     void *response, size_t responseLen) {
3230#if VDBG
3231    RLOGD("getSignalStrengthResponse: serial %d", serial);
3232#endif
3233
3234    if (radioService[slotId]->mRadioResponse != NULL) {
3235        RadioResponseInfo responseInfo = {};
3236        populateResponseInfo(responseInfo, serial, responseType, e);
3237        SignalStrength signalStrength = {};
3238        if (response == NULL || responseLen != sizeof(RIL_SignalStrength_v10)) {
3239            RLOGE("getSignalStrengthResponse: Invalid response");
3240            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3241        } else {
3242            convertRilSignalStrengthToHal(response, responseLen, signalStrength);
3243        }
3244
3245        Return<void> retStatus = radioService[slotId]->mRadioResponse->getSignalStrengthResponse(
3246                responseInfo, signalStrength);
3247        radioService[slotId]->checkReturnStatus(retStatus);
3248    } else {
3249        RLOGE("getSignalStrengthResponse: radioService[%d]->mRadioResponse == NULL",
3250                slotId);
3251    }
3252
3253    return 0;
3254}
3255
3256RIL_CellInfoType getCellInfoTypeRadioTechnology(char *rat) {
3257    if (rat == NULL) {
3258        return RIL_CELL_INFO_TYPE_NONE;
3259    }
3260
3261    int radioTech = atoi(rat);
3262
3263    switch(radioTech) {
3264
3265        case RADIO_TECH_GPRS:
3266        case RADIO_TECH_EDGE:
3267        case RADIO_TECH_GSM: {
3268            return RIL_CELL_INFO_TYPE_GSM;
3269        }
3270
3271        case RADIO_TECH_UMTS:
3272        case RADIO_TECH_HSDPA:
3273        case RADIO_TECH_HSUPA:
3274        case RADIO_TECH_HSPA:
3275        case RADIO_TECH_HSPAP: {
3276            return RIL_CELL_INFO_TYPE_WCDMA;
3277        }
3278
3279        case RADIO_TECH_IS95A:
3280        case RADIO_TECH_IS95B:
3281        case RADIO_TECH_1xRTT:
3282        case RADIO_TECH_EVDO_0:
3283        case RADIO_TECH_EVDO_A:
3284        case RADIO_TECH_EVDO_B:
3285        case RADIO_TECH_EHRPD: {
3286            return RIL_CELL_INFO_TYPE_CDMA;
3287        }
3288
3289        case RADIO_TECH_LTE:
3290        case RADIO_TECH_LTE_CA: {
3291            return RIL_CELL_INFO_TYPE_LTE;
3292        }
3293
3294        case RADIO_TECH_TD_SCDMA: {
3295            return RIL_CELL_INFO_TYPE_TD_SCDMA;
3296        }
3297
3298        default: {
3299            break;
3300        }
3301    }
3302
3303    return RIL_CELL_INFO_TYPE_NONE;
3304
3305}
3306
3307void fillCellIdentityResponse(CellIdentity &cellIdentity, RIL_CellIdentity_v16 &rilCellIdentity) {
3308
3309    cellIdentity.cellIdentityGsm.resize(0);
3310    cellIdentity.cellIdentityWcdma.resize(0);
3311    cellIdentity.cellIdentityCdma.resize(0);
3312    cellIdentity.cellIdentityTdscdma.resize(0);
3313    cellIdentity.cellIdentityLte.resize(0);
3314    cellIdentity.cellInfoType = (CellInfoType)rilCellIdentity.cellInfoType;
3315    switch(rilCellIdentity.cellInfoType) {
3316
3317        case RIL_CELL_INFO_TYPE_GSM: {
3318            cellIdentity.cellIdentityGsm.resize(1);
3319            cellIdentity.cellIdentityGsm[0].mcc =
3320                    std::to_string(rilCellIdentity.cellIdentityGsm.mcc);
3321            cellIdentity.cellIdentityGsm[0].mnc =
3322                    std::to_string(rilCellIdentity.cellIdentityGsm.mnc);
3323            cellIdentity.cellIdentityGsm[0].lac = rilCellIdentity.cellIdentityGsm.lac;
3324            cellIdentity.cellIdentityGsm[0].cid = rilCellIdentity.cellIdentityGsm.cid;
3325            cellIdentity.cellIdentityGsm[0].arfcn = rilCellIdentity.cellIdentityGsm.arfcn;
3326            cellIdentity.cellIdentityGsm[0].bsic = rilCellIdentity.cellIdentityGsm.bsic;
3327            break;
3328        }
3329
3330        case RIL_CELL_INFO_TYPE_WCDMA: {
3331            cellIdentity.cellIdentityWcdma.resize(1);
3332            cellIdentity.cellIdentityWcdma[0].mcc =
3333                    std::to_string(rilCellIdentity.cellIdentityWcdma.mcc);
3334            cellIdentity.cellIdentityWcdma[0].mnc =
3335                    std::to_string(rilCellIdentity.cellIdentityWcdma.mnc);
3336            cellIdentity.cellIdentityWcdma[0].lac = rilCellIdentity.cellIdentityWcdma.lac;
3337            cellIdentity.cellIdentityWcdma[0].cid = rilCellIdentity.cellIdentityWcdma.cid;
3338            cellIdentity.cellIdentityWcdma[0].psc = rilCellIdentity.cellIdentityWcdma.psc;
3339            cellIdentity.cellIdentityWcdma[0].uarfcn = rilCellIdentity.cellIdentityWcdma.uarfcn;
3340            break;
3341        }
3342
3343        case RIL_CELL_INFO_TYPE_CDMA: {
3344            cellIdentity.cellIdentityCdma.resize(1);
3345            cellIdentity.cellIdentityCdma[0].networkId = rilCellIdentity.cellIdentityCdma.networkId;
3346            cellIdentity.cellIdentityCdma[0].systemId = rilCellIdentity.cellIdentityCdma.systemId;
3347            cellIdentity.cellIdentityCdma[0].baseStationId =
3348                    rilCellIdentity.cellIdentityCdma.basestationId;
3349            cellIdentity.cellIdentityCdma[0].longitude = rilCellIdentity.cellIdentityCdma.longitude;
3350            cellIdentity.cellIdentityCdma[0].latitude = rilCellIdentity.cellIdentityCdma.latitude;
3351            break;
3352        }
3353
3354        case RIL_CELL_INFO_TYPE_LTE: {
3355            cellIdentity.cellIdentityLte.resize(1);
3356            cellIdentity.cellIdentityLte[0].mcc =
3357                    std::to_string(rilCellIdentity.cellIdentityLte.mcc);
3358            cellIdentity.cellIdentityLte[0].mnc =
3359                    std::to_string(rilCellIdentity.cellIdentityLte.mnc);
3360            cellIdentity.cellIdentityLte[0].ci = rilCellIdentity.cellIdentityLte.ci;
3361            cellIdentity.cellIdentityLte[0].pci = rilCellIdentity.cellIdentityLte.pci;
3362            cellIdentity.cellIdentityLte[0].tac = rilCellIdentity.cellIdentityLte.tac;
3363            cellIdentity.cellIdentityLte[0].earfcn = rilCellIdentity.cellIdentityLte.earfcn;
3364            break;
3365        }
3366
3367        case RIL_CELL_INFO_TYPE_TD_SCDMA: {
3368            cellIdentity.cellIdentityTdscdma.resize(1);
3369            cellIdentity.cellIdentityTdscdma[0].mcc =
3370                    std::to_string(rilCellIdentity.cellIdentityTdscdma.mcc);
3371            cellIdentity.cellIdentityTdscdma[0].mnc =
3372                    std::to_string(rilCellIdentity.cellIdentityTdscdma.mnc);
3373            cellIdentity.cellIdentityTdscdma[0].lac = rilCellIdentity.cellIdentityTdscdma.lac;
3374            cellIdentity.cellIdentityTdscdma[0].cid = rilCellIdentity.cellIdentityTdscdma.cid;
3375            cellIdentity.cellIdentityTdscdma[0].cpid = rilCellIdentity.cellIdentityTdscdma.cpid;
3376            break;
3377        }
3378
3379        default: {
3380            break;
3381        }
3382    }
3383}
3384
3385int convertResponseStringEntryToInt(char **response, int index, int numStrings) {
3386    if ((response != NULL) &&  (numStrings > index) && (response[index] != NULL)) {
3387        return atoi(response[index]);
3388    }
3389
3390    return -1;
3391}
3392
3393int convertResponseHexStringEntryToInt(char **response, int index, int numStrings) {
3394    const int hexBase = 16;
3395    if ((response != NULL) &&  (numStrings > index) && (response[index] != NULL)) {
3396        return strtol(response[index], NULL, hexBase);
3397    }
3398
3399    return -1;
3400}
3401
3402/* Fill Cell Identity info from Voice Registration State Response.
3403 * This fucntion is applicable only for RIL Version < 15.
3404 * Response is a  "char **".
3405 * First and Second entries are in hex string format
3406 * and rest are integers represented in ascii format. */
3407void fillCellIdentityFromVoiceRegStateResponseString(CellIdentity &cellIdentity,
3408        int numStrings, char** response) {
3409
3410    RIL_CellIdentity_v16 rilCellIdentity;
3411    memset(&rilCellIdentity, -1, sizeof(RIL_CellIdentity_v16));
3412
3413    rilCellIdentity.cellInfoType = getCellInfoTypeRadioTechnology(response[3]);
3414    switch(rilCellIdentity.cellInfoType) {
3415
3416        case RIL_CELL_INFO_TYPE_GSM: {
3417            /* valid LAC are hexstrings in the range 0x0000 - 0xffff */
3418            rilCellIdentity.cellIdentityGsm.lac =
3419                    convertResponseHexStringEntryToInt(response, 1, numStrings);
3420
3421            /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */
3422            rilCellIdentity.cellIdentityGsm.cid =
3423                    convertResponseHexStringEntryToInt(response, 2, numStrings);
3424            break;
3425        }
3426
3427        case RIL_CELL_INFO_TYPE_WCDMA: {
3428            /* valid LAC are hexstrings in the range 0x0000 - 0xffff */
3429            rilCellIdentity.cellIdentityWcdma.lac =
3430                    convertResponseHexStringEntryToInt(response, 1, numStrings);
3431
3432            /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */
3433            rilCellIdentity.cellIdentityWcdma.cid =
3434                    convertResponseHexStringEntryToInt(response, 2, numStrings);
3435            rilCellIdentity.cellIdentityWcdma.psc =
3436                    convertResponseStringEntryToInt(response, 14, numStrings);
3437            break;
3438        }
3439
3440        case RIL_CELL_INFO_TYPE_TD_SCDMA:{
3441            /* valid LAC are hexstrings in the range 0x0000 - 0xffff */
3442            rilCellIdentity.cellIdentityTdscdma.lac =
3443                    convertResponseHexStringEntryToInt(response, 1, numStrings);
3444
3445            /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */
3446            rilCellIdentity.cellIdentityTdscdma.cid =
3447                    convertResponseHexStringEntryToInt(response, 2, numStrings);
3448            break;
3449        }
3450
3451        case RIL_CELL_INFO_TYPE_CDMA:{
3452            rilCellIdentity.cellIdentityCdma.basestationId =
3453                    convertResponseStringEntryToInt(response, 4, numStrings);
3454            rilCellIdentity.cellIdentityCdma.longitude =
3455                    convertResponseStringEntryToInt(response, 5, numStrings);
3456            rilCellIdentity.cellIdentityCdma.latitude =
3457                    convertResponseStringEntryToInt(response, 6, numStrings);
3458            rilCellIdentity.cellIdentityCdma.systemId =
3459                    convertResponseStringEntryToInt(response, 8, numStrings);
3460            rilCellIdentity.cellIdentityCdma.networkId =
3461                    convertResponseStringEntryToInt(response, 9, numStrings);
3462            break;
3463        }
3464
3465        case RIL_CELL_INFO_TYPE_LTE:{
3466            /* valid TAC are hexstrings in the range 0x0000 - 0xffff */
3467            rilCellIdentity.cellIdentityLte.tac =
3468                    convertResponseHexStringEntryToInt(response, 1, numStrings);
3469
3470            /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */
3471            rilCellIdentity.cellIdentityLte.ci =
3472                    convertResponseHexStringEntryToInt(response, 2, numStrings);
3473            break;
3474        }
3475
3476        default: {
3477            break;
3478        }
3479    }
3480
3481    fillCellIdentityResponse(cellIdentity, rilCellIdentity);
3482}
3483
3484/* Fill Cell Identity info from Data Registration State Response.
3485 * This fucntion is applicable only for RIL Version < 15.
3486 * Response is a  "char **".
3487 * First and Second entries are in hex string format
3488 * and rest are integers represented in ascii format. */
3489void fillCellIdentityFromDataRegStateResponseString(CellIdentity &cellIdentity,
3490        int numStrings, char** response) {
3491
3492    RIL_CellIdentity_v16 rilCellIdentity;
3493    memset(&rilCellIdentity, -1, sizeof(RIL_CellIdentity_v16));
3494
3495    rilCellIdentity.cellInfoType = getCellInfoTypeRadioTechnology(response[3]);
3496    switch(rilCellIdentity.cellInfoType) {
3497        case RIL_CELL_INFO_TYPE_GSM: {
3498            /* valid LAC are hexstrings in the range 0x0000 - 0xffff */
3499            rilCellIdentity.cellIdentityGsm.lac =
3500                    convertResponseHexStringEntryToInt(response, 1, numStrings);
3501
3502            /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */
3503            rilCellIdentity.cellIdentityGsm.cid =
3504                    convertResponseHexStringEntryToInt(response, 2, numStrings);
3505            break;
3506        }
3507        case RIL_CELL_INFO_TYPE_WCDMA: {
3508            /* valid LAC are hexstrings in the range 0x0000 - 0xffff */
3509            rilCellIdentity.cellIdentityWcdma.lac =
3510                    convertResponseHexStringEntryToInt(response, 1, numStrings);
3511
3512            /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */
3513            rilCellIdentity.cellIdentityWcdma.cid =
3514                    convertResponseHexStringEntryToInt(response, 2, numStrings);
3515            break;
3516        }
3517        case RIL_CELL_INFO_TYPE_TD_SCDMA:{
3518            /* valid LAC are hexstrings in the range 0x0000 - 0xffff */
3519            rilCellIdentity.cellIdentityTdscdma.lac =
3520                    convertResponseHexStringEntryToInt(response, 1, numStrings);
3521
3522            /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */
3523            rilCellIdentity.cellIdentityTdscdma.cid =
3524                    convertResponseHexStringEntryToInt(response, 2, numStrings);
3525            break;
3526        }
3527        case RIL_CELL_INFO_TYPE_LTE: {
3528            rilCellIdentity.cellIdentityLte.tac =
3529                    convertResponseStringEntryToInt(response, 6, numStrings);
3530            rilCellIdentity.cellIdentityLte.pci =
3531                    convertResponseStringEntryToInt(response, 7, numStrings);
3532            rilCellIdentity.cellIdentityLte.ci =
3533                    convertResponseStringEntryToInt(response, 8, numStrings);
3534            break;
3535        }
3536        default: {
3537            break;
3538        }
3539    }
3540
3541    fillCellIdentityResponse(cellIdentity, rilCellIdentity);
3542}
3543
3544int radio::getVoiceRegistrationStateResponse(int slotId,
3545                                            int responseType, int serial, RIL_Errno e,
3546                                            void *response, size_t responseLen) {
3547#if VDBG
3548    RLOGD("getVoiceRegistrationStateResponse: serial %d", serial);
3549#endif
3550
3551    if (radioService[slotId]->mRadioResponse != NULL) {
3552        RadioResponseInfo responseInfo = {};
3553        populateResponseInfo(responseInfo, serial, responseType, e);
3554
3555        VoiceRegStateResult voiceRegResponse = {};
3556        int numStrings = responseLen / sizeof(char *);
3557        if (response == NULL) {
3558               RLOGE("getVoiceRegistrationStateResponse Invalid response: NULL");
3559               if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3560        } else if (s_vendorFunctions->version <= 14) {
3561            if (numStrings != 15) {
3562                RLOGE("getVoiceRegistrationStateResponse Invalid response: NULL");
3563                if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3564            } else {
3565                char **resp = (char **) response;
3566                voiceRegResponse.regState = (RegState) ATOI_NULL_HANDLED_DEF(resp[0], 4);
3567                voiceRegResponse.rat = ATOI_NULL_HANDLED(resp[3]);
3568                voiceRegResponse.cssSupported = ATOI_NULL_HANDLED_DEF(resp[7], 0);
3569                voiceRegResponse.roamingIndicator = ATOI_NULL_HANDLED(resp[10]);
3570                voiceRegResponse.systemIsInPrl = ATOI_NULL_HANDLED_DEF(resp[11], 0);
3571                voiceRegResponse.defaultRoamingIndicator = ATOI_NULL_HANDLED_DEF(resp[12], 0);
3572                voiceRegResponse.reasonForDenial = ATOI_NULL_HANDLED_DEF(resp[13], 0);
3573                fillCellIdentityFromVoiceRegStateResponseString(voiceRegResponse.cellIdentity,
3574                        numStrings, resp);
3575            }
3576        } else {
3577            RIL_VoiceRegistrationStateResponse *voiceRegState =
3578                    (RIL_VoiceRegistrationStateResponse *)response;
3579
3580            if (responseLen != sizeof(RIL_VoiceRegistrationStateResponse)) {
3581                RLOGE("getVoiceRegistrationStateResponse Invalid response: NULL");
3582                if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3583            } else {
3584                voiceRegResponse.regState = (RegState) voiceRegState->regState;
3585                voiceRegResponse.rat = voiceRegState->rat;;
3586                voiceRegResponse.cssSupported = voiceRegState->cssSupported;
3587                voiceRegResponse.roamingIndicator = voiceRegState->roamingIndicator;
3588                voiceRegResponse.systemIsInPrl = voiceRegState->systemIsInPrl;
3589                voiceRegResponse.defaultRoamingIndicator = voiceRegState->defaultRoamingIndicator;
3590                voiceRegResponse.reasonForDenial = voiceRegState->reasonForDenial;
3591                fillCellIdentityResponse(voiceRegResponse.cellIdentity,
3592                        voiceRegState->cellIdentity);
3593            }
3594        }
3595
3596        Return<void> retStatus =
3597                radioService[slotId]->mRadioResponse->getVoiceRegistrationStateResponse(
3598                responseInfo, voiceRegResponse);
3599        radioService[slotId]->checkReturnStatus(retStatus);
3600    } else {
3601        RLOGE("getVoiceRegistrationStateResponse: radioService[%d]->mRadioResponse == NULL",
3602                slotId);
3603    }
3604
3605    return 0;
3606}
3607
3608int radio::getDataRegistrationStateResponse(int slotId,
3609                                           int responseType, int serial, RIL_Errno e,
3610                                           void *response, size_t responseLen) {
3611#if VDBG
3612    RLOGD("getDataRegistrationStateResponse: serial %d", serial);
3613#endif
3614
3615    if (radioService[slotId]->mRadioResponse != NULL) {
3616        RadioResponseInfo responseInfo = {};
3617        populateResponseInfo(responseInfo, serial, responseType, e);
3618        DataRegStateResult dataRegResponse = {};
3619        if (response == NULL) {
3620            RLOGE("getDataRegistrationStateResponse Invalid response: NULL");
3621            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3622        } else if (s_vendorFunctions->version <= 14) {
3623            int numStrings = responseLen / sizeof(char *);
3624            if ((numStrings != 6) && (numStrings != 11)) {
3625                RLOGE("getDataRegistrationStateResponse Invalid response: NULL");
3626                if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3627            } else {
3628                char **resp = (char **) response;
3629                dataRegResponse.regState = (RegState) ATOI_NULL_HANDLED_DEF(resp[0], 4);
3630                dataRegResponse.rat =  ATOI_NULL_HANDLED_DEF(resp[3], 0);
3631                dataRegResponse.reasonDataDenied =  ATOI_NULL_HANDLED(resp[4]);
3632                dataRegResponse.maxDataCalls =  ATOI_NULL_HANDLED_DEF(resp[5], 1);
3633                fillCellIdentityFromDataRegStateResponseString(dataRegResponse.cellIdentity,
3634                        numStrings, resp);
3635            }
3636        } else {
3637            RIL_DataRegistrationStateResponse *dataRegState =
3638                    (RIL_DataRegistrationStateResponse *)response;
3639
3640            if (responseLen != sizeof(RIL_DataRegistrationStateResponse)) {
3641                RLOGE("getDataRegistrationStateResponse Invalid response: NULL");
3642                if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3643            } else {
3644                dataRegResponse.regState = (RegState) dataRegState->regState;
3645                dataRegResponse.rat = dataRegState->rat;;
3646                dataRegResponse.reasonDataDenied = dataRegState->reasonDataDenied;
3647                dataRegResponse.maxDataCalls = dataRegState->maxDataCalls;
3648                fillCellIdentityResponse(dataRegResponse.cellIdentity, dataRegState->cellIdentity);
3649            }
3650        }
3651
3652        Return<void> retStatus =
3653                radioService[slotId]->mRadioResponse->getDataRegistrationStateResponse(responseInfo,
3654                dataRegResponse);
3655        radioService[slotId]->checkReturnStatus(retStatus);
3656    } else {
3657        RLOGE("getDataRegistrationStateResponse: radioService[%d]->mRadioResponse == NULL",
3658                slotId);
3659    }
3660
3661    return 0;
3662}
3663
3664int radio::getOperatorResponse(int slotId,
3665                              int responseType, int serial, RIL_Errno e, void *response,
3666                              size_t responseLen) {
3667#if VDBG
3668    RLOGD("getOperatorResponse: serial %d", serial);
3669#endif
3670
3671    if (radioService[slotId]->mRadioResponse != NULL) {
3672        RadioResponseInfo responseInfo = {};
3673        populateResponseInfo(responseInfo, serial, responseType, e);
3674        hidl_string longName;
3675        hidl_string shortName;
3676        hidl_string numeric;
3677        int numStrings = responseLen / sizeof(char *);
3678        if (response == NULL || numStrings != 3) {
3679            RLOGE("getOperatorResponse Invalid response: NULL");
3680            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3681
3682        } else {
3683            char **resp = (char **) response;
3684            longName = convertCharPtrToHidlString(resp[0]);
3685            shortName = convertCharPtrToHidlString(resp[1]);
3686            numeric = convertCharPtrToHidlString(resp[2]);
3687        }
3688        Return<void> retStatus = radioService[slotId]->mRadioResponse->getOperatorResponse(
3689                responseInfo, longName, shortName, numeric);
3690        radioService[slotId]->checkReturnStatus(retStatus);
3691    } else {
3692        RLOGE("getOperatorResponse: radioService[%d]->mRadioResponse == NULL",
3693                slotId);
3694    }
3695
3696    return 0;
3697}
3698
3699int radio::setRadioPowerResponse(int slotId,
3700                                int responseType, int serial, RIL_Errno e, void *response,
3701                                size_t responseLen) {
3702    RLOGD("setRadioPowerResponse: serial %d", serial);
3703
3704    if (radioService[slotId]->mRadioResponse != NULL) {
3705        RadioResponseInfo responseInfo = {};
3706        populateResponseInfo(responseInfo, serial, responseType, e);
3707        Return<void> retStatus = radioService[slotId]->mRadioResponse->setRadioPowerResponse(
3708                responseInfo);
3709        radioService[slotId]->checkReturnStatus(retStatus);
3710    } else {
3711        RLOGE("setRadioPowerResponse: radioService[%d]->mRadioResponse == NULL",
3712                slotId);
3713    }
3714
3715    return 0;
3716}
3717
3718int radio::sendDtmfResponse(int slotId,
3719                           int responseType, int serial, RIL_Errno e, void *response,
3720                           size_t responseLen) {
3721#if VDBG
3722    RLOGD("sendDtmfResponse: serial %d", serial);
3723#endif
3724
3725    if (radioService[slotId]->mRadioResponse != NULL) {
3726        RadioResponseInfo responseInfo = {};
3727        populateResponseInfo(responseInfo, serial, responseType, e);
3728        Return<void> retStatus = radioService[slotId]->mRadioResponse->sendDtmfResponse(
3729                responseInfo);
3730        radioService[slotId]->checkReturnStatus(retStatus);
3731    } else {
3732        RLOGE("sendDtmfResponse: radioService[%d]->mRadioResponse == NULL",
3733                slotId);
3734    }
3735
3736    return 0;
3737}
3738
3739SendSmsResult makeSendSmsResult(RadioResponseInfo& responseInfo, int serial, int responseType,
3740                                RIL_Errno e, void *response, size_t responseLen) {
3741    populateResponseInfo(responseInfo, serial, responseType, e);
3742    SendSmsResult result = {};
3743
3744    if (response == NULL || responseLen != sizeof(RIL_SMS_Response)) {
3745        RLOGE("Invalid response: NULL");
3746        if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3747        result.ackPDU = hidl_string();
3748    } else {
3749        RIL_SMS_Response *resp = (RIL_SMS_Response *) response;
3750        result.messageRef = resp->messageRef;
3751        result.ackPDU = convertCharPtrToHidlString(resp->ackPDU);
3752        result.errorCode = resp->errorCode;
3753    }
3754    return result;
3755}
3756
3757int radio::sendSmsResponse(int slotId,
3758                          int responseType, int serial, RIL_Errno e, void *response,
3759                          size_t responseLen) {
3760#if VDBG
3761    RLOGD("sendSmsResponse: serial %d", serial);
3762#endif
3763
3764    if (radioService[slotId]->mRadioResponse != NULL) {
3765        RadioResponseInfo responseInfo = {};
3766        SendSmsResult result = makeSendSmsResult(responseInfo, serial, responseType, e, response,
3767                responseLen);
3768
3769        Return<void> retStatus = radioService[slotId]->mRadioResponse->sendSmsResponse(responseInfo,
3770                result);
3771        radioService[slotId]->checkReturnStatus(retStatus);
3772    } else {
3773        RLOGE("sendSmsResponse: radioService[%d]->mRadioResponse == NULL", slotId);
3774    }
3775
3776    return 0;
3777}
3778
3779int radio::sendSMSExpectMoreResponse(int slotId,
3780                                    int responseType, int serial, RIL_Errno e, void *response,
3781                                    size_t responseLen) {
3782#if VDBG
3783    RLOGD("sendSMSExpectMoreResponse: serial %d", serial);
3784#endif
3785
3786    if (radioService[slotId]->mRadioResponse != NULL) {
3787        RadioResponseInfo responseInfo = {};
3788        SendSmsResult result = makeSendSmsResult(responseInfo, serial, responseType, e, response,
3789                responseLen);
3790
3791        Return<void> retStatus = radioService[slotId]->mRadioResponse->sendSMSExpectMoreResponse(
3792                responseInfo, result);
3793        radioService[slotId]->checkReturnStatus(retStatus);
3794    } else {
3795        RLOGE("sendSMSExpectMoreResponse: radioService[%d]->mRadioResponse == NULL", slotId);
3796    }
3797
3798    return 0;
3799}
3800
3801int radio::setupDataCallResponse(int slotId,
3802                                 int responseType, int serial, RIL_Errno e, void *response,
3803                                 size_t responseLen) {
3804#if VDBG
3805    RLOGD("setupDataCallResponse: serial %d", serial);
3806#endif
3807
3808    if (radioService[slotId]->mRadioResponse != NULL) {
3809        RadioResponseInfo responseInfo = {};
3810        populateResponseInfo(responseInfo, serial, responseType, e);
3811
3812        SetupDataCallResult result = {};
3813        if (response == NULL || responseLen != sizeof(RIL_Data_Call_Response_v11)) {
3814            RLOGE("setupDataCallResponse: Invalid response");
3815            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3816            result.status = DataCallFailCause::ERROR_UNSPECIFIED;
3817            result.type = hidl_string();
3818            result.ifname = hidl_string();
3819            result.addresses = hidl_string();
3820            result.dnses = hidl_string();
3821            result.gateways = hidl_string();
3822            result.pcscf = hidl_string();
3823        } else {
3824            convertRilDataCallToHal((RIL_Data_Call_Response_v11 *) response, result);
3825        }
3826
3827        Return<void> retStatus = radioService[slotId]->mRadioResponse->setupDataCallResponse(
3828                responseInfo, result);
3829        radioService[slotId]->checkReturnStatus(retStatus);
3830    } else {
3831        RLOGE("setupDataCallResponse: radioService[%d]->mRadioResponse == NULL", slotId);
3832    }
3833
3834    return 0;
3835}
3836
3837IccIoResult responseIccIo(RadioResponseInfo& responseInfo, int serial, int responseType,
3838                           RIL_Errno e, void *response, size_t responseLen) {
3839    populateResponseInfo(responseInfo, serial, responseType, e);
3840    IccIoResult result = {};
3841
3842    if (response == NULL || responseLen != sizeof(RIL_SIM_IO_Response)) {
3843        RLOGE("Invalid response: NULL");
3844        if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3845        result.simResponse = hidl_string();
3846    } else {
3847        RIL_SIM_IO_Response *resp = (RIL_SIM_IO_Response *) response;
3848        result.sw1 = resp->sw1;
3849        result.sw2 = resp->sw2;
3850        result.simResponse = convertCharPtrToHidlString(resp->simResponse);
3851    }
3852    return result;
3853}
3854
3855int radio::iccIOForAppResponse(int slotId,
3856                      int responseType, int serial, RIL_Errno e, void *response,
3857                      size_t responseLen) {
3858#if VDBG
3859    RLOGD("iccIOForAppResponse: serial %d", serial);
3860#endif
3861
3862    if (radioService[slotId]->mRadioResponse != NULL) {
3863        RadioResponseInfo responseInfo = {};
3864        IccIoResult result = responseIccIo(responseInfo, serial, responseType, e, response,
3865                responseLen);
3866
3867        Return<void> retStatus = radioService[slotId]->mRadioResponse->iccIOForAppResponse(
3868                responseInfo, result);
3869        radioService[slotId]->checkReturnStatus(retStatus);
3870    } else {
3871        RLOGE("iccIOForAppResponse: radioService[%d]->mRadioResponse == NULL", slotId);
3872    }
3873
3874    return 0;
3875}
3876
3877int radio::sendUssdResponse(int slotId,
3878                           int responseType, int serial, RIL_Errno e, void *response,
3879                           size_t responseLen) {
3880#if VDBG
3881    RLOGD("sendUssdResponse: serial %d", serial);
3882#endif
3883
3884    if (radioService[slotId]->mRadioResponse != NULL) {
3885        RadioResponseInfo responseInfo = {};
3886        populateResponseInfo(responseInfo, serial, responseType, e);
3887        Return<void> retStatus = radioService[slotId]->mRadioResponse->sendUssdResponse(
3888                responseInfo);
3889        radioService[slotId]->checkReturnStatus(retStatus);
3890    } else {
3891        RLOGE("sendUssdResponse: radioService[%d]->mRadioResponse == NULL",
3892                slotId);
3893    }
3894
3895    return 0;
3896}
3897
3898int radio::cancelPendingUssdResponse(int slotId,
3899                                    int responseType, int serial, RIL_Errno e, void *response,
3900                                    size_t responseLen) {
3901#if VDBG
3902    RLOGD("cancelPendingUssdResponse: serial %d", serial);
3903#endif
3904
3905    if (radioService[slotId]->mRadioResponse != NULL) {
3906        RadioResponseInfo responseInfo = {};
3907        populateResponseInfo(responseInfo, serial, responseType, e);
3908        Return<void> retStatus = radioService[slotId]->mRadioResponse->cancelPendingUssdResponse(
3909                responseInfo);
3910        radioService[slotId]->checkReturnStatus(retStatus);
3911    } else {
3912        RLOGE("cancelPendingUssdResponse: radioService[%d]->mRadioResponse == NULL",
3913                slotId);
3914    }
3915
3916    return 0;
3917}
3918
3919int radio::getClirResponse(int slotId,
3920                              int responseType, int serial, RIL_Errno e, void *response,
3921                              size_t responseLen) {
3922#if VDBG
3923    RLOGD("getClirResponse: serial %d", serial);
3924#endif
3925
3926    if (radioService[slotId]->mRadioResponse != NULL) {
3927        RadioResponseInfo responseInfo = {};
3928        populateResponseInfo(responseInfo, serial, responseType, e);
3929        int n = -1, m = -1;
3930        int numInts = responseLen / sizeof(int);
3931        if (response == NULL || numInts != 2) {
3932            RLOGE("getClirResponse Invalid response: NULL");
3933            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3934        } else {
3935            int *pInt = (int *) response;
3936            n = pInt[0];
3937            m = pInt[1];
3938        }
3939        Return<void> retStatus = radioService[slotId]->mRadioResponse->getClirResponse(responseInfo,
3940                n, m);
3941        radioService[slotId]->checkReturnStatus(retStatus);
3942    } else {
3943        RLOGE("getClirResponse: radioService[%d]->mRadioResponse == NULL", slotId);
3944    }
3945
3946    return 0;
3947}
3948
3949int radio::setClirResponse(int slotId,
3950                          int responseType, int serial, RIL_Errno e, void *response,
3951                          size_t responseLen) {
3952#if VDBG
3953    RLOGD("setClirResponse: serial %d", serial);
3954#endif
3955
3956    if (radioService[slotId]->mRadioResponse != NULL) {
3957        RadioResponseInfo responseInfo = {};
3958        populateResponseInfo(responseInfo, serial, responseType, e);
3959        Return<void> retStatus = radioService[slotId]->mRadioResponse->setClirResponse(
3960                responseInfo);
3961        radioService[slotId]->checkReturnStatus(retStatus);
3962    } else {
3963        RLOGE("setClirResponse: radioService[%d]->mRadioResponse == NULL", slotId);
3964    }
3965
3966    return 0;
3967}
3968
3969int radio::getCallForwardStatusResponse(int slotId,
3970                                       int responseType, int serial, RIL_Errno e,
3971                                       void *response, size_t responseLen) {
3972#if VDBG
3973    RLOGD("getCallForwardStatusResponse: serial %d", serial);
3974#endif
3975
3976    if (radioService[slotId]->mRadioResponse != NULL) {
3977        RadioResponseInfo responseInfo = {};
3978        populateResponseInfo(responseInfo, serial, responseType, e);
3979        hidl_vec<CallForwardInfo> callForwardInfos;
3980
3981        if (response == NULL || responseLen % sizeof(RIL_CallForwardInfo *) != 0) {
3982            RLOGE("getCallForwardStatusResponse Invalid response: NULL");
3983            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
3984        } else {
3985            int num = responseLen / sizeof(RIL_CallForwardInfo *);
3986            callForwardInfos.resize(num);
3987            for (int i = 0 ; i < num; i++) {
3988                RIL_CallForwardInfo *resp = ((RIL_CallForwardInfo **) response)[i];
3989                callForwardInfos[i].status = (CallForwardInfoStatus) resp->status;
3990                callForwardInfos[i].reason = resp->reason;
3991                callForwardInfos[i].serviceClass = resp->serviceClass;
3992                callForwardInfos[i].toa = resp->toa;
3993                callForwardInfos[i].number = convertCharPtrToHidlString(resp->number);
3994                callForwardInfos[i].timeSeconds = resp->timeSeconds;
3995            }
3996        }
3997
3998        Return<void> retStatus = radioService[slotId]->mRadioResponse->getCallForwardStatusResponse(
3999                responseInfo, callForwardInfos);
4000        radioService[slotId]->checkReturnStatus(retStatus);
4001    } else {
4002        RLOGE("getCallForwardStatusResponse: radioService[%d]->mRadioResponse == NULL",
4003                slotId);
4004    }
4005
4006    return 0;
4007}
4008
4009int radio::setCallForwardResponse(int slotId,
4010                                 int responseType, int serial, RIL_Errno e, void *response,
4011                                 size_t responseLen) {
4012#if VDBG
4013    RLOGD("setCallForwardResponse: serial %d", serial);
4014#endif
4015
4016    if (radioService[slotId]->mRadioResponse != NULL) {
4017        RadioResponseInfo responseInfo = {};
4018        populateResponseInfo(responseInfo, serial, responseType, e);
4019        Return<void> retStatus = radioService[slotId]->mRadioResponse->setCallForwardResponse(
4020                responseInfo);
4021        radioService[slotId]->checkReturnStatus(retStatus);
4022    } else {
4023        RLOGE("setCallForwardResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4024    }
4025
4026    return 0;
4027}
4028
4029int radio::getCallWaitingResponse(int slotId,
4030                                 int responseType, int serial, RIL_Errno e, void *response,
4031                                 size_t responseLen) {
4032#if VDBG
4033    RLOGD("getCallWaitingResponse: serial %d", serial);
4034#endif
4035
4036    if (radioService[slotId]->mRadioResponse != NULL) {
4037        RadioResponseInfo responseInfo = {};
4038        populateResponseInfo(responseInfo, serial, responseType, e);
4039        bool enable = false;
4040        int serviceClass = -1;
4041        int numInts = responseLen / sizeof(int);
4042        if (response == NULL || numInts != 2) {
4043            RLOGE("getCallWaitingResponse Invalid response: NULL");
4044            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
4045        } else {
4046            int *pInt = (int *) response;
4047            enable = pInt[0] == 1 ? true : false;
4048            serviceClass = pInt[1];
4049        }
4050        Return<void> retStatus = radioService[slotId]->mRadioResponse->getCallWaitingResponse(
4051                responseInfo, enable, serviceClass);
4052        radioService[slotId]->checkReturnStatus(retStatus);
4053    } else {
4054        RLOGE("getCallWaitingResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4055    }
4056
4057    return 0;
4058}
4059
4060int radio::setCallWaitingResponse(int slotId,
4061                                 int responseType, int serial, RIL_Errno e, void *response,
4062                                 size_t responseLen) {
4063#if VDBG
4064    RLOGD("setCallWaitingResponse: serial %d", serial);
4065#endif
4066
4067    if (radioService[slotId]->mRadioResponse != NULL) {
4068        RadioResponseInfo responseInfo = {};
4069        populateResponseInfo(responseInfo, serial, responseType, e);
4070        Return<void> retStatus = radioService[slotId]->mRadioResponse->setCallWaitingResponse(
4071                responseInfo);
4072        radioService[slotId]->checkReturnStatus(retStatus);
4073    } else {
4074        RLOGE("setCallWaitingResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4075    }
4076
4077    return 0;
4078}
4079
4080int radio::acknowledgeLastIncomingGsmSmsResponse(int slotId,
4081                                                int responseType, int serial, RIL_Errno e,
4082                                                void *response, size_t responseLen) {
4083#if VDBG
4084    RLOGD("acknowledgeLastIncomingGsmSmsResponse: serial %d", serial);
4085#endif
4086
4087    if (radioService[slotId]->mRadioResponse != NULL) {
4088        RadioResponseInfo responseInfo = {};
4089        populateResponseInfo(responseInfo, serial, responseType, e);
4090        Return<void> retStatus =
4091                radioService[slotId]->mRadioResponse->acknowledgeLastIncomingGsmSmsResponse(
4092                responseInfo);
4093        radioService[slotId]->checkReturnStatus(retStatus);
4094    } else {
4095        RLOGE("acknowledgeLastIncomingGsmSmsResponse: radioService[%d]->mRadioResponse "
4096                "== NULL", slotId);
4097    }
4098
4099    return 0;
4100}
4101
4102int radio::acceptCallResponse(int slotId,
4103                             int responseType, int serial, RIL_Errno e,
4104                             void *response, size_t responseLen) {
4105#if VDBG
4106    RLOGD("acceptCallResponse: serial %d", serial);
4107#endif
4108
4109    if (radioService[slotId]->mRadioResponse != NULL) {
4110        RadioResponseInfo responseInfo = {};
4111        populateResponseInfo(responseInfo, serial, responseType, e);
4112        Return<void> retStatus = radioService[slotId]->mRadioResponse->acceptCallResponse(
4113                responseInfo);
4114        radioService[slotId]->checkReturnStatus(retStatus);
4115    } else {
4116        RLOGE("acceptCallResponse: radioService[%d]->mRadioResponse == NULL",
4117                slotId);
4118    }
4119
4120    return 0;
4121}
4122
4123int radio::deactivateDataCallResponse(int slotId,
4124                                                int responseType, int serial, RIL_Errno e,
4125                                                void *response, size_t responseLen) {
4126#if VDBG
4127    RLOGD("deactivateDataCallResponse: serial %d", serial);
4128#endif
4129
4130    if (radioService[slotId]->mRadioResponse != NULL) {
4131        RadioResponseInfo responseInfo = {};
4132        populateResponseInfo(responseInfo, serial, responseType, e);
4133        Return<void> retStatus = radioService[slotId]->mRadioResponse->deactivateDataCallResponse(
4134                responseInfo);
4135        radioService[slotId]->checkReturnStatus(retStatus);
4136    } else {
4137        RLOGE("deactivateDataCallResponse: radioService[%d]->mRadioResponse == NULL",
4138                slotId);
4139    }
4140
4141    return 0;
4142}
4143
4144int radio::getFacilityLockForAppResponse(int slotId,
4145                                        int responseType, int serial, RIL_Errno e,
4146                                        void *response, size_t responseLen) {
4147#if VDBG
4148    RLOGD("getFacilityLockForAppResponse: serial %d", serial);
4149#endif
4150
4151    if (radioService[slotId]->mRadioResponse != NULL) {
4152        RadioResponseInfo responseInfo = {};
4153        int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen);
4154        Return<void> retStatus = radioService[slotId]->mRadioResponse->
4155                getFacilityLockForAppResponse(responseInfo, ret);
4156        radioService[slotId]->checkReturnStatus(retStatus);
4157    } else {
4158        RLOGE("getFacilityLockForAppResponse: radioService[%d]->mRadioResponse == NULL",
4159                slotId);
4160    }
4161
4162    return 0;
4163}
4164
4165int radio::setFacilityLockForAppResponse(int slotId,
4166                                      int responseType, int serial, RIL_Errno e,
4167                                      void *response, size_t responseLen) {
4168#if VDBG
4169    RLOGD("setFacilityLockForAppResponse: serial %d", serial);
4170#endif
4171
4172    if (radioService[slotId]->mRadioResponse != NULL) {
4173        RadioResponseInfo responseInfo = {};
4174        int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen);
4175        Return<void> retStatus
4176                = radioService[slotId]->mRadioResponse->setFacilityLockForAppResponse(responseInfo,
4177                ret);
4178        radioService[slotId]->checkReturnStatus(retStatus);
4179    } else {
4180        RLOGE("setFacilityLockForAppResponse: radioService[%d]->mRadioResponse == NULL",
4181                slotId);
4182    }
4183
4184    return 0;
4185}
4186
4187int radio::setBarringPasswordResponse(int slotId,
4188                             int responseType, int serial, RIL_Errno e,
4189                             void *response, size_t responseLen) {
4190#if VDBG
4191    RLOGD("acceptCallResponse: serial %d", serial);
4192#endif
4193
4194    if (radioService[slotId]->mRadioResponse != NULL) {
4195        RadioResponseInfo responseInfo = {};
4196        populateResponseInfo(responseInfo, serial, responseType, e);
4197        Return<void> retStatus
4198                = radioService[slotId]->mRadioResponse->setBarringPasswordResponse(responseInfo);
4199        radioService[slotId]->checkReturnStatus(retStatus);
4200    } else {
4201        RLOGE("setBarringPasswordResponse: radioService[%d]->mRadioResponse == NULL",
4202                slotId);
4203    }
4204
4205    return 0;
4206}
4207
4208int radio::getNetworkSelectionModeResponse(int slotId,
4209                                          int responseType, int serial, RIL_Errno e, void *response,
4210                                          size_t responseLen) {
4211#if VDBG
4212    RLOGD("getNetworkSelectionModeResponse: serial %d", serial);
4213#endif
4214
4215    if (radioService[slotId]->mRadioResponse != NULL) {
4216        RadioResponseInfo responseInfo = {};
4217        populateResponseInfo(responseInfo, serial, responseType, e);
4218        bool manual = false;
4219        int serviceClass;
4220        if (response == NULL || responseLen != sizeof(int)) {
4221            RLOGE("getNetworkSelectionModeResponse Invalid response: NULL");
4222            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
4223        } else {
4224            int *pInt = (int *) response;
4225            manual = pInt[0] == 1 ? true : false;
4226        }
4227        Return<void> retStatus
4228                = radioService[slotId]->mRadioResponse->getNetworkSelectionModeResponse(
4229                responseInfo,
4230                manual);
4231        radioService[slotId]->checkReturnStatus(retStatus);
4232    } else {
4233        RLOGE("getNetworkSelectionModeResponse: radioService[%d]->mRadioResponse == NULL",
4234                slotId);
4235    }
4236
4237    return 0;
4238}
4239
4240int radio::setNetworkSelectionModeAutomaticResponse(int slotId, int responseType, int serial,
4241                                                    RIL_Errno e, void *response,
4242                                                    size_t responseLen) {
4243#if VDBG
4244    RLOGD("setNetworkSelectionModeAutomaticResponse: serial %d", serial);
4245#endif
4246
4247    if (radioService[slotId]->mRadioResponse != NULL) {
4248        RadioResponseInfo responseInfo = {};
4249        populateResponseInfo(responseInfo, serial, responseType, e);
4250        Return<void> retStatus
4251                = radioService[slotId]->mRadioResponse->setNetworkSelectionModeAutomaticResponse(
4252                responseInfo);
4253        radioService[slotId]->checkReturnStatus(retStatus);
4254    } else {
4255        RLOGE("setNetworkSelectionModeAutomaticResponse: radioService[%d]->mRadioResponse "
4256                "== NULL", slotId);
4257    }
4258
4259    return 0;
4260}
4261
4262int radio::setNetworkSelectionModeManualResponse(int slotId,
4263                             int responseType, int serial, RIL_Errno e,
4264                             void *response, size_t responseLen) {
4265#if VDBG
4266    RLOGD("setNetworkSelectionModeManualResponse: serial %d", serial);
4267#endif
4268
4269    if (radioService[slotId]->mRadioResponse != NULL) {
4270        RadioResponseInfo responseInfo = {};
4271        populateResponseInfo(responseInfo, serial, responseType, e);
4272        Return<void> retStatus
4273                = radioService[slotId]->mRadioResponse->setNetworkSelectionModeManualResponse(
4274                responseInfo);
4275        radioService[slotId]->checkReturnStatus(retStatus);
4276    } else {
4277        RLOGE("acceptCallResponse: radioService[%d]->setNetworkSelectionModeManualResponse "
4278                "== NULL", slotId);
4279    }
4280
4281    return 0;
4282}
4283
4284int convertOperatorStatusToInt(const char *str) {
4285    if (strncmp("unknown", str, 9) == 0) {
4286        return (int) OperatorStatus::UNKNOWN;
4287    } else if (strncmp("available", str, 9) == 0) {
4288        return (int) OperatorStatus::AVAILABLE;
4289    } else if (strncmp("current", str, 9) == 0) {
4290        return (int) OperatorStatus::CURRENT;
4291    } else if (strncmp("forbidden", str, 9) == 0) {
4292        return (int) OperatorStatus::FORBIDDEN;
4293    } else {
4294        return -1;
4295    }
4296}
4297
4298int radio::getAvailableNetworksResponse(int slotId,
4299                              int responseType, int serial, RIL_Errno e, void *response,
4300                              size_t responseLen) {
4301#if VDBG
4302    RLOGD("getAvailableNetworksResponse: serial %d", serial);
4303#endif
4304
4305    if (radioService[slotId]->mRadioResponse != NULL) {
4306        RadioResponseInfo responseInfo = {};
4307        populateResponseInfo(responseInfo, serial, responseType, e);
4308        hidl_vec<OperatorInfo> networks;
4309        if (response == NULL || responseLen % (4 * sizeof(char *))!= 0) {
4310            RLOGE("getAvailableNetworksResponse Invalid response: NULL");
4311            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
4312        } else {
4313            char **resp = (char **) response;
4314            int numStrings = responseLen / sizeof(char *);
4315            networks.resize(numStrings/4);
4316            for (int i = 0, j = 0; i < numStrings; i = i + 4, j++) {
4317                networks[j].alphaLong = convertCharPtrToHidlString(resp[i]);
4318                networks[j].alphaShort = convertCharPtrToHidlString(resp[i + 1]);
4319                networks[j].operatorNumeric = convertCharPtrToHidlString(resp[i + 2]);
4320                int status = convertOperatorStatusToInt(resp[i + 3]);
4321                if (status == -1) {
4322                    if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
4323                } else {
4324                    networks[j].status = (OperatorStatus) status;
4325                }
4326            }
4327        }
4328        Return<void> retStatus
4329                = radioService[slotId]->mRadioResponse->getAvailableNetworksResponse(responseInfo,
4330                networks);
4331        radioService[slotId]->checkReturnStatus(retStatus);
4332    } else {
4333        RLOGE("getAvailableNetworksResponse: radioService[%d]->mRadioResponse == NULL",
4334                slotId);
4335    }
4336
4337    return 0;
4338}
4339
4340int radio::startDtmfResponse(int slotId,
4341                            int responseType, int serial, RIL_Errno e,
4342                            void *response, size_t responseLen) {
4343#if VDBG
4344    RLOGD("startDtmfResponse: serial %d", serial);
4345#endif
4346
4347    if (radioService[slotId]->mRadioResponse != NULL) {
4348        RadioResponseInfo responseInfo = {};
4349        populateResponseInfo(responseInfo, serial, responseType, e);
4350        Return<void> retStatus
4351                = radioService[slotId]->mRadioResponse->startDtmfResponse(responseInfo);
4352        radioService[slotId]->checkReturnStatus(retStatus);
4353    } else {
4354        RLOGE("startDtmfResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4355    }
4356
4357    return 0;
4358}
4359
4360int radio::stopDtmfResponse(int slotId,
4361                           int responseType, int serial, RIL_Errno e,
4362                           void *response, size_t responseLen) {
4363#if VDBG
4364    RLOGD("stopDtmfResponse: serial %d", serial);
4365#endif
4366
4367    if (radioService[slotId]->mRadioResponse != NULL) {
4368        RadioResponseInfo responseInfo = {};
4369        populateResponseInfo(responseInfo, serial, responseType, e);
4370        Return<void> retStatus
4371                = radioService[slotId]->mRadioResponse->stopDtmfResponse(responseInfo);
4372        radioService[slotId]->checkReturnStatus(retStatus);
4373    } else {
4374        RLOGE("stopDtmfResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4375    }
4376
4377    return 0;
4378}
4379
4380int radio::getBasebandVersionResponse(int slotId,
4381                                     int responseType, int serial, RIL_Errno e,
4382                                     void *response, size_t responseLen) {
4383#if VDBG
4384    RLOGD("getBasebandVersionResponse: serial %d", serial);
4385#endif
4386
4387    if (radioService[slotId]->mRadioResponse != NULL) {
4388        RadioResponseInfo responseInfo = {};
4389        populateResponseInfo(responseInfo, serial, responseType, e);
4390        Return<void> retStatus
4391                = radioService[slotId]->mRadioResponse->getBasebandVersionResponse(responseInfo,
4392                convertCharPtrToHidlString((char *) response));
4393        radioService[slotId]->checkReturnStatus(retStatus);
4394    } else {
4395        RLOGE("getBasebandVersionResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4396    }
4397
4398    return 0;
4399}
4400
4401int radio::separateConnectionResponse(int slotId,
4402                                     int responseType, int serial, RIL_Errno e,
4403                                     void *response, size_t responseLen) {
4404#if VDBG
4405    RLOGD("separateConnectionResponse: serial %d", serial);
4406#endif
4407
4408    if (radioService[slotId]->mRadioResponse != NULL) {
4409        RadioResponseInfo responseInfo = {};
4410        populateResponseInfo(responseInfo, serial, responseType, e);
4411        Return<void> retStatus
4412                = radioService[slotId]->mRadioResponse->separateConnectionResponse(responseInfo);
4413        radioService[slotId]->checkReturnStatus(retStatus);
4414    } else {
4415        RLOGE("separateConnectionResponse: radioService[%d]->mRadioResponse == NULL",
4416                slotId);
4417    }
4418
4419    return 0;
4420}
4421
4422int radio::setMuteResponse(int slotId,
4423                          int responseType, int serial, RIL_Errno e,
4424                          void *response, size_t responseLen) {
4425#if VDBG
4426    RLOGD("setMuteResponse: serial %d", serial);
4427#endif
4428
4429    if (radioService[slotId]->mRadioResponse != NULL) {
4430        RadioResponseInfo responseInfo = {};
4431        populateResponseInfo(responseInfo, serial, responseType, e);
4432        Return<void> retStatus
4433                = radioService[slotId]->mRadioResponse->setMuteResponse(responseInfo);
4434        radioService[slotId]->checkReturnStatus(retStatus);
4435    } else {
4436        RLOGE("setMuteResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4437    }
4438
4439    return 0;
4440}
4441
4442int radio::getMuteResponse(int slotId,
4443                          int responseType, int serial, RIL_Errno e, void *response,
4444                          size_t responseLen) {
4445#if VDBG
4446    RLOGD("getMuteResponse: serial %d", serial);
4447#endif
4448
4449    if (radioService[slotId]->mRadioResponse != NULL) {
4450        RadioResponseInfo responseInfo = {};
4451        populateResponseInfo(responseInfo, serial, responseType, e);
4452        bool enable = false;
4453        int serviceClass;
4454        if (response == NULL || responseLen != sizeof(int)) {
4455            RLOGE("getMuteResponse Invalid response: NULL");
4456            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
4457        } else {
4458            int *pInt = (int *) response;
4459            enable = pInt[0] == 1 ? true : false;
4460        }
4461        Return<void> retStatus = radioService[slotId]->mRadioResponse->getMuteResponse(responseInfo,
4462                enable);
4463        radioService[slotId]->checkReturnStatus(retStatus);
4464    } else {
4465        RLOGE("getMuteResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4466    }
4467
4468    return 0;
4469}
4470
4471int radio::getClipResponse(int slotId,
4472                          int responseType, int serial, RIL_Errno e,
4473                          void *response, size_t responseLen) {
4474#if VDBG
4475    RLOGD("getClipResponse: serial %d", serial);
4476#endif
4477
4478    if (radioService[slotId]->mRadioResponse != NULL) {
4479        RadioResponseInfo responseInfo = {};
4480        int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen);
4481        Return<void> retStatus = radioService[slotId]->mRadioResponse->getClipResponse(responseInfo,
4482                (ClipStatus) ret);
4483        radioService[slotId]->checkReturnStatus(retStatus);
4484    } else {
4485        RLOGE("getClipResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4486    }
4487
4488    return 0;
4489}
4490
4491int radio::getDataCallListResponse(int slotId,
4492                                   int responseType, int serial, RIL_Errno e,
4493                                   void *response, size_t responseLen) {
4494#if VDBG
4495    RLOGD("getDataCallListResponse: serial %d", serial);
4496#endif
4497
4498    if (radioService[slotId]->mRadioResponse != NULL) {
4499        RadioResponseInfo responseInfo = {};
4500        populateResponseInfo(responseInfo, serial, responseType, e);
4501
4502        hidl_vec<SetupDataCallResult> ret;
4503        if (response == NULL || responseLen % sizeof(RIL_Data_Call_Response_v11) != 0) {
4504            RLOGE("getDataCallListResponse: invalid response");
4505            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
4506        } else {
4507            convertRilDataCallListToHal(response, responseLen, ret);
4508        }
4509
4510        Return<void> retStatus = radioService[slotId]->mRadioResponse->getDataCallListResponse(
4511                responseInfo, ret);
4512        radioService[slotId]->checkReturnStatus(retStatus);
4513    } else {
4514        RLOGE("getDataCallListResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4515    }
4516
4517    return 0;
4518}
4519
4520int radio::setSuppServiceNotificationsResponse(int slotId,
4521                                              int responseType, int serial, RIL_Errno e,
4522                                              void *response, size_t responseLen) {
4523#if VDBG
4524    RLOGD("setSuppServiceNotificationsResponse: serial %d", serial);
4525#endif
4526
4527    if (radioService[slotId]->mRadioResponse != NULL) {
4528        RadioResponseInfo responseInfo = {};
4529        populateResponseInfo(responseInfo, serial, responseType, e);
4530        Return<void> retStatus
4531                = radioService[slotId]->mRadioResponse->setSuppServiceNotificationsResponse(
4532                responseInfo);
4533        radioService[slotId]->checkReturnStatus(retStatus);
4534    } else {
4535        RLOGE("setSuppServiceNotificationsResponse: radioService[%d]->mRadioResponse "
4536                "== NULL", slotId);
4537    }
4538
4539    return 0;
4540}
4541
4542int radio::deleteSmsOnSimResponse(int slotId,
4543                                 int responseType, int serial, RIL_Errno e,
4544                                 void *response, size_t responseLen) {
4545#if VDBG
4546    RLOGD("deleteSmsOnSimResponse: serial %d", serial);
4547#endif
4548
4549    if (radioService[slotId]->mRadioResponse != NULL) {
4550        RadioResponseInfo responseInfo = {};
4551        populateResponseInfo(responseInfo, serial, responseType, e);
4552        Return<void> retStatus
4553                = radioService[slotId]->mRadioResponse->deleteSmsOnSimResponse(responseInfo);
4554        radioService[slotId]->checkReturnStatus(retStatus);
4555    } else {
4556        RLOGE("deleteSmsOnSimResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4557    }
4558
4559    return 0;
4560}
4561
4562int radio::setBandModeResponse(int slotId,
4563                              int responseType, int serial, RIL_Errno e,
4564                              void *response, size_t responseLen) {
4565#if VDBG
4566    RLOGD("setBandModeResponse: serial %d", serial);
4567#endif
4568
4569    if (radioService[slotId]->mRadioResponse != NULL) {
4570        RadioResponseInfo responseInfo = {};
4571        populateResponseInfo(responseInfo, serial, responseType, e);
4572        Return<void> retStatus
4573                = radioService[slotId]->mRadioResponse->setBandModeResponse(responseInfo);
4574        radioService[slotId]->checkReturnStatus(retStatus);
4575    } else {
4576        RLOGE("setBandModeResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4577    }
4578
4579    return 0;
4580}
4581
4582int radio::writeSmsToSimResponse(int slotId,
4583                                int responseType, int serial, RIL_Errno e,
4584                                void *response, size_t responseLen) {
4585#if VDBG
4586    RLOGD("writeSmsToSimResponse: serial %d", serial);
4587#endif
4588
4589    if (radioService[slotId]->mRadioResponse != NULL) {
4590        RadioResponseInfo responseInfo = {};
4591        int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen);
4592        Return<void> retStatus
4593                = radioService[slotId]->mRadioResponse->writeSmsToSimResponse(responseInfo, ret);
4594        radioService[slotId]->checkReturnStatus(retStatus);
4595    } else {
4596        RLOGE("writeSmsToSimResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4597    }
4598
4599    return 0;
4600}
4601
4602int radio::getAvailableBandModesResponse(int slotId,
4603                                        int responseType, int serial, RIL_Errno e, void *response,
4604                                        size_t responseLen) {
4605#if VDBG
4606    RLOGD("getAvailableBandModesResponse: serial %d", serial);
4607#endif
4608
4609    if (radioService[slotId]->mRadioResponse != NULL) {
4610        RadioResponseInfo responseInfo = {};
4611        populateResponseInfo(responseInfo, serial, responseType, e);
4612        hidl_vec<RadioBandMode> modes;
4613        if (response == NULL || responseLen % sizeof(int) != 0) {
4614            RLOGE("getAvailableBandModesResponse Invalid response: NULL");
4615            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
4616        } else {
4617            int *pInt = (int *) response;
4618            int numInts = responseLen / sizeof(int);
4619            modes.resize(numInts);
4620            for (int i = 0; i < numInts; i++) {
4621                modes[i] = (RadioBandMode) pInt[i];
4622            }
4623        }
4624        Return<void> retStatus
4625                = radioService[slotId]->mRadioResponse->getAvailableBandModesResponse(responseInfo,
4626                modes);
4627        radioService[slotId]->checkReturnStatus(retStatus);
4628    } else {
4629        RLOGE("getAvailableBandModesResponse: radioService[%d]->mRadioResponse == NULL",
4630                slotId);
4631    }
4632
4633    return 0;
4634}
4635
4636int radio::sendEnvelopeResponse(int slotId,
4637                               int responseType, int serial, RIL_Errno e,
4638                               void *response, size_t responseLen) {
4639#if VDBG
4640    RLOGD("sendEnvelopeResponse: serial %d", serial);
4641#endif
4642
4643    if (radioService[slotId]->mRadioResponse != NULL) {
4644        RadioResponseInfo responseInfo = {};
4645        populateResponseInfo(responseInfo, serial, responseType, e);
4646        Return<void> retStatus
4647                = radioService[slotId]->mRadioResponse->sendEnvelopeResponse(responseInfo,
4648                convertCharPtrToHidlString((char *) response));
4649        radioService[slotId]->checkReturnStatus(retStatus);
4650    } else {
4651        RLOGE("sendEnvelopeResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4652    }
4653
4654    return 0;
4655}
4656
4657int radio::sendTerminalResponseToSimResponse(int slotId,
4658                                            int responseType, int serial, RIL_Errno e,
4659                                            void *response, size_t responseLen) {
4660#if VDBG
4661    RLOGD("sendTerminalResponseToSimResponse: serial %d", serial);
4662#endif
4663
4664    if (radioService[slotId]->mRadioResponse != NULL) {
4665        RadioResponseInfo responseInfo = {};
4666        populateResponseInfo(responseInfo, serial, responseType, e);
4667        Return<void> retStatus
4668                = radioService[slotId]->mRadioResponse->sendTerminalResponseToSimResponse(
4669                responseInfo);
4670        radioService[slotId]->checkReturnStatus(retStatus);
4671    } else {
4672        RLOGE("sendTerminalResponseToSimResponse: radioService[%d]->mRadioResponse == NULL",
4673                slotId);
4674    }
4675
4676    return 0;
4677}
4678
4679int radio::handleStkCallSetupRequestFromSimResponse(int slotId,
4680                                                   int responseType, int serial,
4681                                                   RIL_Errno e, void *response,
4682                                                   size_t responseLen) {
4683#if VDBG
4684    RLOGD("handleStkCallSetupRequestFromSimResponse: serial %d", serial);
4685#endif
4686
4687    if (radioService[slotId]->mRadioResponse != NULL) {
4688        RadioResponseInfo responseInfo = {};
4689        populateResponseInfo(responseInfo, serial, responseType, e);
4690        Return<void> retStatus
4691                = radioService[slotId]->mRadioResponse->handleStkCallSetupRequestFromSimResponse(
4692                responseInfo);
4693        radioService[slotId]->checkReturnStatus(retStatus);
4694    } else {
4695        RLOGE("handleStkCallSetupRequestFromSimResponse: radioService[%d]->mRadioResponse "
4696                "== NULL", slotId);
4697    }
4698
4699    return 0;
4700}
4701
4702int radio::explicitCallTransferResponse(int slotId,
4703                                       int responseType, int serial, RIL_Errno e,
4704                                       void *response, size_t responseLen) {
4705#if VDBG
4706    RLOGD("explicitCallTransferResponse: serial %d", serial);
4707#endif
4708
4709    if (radioService[slotId]->mRadioResponse != NULL) {
4710        RadioResponseInfo responseInfo = {};
4711        populateResponseInfo(responseInfo, serial, responseType, e);
4712        Return<void> retStatus
4713                = radioService[slotId]->mRadioResponse->explicitCallTransferResponse(responseInfo);
4714        radioService[slotId]->checkReturnStatus(retStatus);
4715    } else {
4716        RLOGE("explicitCallTransferResponse: radioService[%d]->mRadioResponse == NULL",
4717                slotId);
4718    }
4719
4720    return 0;
4721}
4722
4723int radio::setPreferredNetworkTypeResponse(int slotId,
4724                                 int responseType, int serial, RIL_Errno e,
4725                                 void *response, size_t responseLen) {
4726#if VDBG
4727    RLOGD("setPreferredNetworkTypeResponse: serial %d", serial);
4728#endif
4729
4730    if (radioService[slotId]->mRadioResponse != NULL) {
4731        RadioResponseInfo responseInfo = {};
4732        populateResponseInfo(responseInfo, serial, responseType, e);
4733        Return<void> retStatus
4734                = radioService[slotId]->mRadioResponse->setPreferredNetworkTypeResponse(
4735                responseInfo);
4736        radioService[slotId]->checkReturnStatus(retStatus);
4737    } else {
4738        RLOGE("setPreferredNetworkTypeResponse: radioService[%d]->mRadioResponse == NULL",
4739                slotId);
4740    }
4741
4742    return 0;
4743}
4744
4745
4746int radio::getPreferredNetworkTypeResponse(int slotId,
4747                                          int responseType, int serial, RIL_Errno e,
4748                                          void *response, size_t responseLen) {
4749#if VDBG
4750    RLOGD("getPreferredNetworkTypeResponse: serial %d", serial);
4751#endif
4752
4753    if (radioService[slotId]->mRadioResponse != NULL) {
4754        RadioResponseInfo responseInfo = {};
4755        int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen);
4756        Return<void> retStatus
4757                = radioService[slotId]->mRadioResponse->getPreferredNetworkTypeResponse(
4758                responseInfo, (PreferredNetworkType) ret);
4759        radioService[slotId]->checkReturnStatus(retStatus);
4760    } else {
4761        RLOGE("getPreferredNetworkTypeResponse: radioService[%d]->mRadioResponse == NULL",
4762                slotId);
4763    }
4764
4765    return 0;
4766}
4767
4768int radio::getNeighboringCidsResponse(int slotId,
4769                                     int responseType, int serial, RIL_Errno e,
4770                                     void *response, size_t responseLen) {
4771#if VDBG
4772    RLOGD("getNeighboringCidsResponse: serial %d", serial);
4773#endif
4774
4775    if (radioService[slotId]->mRadioResponse != NULL) {
4776        RadioResponseInfo responseInfo = {};
4777        populateResponseInfo(responseInfo, serial, responseType, e);
4778        hidl_vec<NeighboringCell> cells;
4779
4780        if (response == NULL || responseLen % sizeof(RIL_NeighboringCell *) != 0) {
4781            RLOGE("getNeighboringCidsResponse Invalid response: NULL");
4782            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
4783        } else {
4784            int num = responseLen / sizeof(RIL_NeighboringCell *);
4785            cells.resize(num);
4786            for (int i = 0 ; i < num; i++) {
4787                RIL_NeighboringCell *resp = ((RIL_NeighboringCell **) response)[i];
4788                cells[i].cid = convertCharPtrToHidlString(resp->cid);
4789                cells[i].rssi = resp->rssi;
4790            }
4791        }
4792
4793        Return<void> retStatus
4794                = radioService[slotId]->mRadioResponse->getNeighboringCidsResponse(responseInfo,
4795                cells);
4796        radioService[slotId]->checkReturnStatus(retStatus);
4797    } else {
4798        RLOGE("getNeighboringCidsResponse: radioService[%d]->mRadioResponse == NULL",
4799                slotId);
4800    }
4801
4802    return 0;
4803}
4804
4805int radio::setLocationUpdatesResponse(int slotId,
4806                                     int responseType, int serial, RIL_Errno e,
4807                                     void *response, size_t responseLen) {
4808#if VDBG
4809    RLOGD("setLocationUpdatesResponse: serial %d", serial);
4810#endif
4811
4812    if (radioService[slotId]->mRadioResponse != NULL) {
4813        RadioResponseInfo responseInfo = {};
4814        populateResponseInfo(responseInfo, serial, responseType, e);
4815        Return<void> retStatus
4816                = radioService[slotId]->mRadioResponse->setLocationUpdatesResponse(responseInfo);
4817        radioService[slotId]->checkReturnStatus(retStatus);
4818    } else {
4819        RLOGE("setLocationUpdatesResponse: radioService[%d]->mRadioResponse == NULL",
4820                slotId);
4821    }
4822
4823    return 0;
4824}
4825
4826int radio::setCdmaSubscriptionSourceResponse(int slotId,
4827                                 int responseType, int serial, RIL_Errno e,
4828                                 void *response, size_t responseLen) {
4829#if VDBG
4830    RLOGD("setCdmaSubscriptionSourceResponse: serial %d", serial);
4831#endif
4832
4833    if (radioService[slotId]->mRadioResponse != NULL) {
4834        RadioResponseInfo responseInfo = {};
4835        populateResponseInfo(responseInfo, serial, responseType, e);
4836        Return<void> retStatus
4837                = radioService[slotId]->mRadioResponse->setCdmaSubscriptionSourceResponse(
4838                responseInfo);
4839        radioService[slotId]->checkReturnStatus(retStatus);
4840    } else {
4841        RLOGE("setCdmaSubscriptionSourceResponse: radioService[%d]->mRadioResponse == NULL",
4842                slotId);
4843    }
4844
4845    return 0;
4846}
4847
4848int radio::setCdmaRoamingPreferenceResponse(int slotId,
4849                                 int responseType, int serial, RIL_Errno e,
4850                                 void *response, size_t responseLen) {
4851#if VDBG
4852    RLOGD("setCdmaRoamingPreferenceResponse: serial %d", serial);
4853#endif
4854
4855    if (radioService[slotId]->mRadioResponse != NULL) {
4856        RadioResponseInfo responseInfo = {};
4857        populateResponseInfo(responseInfo, serial, responseType, e);
4858        Return<void> retStatus
4859                = radioService[slotId]->mRadioResponse->setCdmaRoamingPreferenceResponse(
4860                responseInfo);
4861        radioService[slotId]->checkReturnStatus(retStatus);
4862    } else {
4863        RLOGE("setCdmaRoamingPreferenceResponse: radioService[%d]->mRadioResponse == NULL",
4864                slotId);
4865    }
4866
4867    return 0;
4868}
4869
4870int radio::getCdmaRoamingPreferenceResponse(int slotId,
4871                                           int responseType, int serial, RIL_Errno e,
4872                                           void *response, size_t responseLen) {
4873#if VDBG
4874    RLOGD("getCdmaRoamingPreferenceResponse: serial %d", serial);
4875#endif
4876
4877    if (radioService[slotId]->mRadioResponse != NULL) {
4878        RadioResponseInfo responseInfo = {};
4879        int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen);
4880        Return<void> retStatus
4881                = radioService[slotId]->mRadioResponse->getCdmaRoamingPreferenceResponse(
4882                responseInfo, (CdmaRoamingType) ret);
4883        radioService[slotId]->checkReturnStatus(retStatus);
4884    } else {
4885        RLOGE("getCdmaRoamingPreferenceResponse: radioService[%d]->mRadioResponse == NULL",
4886                slotId);
4887    }
4888
4889    return 0;
4890}
4891
4892int radio::setTTYModeResponse(int slotId,
4893                             int responseType, int serial, RIL_Errno e,
4894                             void *response, size_t responseLen) {
4895#if VDBG
4896    RLOGD("setTTYModeResponse: serial %d", serial);
4897#endif
4898
4899    if (radioService[slotId]->mRadioResponse != NULL) {
4900        RadioResponseInfo responseInfo = {};
4901        populateResponseInfo(responseInfo, serial, responseType, e);
4902        Return<void> retStatus
4903                = radioService[slotId]->mRadioResponse->setTTYModeResponse(responseInfo);
4904        radioService[slotId]->checkReturnStatus(retStatus);
4905    } else {
4906        RLOGE("setTTYModeResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4907    }
4908
4909    return 0;
4910}
4911
4912int radio::getTTYModeResponse(int slotId,
4913                             int responseType, int serial, RIL_Errno e,
4914                             void *response, size_t responseLen) {
4915#if VDBG
4916    RLOGD("getTTYModeResponse: serial %d", serial);
4917#endif
4918
4919    if (radioService[slotId]->mRadioResponse != NULL) {
4920        RadioResponseInfo responseInfo = {};
4921        int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen);
4922        Return<void> retStatus
4923                = radioService[slotId]->mRadioResponse->getTTYModeResponse(responseInfo,
4924                (TtyMode) ret);
4925        radioService[slotId]->checkReturnStatus(retStatus);
4926    } else {
4927        RLOGE("getTTYModeResponse: radioService[%d]->mRadioResponse == NULL", slotId);
4928    }
4929
4930    return 0;
4931}
4932
4933int radio::setPreferredVoicePrivacyResponse(int slotId,
4934                                 int responseType, int serial, RIL_Errno e,
4935                                 void *response, size_t responseLen) {
4936#if VDBG
4937    RLOGD("setPreferredVoicePrivacyResponse: serial %d", serial);
4938#endif
4939
4940    if (radioService[slotId]->mRadioResponse != NULL) {
4941        RadioResponseInfo responseInfo = {};
4942        populateResponseInfo(responseInfo, serial, responseType, e);
4943        Return<void> retStatus
4944                = radioService[slotId]->mRadioResponse->setPreferredVoicePrivacyResponse(
4945                responseInfo);
4946        radioService[slotId]->checkReturnStatus(retStatus);
4947    } else {
4948        RLOGE("setPreferredVoicePrivacyResponse: radioService[%d]->mRadioResponse == NULL",
4949                slotId);
4950    }
4951
4952    return 0;
4953}
4954
4955int radio::getPreferredVoicePrivacyResponse(int slotId,
4956                                           int responseType, int serial, RIL_Errno e,
4957                                           void *response, size_t responseLen) {
4958#if VDBG
4959    RLOGD("getPreferredVoicePrivacyResponse: serial %d", serial);
4960#endif
4961
4962    if (radioService[slotId]->mRadioResponse != NULL) {
4963        RadioResponseInfo responseInfo = {};
4964        populateResponseInfo(responseInfo, serial, responseType, e);
4965        bool enable = false;
4966        int numInts = responseLen / sizeof(int);
4967        if (response == NULL || numInts != 1) {
4968            RLOGE("getPreferredVoicePrivacyResponse Invalid response: NULL");
4969            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
4970        } else {
4971            int *pInt = (int *) response;
4972            enable = pInt[0] == 1 ? true : false;
4973        }
4974        Return<void> retStatus
4975                = radioService[slotId]->mRadioResponse->getPreferredVoicePrivacyResponse(
4976                responseInfo, enable);
4977        radioService[slotId]->checkReturnStatus(retStatus);
4978    } else {
4979        RLOGE("getPreferredVoicePrivacyResponse: radioService[%d]->mRadioResponse == NULL",
4980                slotId);
4981    }
4982
4983    return 0;
4984}
4985
4986int radio::sendCDMAFeatureCodeResponse(int slotId,
4987                                 int responseType, int serial, RIL_Errno e,
4988                                 void *response, size_t responseLen) {
4989#if VDBG
4990    RLOGD("sendCDMAFeatureCodeResponse: serial %d", serial);
4991#endif
4992
4993    if (radioService[slotId]->mRadioResponse != NULL) {
4994        RadioResponseInfo responseInfo = {};
4995        populateResponseInfo(responseInfo, serial, responseType, e);
4996        Return<void> retStatus
4997                = radioService[slotId]->mRadioResponse->sendCDMAFeatureCodeResponse(responseInfo);
4998        radioService[slotId]->checkReturnStatus(retStatus);
4999    } else {
5000        RLOGE("sendCDMAFeatureCodeResponse: radioService[%d]->mRadioResponse == NULL",
5001                slotId);
5002    }
5003
5004    return 0;
5005}
5006
5007int radio::sendBurstDtmfResponse(int slotId,
5008                                 int responseType, int serial, RIL_Errno e,
5009                                 void *response, size_t responseLen) {
5010#if VDBG
5011    RLOGD("sendBurstDtmfResponse: serial %d", serial);
5012#endif
5013
5014    if (radioService[slotId]->mRadioResponse != NULL) {
5015        RadioResponseInfo responseInfo = {};
5016        populateResponseInfo(responseInfo, serial, responseType, e);
5017        Return<void> retStatus
5018                = radioService[slotId]->mRadioResponse->sendBurstDtmfResponse(responseInfo);
5019        radioService[slotId]->checkReturnStatus(retStatus);
5020    } else {
5021        RLOGE("sendBurstDtmfResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5022    }
5023
5024    return 0;
5025}
5026
5027int radio::sendCdmaSmsResponse(int slotId,
5028                              int responseType, int serial, RIL_Errno e, void *response,
5029                              size_t responseLen) {
5030#if VDBG
5031    RLOGD("sendCdmaSmsResponse: serial %d", serial);
5032#endif
5033
5034    if (radioService[slotId]->mRadioResponse != NULL) {
5035        RadioResponseInfo responseInfo = {};
5036        SendSmsResult result = makeSendSmsResult(responseInfo, serial, responseType, e, response,
5037                responseLen);
5038
5039        Return<void> retStatus
5040                = radioService[slotId]->mRadioResponse->sendCdmaSmsResponse(responseInfo, result);
5041        radioService[slotId]->checkReturnStatus(retStatus);
5042    } else {
5043        RLOGE("sendCdmaSmsResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5044    }
5045
5046    return 0;
5047}
5048
5049int radio::acknowledgeLastIncomingCdmaSmsResponse(int slotId,
5050                                                 int responseType, int serial, RIL_Errno e,
5051                                                 void *response, size_t responseLen) {
5052#if VDBG
5053    RLOGD("acknowledgeLastIncomingCdmaSmsResponse: serial %d", serial);
5054#endif
5055
5056    if (radioService[slotId]->mRadioResponse != NULL) {
5057        RadioResponseInfo responseInfo = {};
5058        populateResponseInfo(responseInfo, serial, responseType, e);
5059        Return<void> retStatus
5060                = radioService[slotId]->mRadioResponse->acknowledgeLastIncomingCdmaSmsResponse(
5061                responseInfo);
5062        radioService[slotId]->checkReturnStatus(retStatus);
5063    } else {
5064        RLOGE("acknowledgeLastIncomingCdmaSmsResponse: radioService[%d]->mRadioResponse "
5065                "== NULL", slotId);
5066    }
5067
5068    return 0;
5069}
5070
5071int radio::getGsmBroadcastConfigResponse(int slotId,
5072                                        int responseType, int serial, RIL_Errno e,
5073                                        void *response, size_t responseLen) {
5074#if VDBG
5075    RLOGD("getGsmBroadcastConfigResponse: serial %d", serial);
5076#endif
5077
5078    if (radioService[slotId]->mRadioResponse != NULL) {
5079        RadioResponseInfo responseInfo = {};
5080        populateResponseInfo(responseInfo, serial, responseType, e);
5081        hidl_vec<GsmBroadcastSmsConfigInfo> configs;
5082
5083        if (response == NULL || responseLen % sizeof(RIL_GSM_BroadcastSmsConfigInfo *) != 0) {
5084            RLOGE("getGsmBroadcastConfigResponse Invalid response: NULL");
5085            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
5086        } else {
5087            int num = responseLen / sizeof(RIL_GSM_BroadcastSmsConfigInfo *);
5088            configs.resize(num);
5089            for (int i = 0 ; i < num; i++) {
5090                RIL_GSM_BroadcastSmsConfigInfo *resp =
5091                        ((RIL_GSM_BroadcastSmsConfigInfo **) response)[i];
5092                configs[i].fromServiceId = resp->fromServiceId;
5093                configs[i].toServiceId = resp->toServiceId;
5094                configs[i].fromCodeScheme = resp->fromCodeScheme;
5095                configs[i].toCodeScheme = resp->toCodeScheme;
5096                configs[i].selected = resp->selected == 1 ? true : false;
5097            }
5098        }
5099
5100        Return<void> retStatus
5101                = radioService[slotId]->mRadioResponse->getGsmBroadcastConfigResponse(responseInfo,
5102                configs);
5103        radioService[slotId]->checkReturnStatus(retStatus);
5104    } else {
5105        RLOGE("getGsmBroadcastConfigResponse: radioService[%d]->mRadioResponse == NULL",
5106                slotId);
5107    }
5108
5109    return 0;
5110}
5111
5112int radio::setGsmBroadcastConfigResponse(int slotId,
5113                                        int responseType, int serial, RIL_Errno e,
5114                                        void *response, size_t responseLen) {
5115#if VDBG
5116    RLOGD("setGsmBroadcastConfigResponse: serial %d", serial);
5117#endif
5118
5119    if (radioService[slotId]->mRadioResponse != NULL) {
5120        RadioResponseInfo responseInfo = {};
5121        populateResponseInfo(responseInfo, serial, responseType, e);
5122        Return<void> retStatus
5123                = radioService[slotId]->mRadioResponse->setGsmBroadcastConfigResponse(responseInfo);
5124        radioService[slotId]->checkReturnStatus(retStatus);
5125    } else {
5126        RLOGE("setGsmBroadcastConfigResponse: radioService[%d]->mRadioResponse == NULL",
5127                slotId);
5128    }
5129
5130    return 0;
5131}
5132
5133int radio::setGsmBroadcastActivationResponse(int slotId,
5134                                            int responseType, int serial, RIL_Errno e,
5135                                            void *response, size_t responseLen) {
5136#if VDBG
5137    RLOGD("setGsmBroadcastActivationResponse: serial %d", serial);
5138#endif
5139
5140    if (radioService[slotId]->mRadioResponse != NULL) {
5141        RadioResponseInfo responseInfo = {};
5142        populateResponseInfo(responseInfo, serial, responseType, e);
5143        Return<void> retStatus
5144                = radioService[slotId]->mRadioResponse->setGsmBroadcastActivationResponse(
5145                responseInfo);
5146        radioService[slotId]->checkReturnStatus(retStatus);
5147    } else {
5148        RLOGE("setGsmBroadcastActivationResponse: radioService[%d]->mRadioResponse == NULL",
5149                slotId);
5150    }
5151
5152    return 0;
5153}
5154
5155int radio::getCdmaBroadcastConfigResponse(int slotId,
5156                                         int responseType, int serial, RIL_Errno e,
5157                                         void *response, size_t responseLen) {
5158#if VDBG
5159    RLOGD("getCdmaBroadcastConfigResponse: serial %d", serial);
5160#endif
5161
5162    if (radioService[slotId]->mRadioResponse != NULL) {
5163        RadioResponseInfo responseInfo = {};
5164        populateResponseInfo(responseInfo, serial, responseType, e);
5165        hidl_vec<CdmaBroadcastSmsConfigInfo> configs;
5166
5167        if (response == NULL || responseLen % sizeof(RIL_CDMA_BroadcastSmsConfigInfo *) != 0) {
5168            RLOGE("getCdmaBroadcastConfigResponse Invalid response: NULL");
5169            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
5170        } else {
5171            int num = responseLen / sizeof(RIL_CDMA_BroadcastSmsConfigInfo *);
5172            configs.resize(num);
5173            for (int i = 0 ; i < num; i++) {
5174                RIL_CDMA_BroadcastSmsConfigInfo *resp =
5175                        ((RIL_CDMA_BroadcastSmsConfigInfo **) response)[i];
5176                configs[i].serviceCategory = resp->service_category;
5177                configs[i].language = resp->language;
5178                configs[i].selected = resp->selected == 1 ? true : false;
5179            }
5180        }
5181
5182        Return<void> retStatus
5183                = radioService[slotId]->mRadioResponse->getCdmaBroadcastConfigResponse(responseInfo,
5184                configs);
5185        radioService[slotId]->checkReturnStatus(retStatus);
5186    } else {
5187        RLOGE("getCdmaBroadcastConfigResponse: radioService[%d]->mRadioResponse == NULL",
5188                slotId);
5189    }
5190
5191    return 0;
5192}
5193
5194int radio::setCdmaBroadcastConfigResponse(int slotId,
5195                                         int responseType, int serial, RIL_Errno e,
5196                                         void *response, size_t responseLen) {
5197#if VDBG
5198    RLOGD("setCdmaBroadcastConfigResponse: serial %d", serial);
5199#endif
5200
5201    if (radioService[slotId]->mRadioResponse != NULL) {
5202        RadioResponseInfo responseInfo = {};
5203        populateResponseInfo(responseInfo, serial, responseType, e);
5204        Return<void> retStatus
5205                = radioService[slotId]->mRadioResponse->setCdmaBroadcastConfigResponse(
5206                responseInfo);
5207        radioService[slotId]->checkReturnStatus(retStatus);
5208    } else {
5209        RLOGE("setCdmaBroadcastConfigResponse: radioService[%d]->mRadioResponse == NULL",
5210                slotId);
5211    }
5212
5213    return 0;
5214}
5215
5216int radio::setCdmaBroadcastActivationResponse(int slotId,
5217                                             int responseType, int serial, RIL_Errno e,
5218                                             void *response, size_t responseLen) {
5219#if VDBG
5220    RLOGD("setCdmaBroadcastActivationResponse: serial %d", serial);
5221#endif
5222
5223    if (radioService[slotId]->mRadioResponse != NULL) {
5224        RadioResponseInfo responseInfo = {};
5225        populateResponseInfo(responseInfo, serial, responseType, e);
5226        Return<void> retStatus
5227                = radioService[slotId]->mRadioResponse->setCdmaBroadcastActivationResponse(
5228                responseInfo);
5229        radioService[slotId]->checkReturnStatus(retStatus);
5230    } else {
5231        RLOGE("setCdmaBroadcastActivationResponse: radioService[%d]->mRadioResponse == NULL",
5232                slotId);
5233    }
5234
5235    return 0;
5236}
5237
5238int radio::getCDMASubscriptionResponse(int slotId,
5239                                      int responseType, int serial, RIL_Errno e, void *response,
5240                                      size_t responseLen) {
5241#if VDBG
5242    RLOGD("getCDMASubscriptionResponse: serial %d", serial);
5243#endif
5244
5245    if (radioService[slotId]->mRadioResponse != NULL) {
5246        RadioResponseInfo responseInfo = {};
5247        populateResponseInfo(responseInfo, serial, responseType, e);
5248
5249        int numStrings = responseLen / sizeof(char *);
5250        hidl_string emptyString;
5251        if (response == NULL || numStrings != 5) {
5252            RLOGE("getOperatorResponse Invalid response: NULL");
5253            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
5254            Return<void> retStatus
5255                    = radioService[slotId]->mRadioResponse->getCDMASubscriptionResponse(
5256                    responseInfo, emptyString, emptyString, emptyString, emptyString, emptyString);
5257            radioService[slotId]->checkReturnStatus(retStatus);
5258        } else {
5259            char **resp = (char **) response;
5260            Return<void> retStatus
5261                    = radioService[slotId]->mRadioResponse->getCDMASubscriptionResponse(
5262                    responseInfo,
5263                    convertCharPtrToHidlString(resp[0]),
5264                    convertCharPtrToHidlString(resp[1]),
5265                    convertCharPtrToHidlString(resp[2]),
5266                    convertCharPtrToHidlString(resp[3]),
5267                    convertCharPtrToHidlString(resp[4]));
5268            radioService[slotId]->checkReturnStatus(retStatus);
5269        }
5270    } else {
5271        RLOGE("getCDMASubscriptionResponse: radioService[%d]->mRadioResponse == NULL",
5272                slotId);
5273    }
5274
5275    return 0;
5276}
5277
5278int radio::writeSmsToRuimResponse(int slotId,
5279                                 int responseType, int serial, RIL_Errno e,
5280                                 void *response, size_t responseLen) {
5281#if VDBG
5282    RLOGD("writeSmsToRuimResponse: serial %d", serial);
5283#endif
5284
5285    if (radioService[slotId]->mRadioResponse != NULL) {
5286        RadioResponseInfo responseInfo = {};
5287        int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen);
5288        Return<void> retStatus
5289                = radioService[slotId]->mRadioResponse->writeSmsToRuimResponse(responseInfo, ret);
5290        radioService[slotId]->checkReturnStatus(retStatus);
5291    } else {
5292        RLOGE("writeSmsToRuimResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5293    }
5294
5295    return 0;
5296}
5297
5298int radio::deleteSmsOnRuimResponse(int slotId,
5299                                  int responseType, int serial, RIL_Errno e,
5300                                  void *response, size_t responseLen) {
5301#if VDBG
5302    RLOGD("deleteSmsOnRuimResponse: serial %d", serial);
5303#endif
5304
5305    if (radioService[slotId]->mRadioResponse != NULL) {
5306        RadioResponseInfo responseInfo = {};
5307        populateResponseInfo(responseInfo, serial, responseType, e);
5308        Return<void> retStatus
5309                = radioService[slotId]->mRadioResponse->deleteSmsOnRuimResponse(responseInfo);
5310        radioService[slotId]->checkReturnStatus(retStatus);
5311    } else {
5312        RLOGE("deleteSmsOnRuimResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5313    }
5314
5315    return 0;
5316}
5317
5318int radio::getDeviceIdentityResponse(int slotId,
5319                                    int responseType, int serial, RIL_Errno e, void *response,
5320                                    size_t responseLen) {
5321#if VDBG
5322    RLOGD("getDeviceIdentityResponse: serial %d", serial);
5323#endif
5324
5325    if (radioService[slotId]->mRadioResponse != NULL) {
5326        RadioResponseInfo responseInfo = {};
5327        populateResponseInfo(responseInfo, serial, responseType, e);
5328
5329        int numStrings = responseLen / sizeof(char *);
5330        hidl_string emptyString;
5331        if (response == NULL || numStrings != 4) {
5332            RLOGE("getDeviceIdentityResponse Invalid response: NULL");
5333            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
5334            Return<void> retStatus
5335                    = radioService[slotId]->mRadioResponse->getDeviceIdentityResponse(responseInfo,
5336                    emptyString, emptyString, emptyString, emptyString);
5337            radioService[slotId]->checkReturnStatus(retStatus);
5338        } else {
5339            char **resp = (char **) response;
5340            Return<void> retStatus
5341                    = radioService[slotId]->mRadioResponse->getDeviceIdentityResponse(responseInfo,
5342                    convertCharPtrToHidlString(resp[0]),
5343                    convertCharPtrToHidlString(resp[1]),
5344                    convertCharPtrToHidlString(resp[2]),
5345                    convertCharPtrToHidlString(resp[3]));
5346            radioService[slotId]->checkReturnStatus(retStatus);
5347        }
5348    } else {
5349        RLOGE("getDeviceIdentityResponse: radioService[%d]->mRadioResponse == NULL",
5350                slotId);
5351    }
5352
5353    return 0;
5354}
5355
5356int radio::exitEmergencyCallbackModeResponse(int slotId,
5357                                            int responseType, int serial, RIL_Errno e,
5358                                            void *response, size_t responseLen) {
5359#if VDBG
5360    RLOGD("exitEmergencyCallbackModeResponse: serial %d", serial);
5361#endif
5362
5363    if (radioService[slotId]->mRadioResponse != NULL) {
5364        RadioResponseInfo responseInfo = {};
5365        populateResponseInfo(responseInfo, serial, responseType, e);
5366        Return<void> retStatus
5367                = radioService[slotId]->mRadioResponse->exitEmergencyCallbackModeResponse(
5368                responseInfo);
5369        radioService[slotId]->checkReturnStatus(retStatus);
5370    } else {
5371        RLOGE("exitEmergencyCallbackModeResponse: radioService[%d]->mRadioResponse == NULL",
5372                slotId);
5373    }
5374
5375    return 0;
5376}
5377
5378int radio::getSmscAddressResponse(int slotId,
5379                                  int responseType, int serial, RIL_Errno e,
5380                                  void *response, size_t responseLen) {
5381#if VDBG
5382    RLOGD("getSmscAddressResponse: serial %d", serial);
5383#endif
5384
5385    if (radioService[slotId]->mRadioResponse != NULL) {
5386        RadioResponseInfo responseInfo = {};
5387        populateResponseInfo(responseInfo, serial, responseType, e);
5388        Return<void> retStatus
5389                = radioService[slotId]->mRadioResponse->getSmscAddressResponse(responseInfo,
5390                convertCharPtrToHidlString((char *) response));
5391        radioService[slotId]->checkReturnStatus(retStatus);
5392    } else {
5393        RLOGE("getSmscAddressResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5394    }
5395
5396    return 0;
5397}
5398
5399int radio::setSmscAddressResponse(int slotId,
5400                                             int responseType, int serial, RIL_Errno e,
5401                                             void *response, size_t responseLen) {
5402#if VDBG
5403    RLOGD("setSmscAddressResponse: serial %d", serial);
5404#endif
5405
5406    if (radioService[slotId]->mRadioResponse != NULL) {
5407        RadioResponseInfo responseInfo = {};
5408        populateResponseInfo(responseInfo, serial, responseType, e);
5409        Return<void> retStatus
5410                = radioService[slotId]->mRadioResponse->setSmscAddressResponse(responseInfo);
5411        radioService[slotId]->checkReturnStatus(retStatus);
5412    } else {
5413        RLOGE("setSmscAddressResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5414    }
5415
5416    return 0;
5417}
5418
5419int radio::reportSmsMemoryStatusResponse(int slotId,
5420                                        int responseType, int serial, RIL_Errno e,
5421                                        void *response, size_t responseLen) {
5422#if VDBG
5423    RLOGD("reportSmsMemoryStatusResponse: serial %d", serial);
5424#endif
5425
5426    if (radioService[slotId]->mRadioResponse != NULL) {
5427        RadioResponseInfo responseInfo = {};
5428        populateResponseInfo(responseInfo, serial, responseType, e);
5429        Return<void> retStatus
5430                = radioService[slotId]->mRadioResponse->reportSmsMemoryStatusResponse(responseInfo);
5431        radioService[slotId]->checkReturnStatus(retStatus);
5432    } else {
5433        RLOGE("reportSmsMemoryStatusResponse: radioService[%d]->mRadioResponse == NULL",
5434                slotId);
5435    }
5436
5437    return 0;
5438}
5439
5440int radio::reportStkServiceIsRunningResponse(int slotId,
5441                                             int responseType, int serial, RIL_Errno e,
5442                                             void *response, size_t responseLen) {
5443#if VDBG
5444    RLOGD("reportStkServiceIsRunningResponse: serial %d", serial);
5445#endif
5446
5447    if (radioService[slotId]->mRadioResponse != NULL) {
5448        RadioResponseInfo responseInfo = {};
5449        populateResponseInfo(responseInfo, serial, responseType, e);
5450        Return<void> retStatus = radioService[slotId]->mRadioResponse->
5451                reportStkServiceIsRunningResponse(responseInfo);
5452        radioService[slotId]->checkReturnStatus(retStatus);
5453    } else {
5454        RLOGE("reportStkServiceIsRunningResponse: radioService[%d]->mRadioResponse == NULL",
5455                slotId);
5456    }
5457
5458    return 0;
5459}
5460
5461int radio::getCdmaSubscriptionSourceResponse(int slotId,
5462                                            int responseType, int serial, RIL_Errno e,
5463                                            void *response, size_t responseLen) {
5464#if VDBG
5465    RLOGD("getCdmaSubscriptionSourceResponse: serial %d", serial);
5466#endif
5467
5468    if (radioService[slotId]->mRadioResponse != NULL) {
5469        RadioResponseInfo responseInfo = {};
5470        int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen);
5471        Return<void> retStatus
5472                = radioService[slotId]->mRadioResponse->getCdmaSubscriptionSourceResponse(
5473                responseInfo, (CdmaSubscriptionSource) ret);
5474        radioService[slotId]->checkReturnStatus(retStatus);
5475    } else {
5476        RLOGE("getCdmaSubscriptionSourceResponse: radioService[%d]->mRadioResponse == NULL",
5477                slotId);
5478    }
5479
5480    return 0;
5481}
5482
5483int radio::requestIsimAuthenticationResponse(int slotId,
5484                                            int responseType, int serial, RIL_Errno e,
5485                                            void *response, size_t responseLen) {
5486#if VDBG
5487    RLOGD("requestIsimAuthenticationResponse: serial %d", serial);
5488#endif
5489
5490    if (radioService[slotId]->mRadioResponse != NULL) {
5491        RadioResponseInfo responseInfo = {};
5492        populateResponseInfo(responseInfo, serial, responseType, e);
5493        Return<void> retStatus
5494                = radioService[slotId]->mRadioResponse->requestIsimAuthenticationResponse(
5495                responseInfo,
5496                convertCharPtrToHidlString((char *) response));
5497        radioService[slotId]->checkReturnStatus(retStatus);
5498    } else {
5499        RLOGE("requestIsimAuthenticationResponse: radioService[%d]->mRadioResponse == NULL",
5500                slotId);
5501    }
5502
5503    return 0;
5504}
5505
5506int radio::acknowledgeIncomingGsmSmsWithPduResponse(int slotId,
5507                                                   int responseType,
5508                                                   int serial, RIL_Errno e, void *response,
5509                                                   size_t responseLen) {
5510#if VDBG
5511    RLOGD("acknowledgeIncomingGsmSmsWithPduResponse: serial %d", serial);
5512#endif
5513
5514    if (radioService[slotId]->mRadioResponse != NULL) {
5515        RadioResponseInfo responseInfo = {};
5516        populateResponseInfo(responseInfo, serial, responseType, e);
5517        Return<void> retStatus
5518                = radioService[slotId]->mRadioResponse->acknowledgeIncomingGsmSmsWithPduResponse(
5519                responseInfo);
5520        radioService[slotId]->checkReturnStatus(retStatus);
5521    } else {
5522        RLOGE("acknowledgeIncomingGsmSmsWithPduResponse: radioService[%d]->mRadioResponse "
5523                "== NULL", slotId);
5524    }
5525
5526    return 0;
5527}
5528
5529int radio::sendEnvelopeWithStatusResponse(int slotId,
5530                                         int responseType, int serial, RIL_Errno e, void *response,
5531                                         size_t responseLen) {
5532#if VDBG
5533    RLOGD("sendEnvelopeWithStatusResponse: serial %d", serial);
5534#endif
5535
5536    if (radioService[slotId]->mRadioResponse != NULL) {
5537        RadioResponseInfo responseInfo = {};
5538        IccIoResult result = responseIccIo(responseInfo, serial, responseType, e,
5539                response, responseLen);
5540
5541        Return<void> retStatus
5542                = radioService[slotId]->mRadioResponse->sendEnvelopeWithStatusResponse(responseInfo,
5543                result);
5544        radioService[slotId]->checkReturnStatus(retStatus);
5545    } else {
5546        RLOGE("sendEnvelopeWithStatusResponse: radioService[%d]->mRadioResponse == NULL",
5547                slotId);
5548    }
5549
5550    return 0;
5551}
5552
5553int radio::getVoiceRadioTechnologyResponse(int slotId,
5554                                          int responseType, int serial, RIL_Errno e,
5555                                          void *response, size_t responseLen) {
5556#if VDBG
5557    RLOGD("getVoiceRadioTechnologyResponse: serial %d", serial);
5558#endif
5559
5560    if (radioService[slotId]->mRadioResponse != NULL) {
5561        RadioResponseInfo responseInfo = {};
5562        int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen);
5563        Return<void> retStatus
5564                = radioService[slotId]->mRadioResponse->getVoiceRadioTechnologyResponse(
5565                responseInfo, (RadioTechnology) ret);
5566        radioService[slotId]->checkReturnStatus(retStatus);
5567    } else {
5568        RLOGE("getVoiceRadioTechnologyResponse: radioService[%d]->mRadioResponse == NULL",
5569                slotId);
5570    }
5571
5572    return 0;
5573}
5574
5575int radio::getCellInfoListResponse(int slotId,
5576                                   int responseType,
5577                                   int serial, RIL_Errno e, void *response,
5578                                   size_t responseLen) {
5579#if VDBG
5580    RLOGD("getCellInfoListResponse: serial %d", serial);
5581#endif
5582
5583    if (radioService[slotId]->mRadioResponse != NULL) {
5584        RadioResponseInfo responseInfo = {};
5585        populateResponseInfo(responseInfo, serial, responseType, e);
5586
5587        hidl_vec<CellInfo> ret;
5588        if (response == NULL || responseLen % sizeof(RIL_CellInfo_v12) != 0) {
5589            RLOGE("getCellInfoListResponse: Invalid response");
5590            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
5591        } else {
5592            convertRilCellInfoListToHal(response, responseLen, ret);
5593        }
5594
5595        Return<void> retStatus = radioService[slotId]->mRadioResponse->getCellInfoListResponse(
5596                responseInfo, ret);
5597        radioService[slotId]->checkReturnStatus(retStatus);
5598    } else {
5599        RLOGE("getCellInfoListResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5600    }
5601
5602    return 0;
5603}
5604
5605int radio::setCellInfoListRateResponse(int slotId,
5606                                       int responseType,
5607                                       int serial, RIL_Errno e, void *response,
5608                                       size_t responseLen) {
5609#if VDBG
5610    RLOGD("setCellInfoListRateResponse: serial %d", serial);
5611#endif
5612
5613    if (radioService[slotId]->mRadioResponse != NULL) {
5614        RadioResponseInfo responseInfo = {};
5615        populateResponseInfo(responseInfo, serial, responseType, e);
5616        Return<void> retStatus
5617                = radioService[slotId]->mRadioResponse->setCellInfoListRateResponse(responseInfo);
5618        radioService[slotId]->checkReturnStatus(retStatus);
5619    } else {
5620        RLOGE("setCellInfoListRateResponse: radioService[%d]->mRadioResponse == NULL",
5621                slotId);
5622    }
5623
5624    return 0;
5625}
5626
5627int radio::setInitialAttachApnResponse(int slotId,
5628                                       int responseType, int serial, RIL_Errno e,
5629                                       void *response, size_t responseLen) {
5630#if VDBG
5631    RLOGD("setInitialAttachApnResponse: serial %d", serial);
5632#endif
5633
5634    if (radioService[slotId]->mRadioResponse != NULL) {
5635        RadioResponseInfo responseInfo = {};
5636        populateResponseInfo(responseInfo, serial, responseType, e);
5637        Return<void> retStatus
5638                = radioService[slotId]->mRadioResponse->setInitialAttachApnResponse(responseInfo);
5639        radioService[slotId]->checkReturnStatus(retStatus);
5640    } else {
5641        RLOGE("setInitialAttachApnResponse: radioService[%d]->mRadioResponse == NULL",
5642                slotId);
5643    }
5644
5645    return 0;
5646}
5647
5648int radio::getImsRegistrationStateResponse(int slotId,
5649                                           int responseType, int serial, RIL_Errno e,
5650                                           void *response, size_t responseLen) {
5651#if VDBG
5652    RLOGD("getImsRegistrationStateResponse: serial %d", serial);
5653#endif
5654
5655    if (radioService[slotId]->mRadioResponse != NULL) {
5656        RadioResponseInfo responseInfo = {};
5657        populateResponseInfo(responseInfo, serial, responseType, e);
5658        bool isRegistered = false;
5659        int ratFamily = 0;
5660        int numInts = responseLen / sizeof(int);
5661        if (response == NULL || numInts != 2) {
5662            RLOGE("getImsRegistrationStateResponse Invalid response: NULL");
5663            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
5664        } else {
5665            int *pInt = (int *) response;
5666            isRegistered = pInt[0] == 1 ? true : false;
5667            ratFamily = pInt[1];
5668        }
5669        Return<void> retStatus
5670                = radioService[slotId]->mRadioResponse->getImsRegistrationStateResponse(
5671                responseInfo, isRegistered, (RadioTechnologyFamily) ratFamily);
5672        radioService[slotId]->checkReturnStatus(retStatus);
5673    } else {
5674        RLOGE("getImsRegistrationStateResponse: radioService[%d]->mRadioResponse == NULL",
5675                slotId);
5676    }
5677
5678    return 0;
5679}
5680
5681int radio::sendImsSmsResponse(int slotId,
5682                              int responseType, int serial, RIL_Errno e, void *response,
5683                              size_t responseLen) {
5684#if VDBG
5685    RLOGD("sendImsSmsResponse: serial %d", serial);
5686#endif
5687
5688    if (radioService[slotId]->mRadioResponse != NULL) {
5689        RadioResponseInfo responseInfo = {};
5690        SendSmsResult result = makeSendSmsResult(responseInfo, serial, responseType, e, response,
5691                responseLen);
5692
5693        Return<void> retStatus
5694                = radioService[slotId]->mRadioResponse->sendImsSmsResponse(responseInfo, result);
5695        radioService[slotId]->checkReturnStatus(retStatus);
5696    } else {
5697        RLOGE("sendSmsResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5698    }
5699
5700    return 0;
5701}
5702
5703int radio::iccTransmitApduBasicChannelResponse(int slotId,
5704                                               int responseType, int serial, RIL_Errno e,
5705                                               void *response, size_t responseLen) {
5706#if VDBG
5707    RLOGD("iccTransmitApduBasicChannelResponse: serial %d", serial);
5708#endif
5709
5710    if (radioService[slotId]->mRadioResponse != NULL) {
5711        RadioResponseInfo responseInfo = {};
5712        IccIoResult result = responseIccIo(responseInfo, serial, responseType, e, response,
5713                responseLen);
5714
5715        Return<void> retStatus
5716                = radioService[slotId]->mRadioResponse->iccTransmitApduBasicChannelResponse(
5717                responseInfo, result);
5718        radioService[slotId]->checkReturnStatus(retStatus);
5719    } else {
5720        RLOGE("iccTransmitApduBasicChannelResponse: radioService[%d]->mRadioResponse "
5721                "== NULL", slotId);
5722    }
5723
5724    return 0;
5725}
5726
5727int radio::iccOpenLogicalChannelResponse(int slotId,
5728                                         int responseType, int serial, RIL_Errno e, void *response,
5729                                         size_t responseLen) {
5730#if VDBG
5731    RLOGD("iccOpenLogicalChannelResponse: serial %d", serial);
5732#endif
5733
5734    if (radioService[slotId]->mRadioResponse != NULL) {
5735        RadioResponseInfo responseInfo = {};
5736        populateResponseInfo(responseInfo, serial, responseType, e);
5737        int channelId = -1;
5738        hidl_vec<int8_t> selectResponse;
5739        int numInts = responseLen / sizeof(int);
5740        if (response == NULL || responseLen % sizeof(int) != 0) {
5741            RLOGE("iccOpenLogicalChannelResponse Invalid response: NULL");
5742            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
5743        } else {
5744            int *pInt = (int *) response;
5745            channelId = pInt[0];
5746            selectResponse.resize(numInts - 1);
5747            for (int i = 1; i < numInts; i++) {
5748                selectResponse[i - 1] = (int8_t) pInt[i];
5749            }
5750        }
5751        Return<void> retStatus
5752                = radioService[slotId]->mRadioResponse->iccOpenLogicalChannelResponse(responseInfo,
5753                channelId, selectResponse);
5754        radioService[slotId]->checkReturnStatus(retStatus);
5755    } else {
5756        RLOGE("iccOpenLogicalChannelResponse: radioService[%d]->mRadioResponse == NULL",
5757                slotId);
5758    }
5759
5760    return 0;
5761}
5762
5763int radio::iccCloseLogicalChannelResponse(int slotId,
5764                                          int responseType, int serial, RIL_Errno e,
5765                                          void *response, size_t responseLen) {
5766#if VDBG
5767    RLOGD("iccCloseLogicalChannelResponse: serial %d", serial);
5768#endif
5769
5770    if (radioService[slotId]->mRadioResponse != NULL) {
5771        RadioResponseInfo responseInfo = {};
5772        populateResponseInfo(responseInfo, serial, responseType, e);
5773        Return<void> retStatus
5774                = radioService[slotId]->mRadioResponse->iccCloseLogicalChannelResponse(
5775                responseInfo);
5776        radioService[slotId]->checkReturnStatus(retStatus);
5777    } else {
5778        RLOGE("iccCloseLogicalChannelResponse: radioService[%d]->mRadioResponse == NULL",
5779                slotId);
5780    }
5781
5782    return 0;
5783}
5784
5785int radio::iccTransmitApduLogicalChannelResponse(int slotId,
5786                                                 int responseType, int serial, RIL_Errno e,
5787                                                 void *response, size_t responseLen) {
5788#if VDBG
5789    RLOGD("iccTransmitApduLogicalChannelResponse: serial %d", serial);
5790#endif
5791
5792    if (radioService[slotId]->mRadioResponse != NULL) {
5793        RadioResponseInfo responseInfo = {};
5794        IccIoResult result = responseIccIo(responseInfo, serial, responseType, e, response,
5795                responseLen);
5796
5797        Return<void> retStatus
5798                = radioService[slotId]->mRadioResponse->iccTransmitApduLogicalChannelResponse(
5799                responseInfo, result);
5800        radioService[slotId]->checkReturnStatus(retStatus);
5801    } else {
5802        RLOGE("iccTransmitApduLogicalChannelResponse: radioService[%d]->mRadioResponse "
5803                "== NULL", slotId);
5804    }
5805
5806    return 0;
5807}
5808
5809int radio::nvReadItemResponse(int slotId,
5810                              int responseType, int serial, RIL_Errno e,
5811                              void *response, size_t responseLen) {
5812#if VDBG
5813    RLOGD("nvReadItemResponse: serial %d", serial);
5814#endif
5815
5816    if (radioService[slotId]->mRadioResponse != NULL) {
5817        RadioResponseInfo responseInfo = {};
5818        populateResponseInfo(responseInfo, serial, responseType, e);
5819        Return<void> retStatus = radioService[slotId]->mRadioResponse->nvReadItemResponse(
5820                responseInfo,
5821                convertCharPtrToHidlString((char *) response));
5822        radioService[slotId]->checkReturnStatus(retStatus);
5823    } else {
5824        RLOGE("nvReadItemResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5825    }
5826
5827    return 0;
5828}
5829
5830int radio::nvWriteItemResponse(int slotId,
5831                               int responseType, int serial, RIL_Errno e,
5832                               void *response, size_t responseLen) {
5833#if VDBG
5834    RLOGD("nvWriteItemResponse: serial %d", serial);
5835#endif
5836
5837    if (radioService[slotId]->mRadioResponse != NULL) {
5838        RadioResponseInfo responseInfo = {};
5839        populateResponseInfo(responseInfo, serial, responseType, e);
5840        Return<void> retStatus
5841                = radioService[slotId]->mRadioResponse->nvWriteItemResponse(responseInfo);
5842        radioService[slotId]->checkReturnStatus(retStatus);
5843    } else {
5844        RLOGE("nvWriteItemResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5845    }
5846
5847    return 0;
5848}
5849
5850int radio::nvWriteCdmaPrlResponse(int slotId,
5851                                  int responseType, int serial, RIL_Errno e,
5852                                  void *response, size_t responseLen) {
5853#if VDBG
5854    RLOGD("nvWriteCdmaPrlResponse: serial %d", serial);
5855#endif
5856
5857    if (radioService[slotId]->mRadioResponse != NULL) {
5858        RadioResponseInfo responseInfo = {};
5859        populateResponseInfo(responseInfo, serial, responseType, e);
5860        Return<void> retStatus
5861                = radioService[slotId]->mRadioResponse->nvWriteCdmaPrlResponse(responseInfo);
5862        radioService[slotId]->checkReturnStatus(retStatus);
5863    } else {
5864        RLOGE("nvWriteCdmaPrlResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5865    }
5866
5867    return 0;
5868}
5869
5870int radio::nvResetConfigResponse(int slotId,
5871                                 int responseType, int serial, RIL_Errno e,
5872                                 void *response, size_t responseLen) {
5873#if VDBG
5874    RLOGD("nvResetConfigResponse: serial %d", serial);
5875#endif
5876
5877    if (radioService[slotId]->mRadioResponse != NULL) {
5878        RadioResponseInfo responseInfo = {};
5879        populateResponseInfo(responseInfo, serial, responseType, e);
5880        Return<void> retStatus
5881                = radioService[slotId]->mRadioResponse->nvResetConfigResponse(responseInfo);
5882        radioService[slotId]->checkReturnStatus(retStatus);
5883    } else {
5884        RLOGE("nvResetConfigResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5885    }
5886
5887    return 0;
5888}
5889
5890int radio::setUiccSubscriptionResponse(int slotId,
5891                                       int responseType, int serial, RIL_Errno e,
5892                                       void *response, size_t responseLen) {
5893#if VDBG
5894    RLOGD("setUiccSubscriptionResponse: serial %d", serial);
5895#endif
5896
5897    if (radioService[slotId]->mRadioResponse != NULL) {
5898        RadioResponseInfo responseInfo = {};
5899        populateResponseInfo(responseInfo, serial, responseType, e);
5900        Return<void> retStatus
5901                = radioService[slotId]->mRadioResponse->setUiccSubscriptionResponse(responseInfo);
5902        radioService[slotId]->checkReturnStatus(retStatus);
5903    } else {
5904        RLOGE("setUiccSubscriptionResponse: radioService[%d]->mRadioResponse == NULL",
5905                slotId);
5906    }
5907
5908    return 0;
5909}
5910
5911int radio::setDataAllowedResponse(int slotId,
5912                                  int responseType, int serial, RIL_Errno e,
5913                                  void *response, size_t responseLen) {
5914#if VDBG
5915    RLOGD("setDataAllowedResponse: serial %d", serial);
5916#endif
5917
5918    if (radioService[slotId]->mRadioResponse != NULL) {
5919        RadioResponseInfo responseInfo = {};
5920        populateResponseInfo(responseInfo, serial, responseType, e);
5921        Return<void> retStatus
5922                = radioService[slotId]->mRadioResponse->setDataAllowedResponse(responseInfo);
5923        radioService[slotId]->checkReturnStatus(retStatus);
5924    } else {
5925        RLOGE("setDataAllowedResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5926    }
5927
5928    return 0;
5929}
5930
5931int radio::getHardwareConfigResponse(int slotId,
5932                                     int responseType, int serial, RIL_Errno e,
5933                                     void *response, size_t responseLen) {
5934#if VDBG
5935    RLOGD("getHardwareConfigResponse: serial %d", serial);
5936#endif
5937
5938    if (radioService[slotId]->mRadioResponse != NULL) {
5939        RadioResponseInfo responseInfo = {};
5940        populateResponseInfo(responseInfo, serial, responseType, e);
5941
5942        hidl_vec<HardwareConfig> result;
5943        if (response == NULL || responseLen % sizeof(RIL_HardwareConfig) != 0) {
5944            RLOGE("hardwareConfigChangedInd: invalid response");
5945            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
5946        } else {
5947            convertRilHardwareConfigListToHal(response, responseLen, result);
5948        }
5949
5950        Return<void> retStatus = radioService[slotId]->mRadioResponse->getHardwareConfigResponse(
5951                responseInfo, result);
5952        radioService[slotId]->checkReturnStatus(retStatus);
5953    } else {
5954        RLOGE("getHardwareConfigResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5955    }
5956
5957    return 0;
5958}
5959
5960int radio::requestIccSimAuthenticationResponse(int slotId,
5961                                               int responseType, int serial, RIL_Errno e,
5962                                               void *response, size_t responseLen) {
5963#if VDBG
5964    RLOGD("requestIccSimAuthenticationResponse: serial %d", serial);
5965#endif
5966
5967    if (radioService[slotId]->mRadioResponse != NULL) {
5968        RadioResponseInfo responseInfo = {};
5969        IccIoResult result = responseIccIo(responseInfo, serial, responseType, e, response,
5970                responseLen);
5971
5972        Return<void> retStatus
5973                = radioService[slotId]->mRadioResponse->requestIccSimAuthenticationResponse(
5974                responseInfo, result);
5975        radioService[slotId]->checkReturnStatus(retStatus);
5976    } else {
5977        RLOGE("requestIccSimAuthenticationResponse: radioService[%d]->mRadioResponse "
5978                "== NULL", slotId);
5979    }
5980
5981    return 0;
5982}
5983
5984int radio::setDataProfileResponse(int slotId,
5985                                  int responseType, int serial, RIL_Errno e,
5986                                  void *response, size_t responseLen) {
5987#if VDBG
5988    RLOGD("setDataProfileResponse: serial %d", serial);
5989#endif
5990
5991    if (radioService[slotId]->mRadioResponse != NULL) {
5992        RadioResponseInfo responseInfo = {};
5993        populateResponseInfo(responseInfo, serial, responseType, e);
5994        Return<void> retStatus
5995                = radioService[slotId]->mRadioResponse->setDataProfileResponse(responseInfo);
5996        radioService[slotId]->checkReturnStatus(retStatus);
5997    } else {
5998        RLOGE("setDataProfileResponse: radioService[%d]->mRadioResponse == NULL", slotId);
5999    }
6000
6001    return 0;
6002}
6003
6004int radio::requestShutdownResponse(int slotId,
6005                                  int responseType, int serial, RIL_Errno e,
6006                                  void *response, size_t responseLen) {
6007#if VDBG
6008    RLOGD("requestShutdownResponse: serial %d", serial);
6009#endif
6010
6011    if (radioService[slotId]->mRadioResponse != NULL) {
6012        RadioResponseInfo responseInfo = {};
6013        populateResponseInfo(responseInfo, serial, responseType, e);
6014        Return<void> retStatus
6015                = radioService[slotId]->mRadioResponse->requestShutdownResponse(responseInfo);
6016        radioService[slotId]->checkReturnStatus(retStatus);
6017    } else {
6018        RLOGE("requestShutdownResponse: radioService[%d]->mRadioResponse == NULL", slotId);
6019    }
6020
6021    return 0;
6022}
6023
6024void responseRadioCapability(RadioResponseInfo& responseInfo, int serial,
6025        int responseType, RIL_Errno e, void *response, size_t responseLen, RadioCapability& rc) {
6026    populateResponseInfo(responseInfo, serial, responseType, e);
6027
6028    if (response == NULL || responseLen != sizeof(RIL_RadioCapability)) {
6029        RLOGE("responseRadioCapability: Invalid response");
6030        if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
6031        rc.logicalModemUuid = hidl_string();
6032    } else {
6033        convertRilRadioCapabilityToHal(response, responseLen, rc);
6034    }
6035}
6036
6037int radio::getRadioCapabilityResponse(int slotId,
6038                                     int responseType, int serial, RIL_Errno e,
6039                                     void *response, size_t responseLen) {
6040#if VDBG
6041    RLOGD("getRadioCapabilityResponse: serial %d", serial);
6042#endif
6043
6044    if (radioService[slotId]->mRadioResponse != NULL) {
6045        RadioResponseInfo responseInfo = {};
6046        RadioCapability result = {};
6047        responseRadioCapability(responseInfo, serial, responseType, e, response, responseLen,
6048                result);
6049        Return<void> retStatus = radioService[slotId]->mRadioResponse->getRadioCapabilityResponse(
6050                responseInfo, result);
6051        radioService[slotId]->checkReturnStatus(retStatus);
6052    } else {
6053        RLOGE("getRadioCapabilityResponse: radioService[%d]->mRadioResponse == NULL", slotId);
6054    }
6055
6056    return 0;
6057}
6058
6059int radio::setRadioCapabilityResponse(int slotId,
6060                                     int responseType, int serial, RIL_Errno e,
6061                                     void *response, size_t responseLen) {
6062#if VDBG
6063    RLOGD("setRadioCapabilityResponse: serial %d", serial);
6064#endif
6065
6066    if (radioService[slotId]->mRadioResponse != NULL) {
6067        RadioResponseInfo responseInfo = {};
6068        RadioCapability result = {};
6069        responseRadioCapability(responseInfo, serial, responseType, e, response, responseLen,
6070                result);
6071        Return<void> retStatus = radioService[slotId]->mRadioResponse->setRadioCapabilityResponse(
6072                responseInfo, result);
6073        radioService[slotId]->checkReturnStatus(retStatus);
6074    } else {
6075        RLOGE("setRadioCapabilityResponse: radioService[%d]->mRadioResponse == NULL", slotId);
6076    }
6077
6078    return 0;
6079}
6080
6081LceStatusInfo responseLceStatusInfo(RadioResponseInfo& responseInfo, int serial, int responseType,
6082                                    RIL_Errno e, void *response, size_t responseLen) {
6083    populateResponseInfo(responseInfo, serial, responseType, e);
6084    LceStatusInfo result = {};
6085
6086    if (response == NULL || responseLen != sizeof(RIL_LceStatusInfo)) {
6087        RLOGE("Invalid response: NULL");
6088        if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
6089    } else {
6090        RIL_LceStatusInfo *resp = (RIL_LceStatusInfo *) response;
6091        result.lceStatus = (LceStatus) resp->lce_status;
6092        result.actualIntervalMs = (uint8_t) resp->actual_interval_ms;
6093    }
6094    return result;
6095}
6096
6097int radio::startLceServiceResponse(int slotId,
6098                                   int responseType, int serial, RIL_Errno e,
6099                                   void *response, size_t responseLen) {
6100#if VDBG
6101    RLOGD("startLceServiceResponse: serial %d", serial);
6102#endif
6103
6104    if (radioService[slotId]->mRadioResponse != NULL) {
6105        RadioResponseInfo responseInfo = {};
6106        LceStatusInfo result = responseLceStatusInfo(responseInfo, serial, responseType, e,
6107                response, responseLen);
6108
6109        Return<void> retStatus
6110                = radioService[slotId]->mRadioResponse->startLceServiceResponse(responseInfo,
6111                result);
6112        radioService[slotId]->checkReturnStatus(retStatus);
6113    } else {
6114        RLOGE("startLceServiceResponse: radioService[%d]->mRadioResponse == NULL", slotId);
6115    }
6116
6117    return 0;
6118}
6119
6120int radio::stopLceServiceResponse(int slotId,
6121                                  int responseType, int serial, RIL_Errno e,
6122                                  void *response, size_t responseLen) {
6123#if VDBG
6124    RLOGD("stopLceServiceResponse: serial %d", serial);
6125#endif
6126
6127    if (radioService[slotId]->mRadioResponse != NULL) {
6128        RadioResponseInfo responseInfo = {};
6129        LceStatusInfo result = responseLceStatusInfo(responseInfo, serial, responseType, e,
6130                response, responseLen);
6131
6132        Return<void> retStatus
6133                = radioService[slotId]->mRadioResponse->stopLceServiceResponse(responseInfo,
6134                result);
6135        radioService[slotId]->checkReturnStatus(retStatus);
6136    } else {
6137        RLOGE("stopLceServiceResponse: radioService[%d]->mRadioResponse == NULL", slotId);
6138    }
6139
6140    return 0;
6141}
6142
6143int radio::pullLceDataResponse(int slotId,
6144                               int responseType, int serial, RIL_Errno e,
6145                               void *response, size_t responseLen) {
6146#if VDBG
6147    RLOGD("pullLceDataResponse: serial %d", serial);
6148#endif
6149
6150    if (radioService[slotId]->mRadioResponse != NULL) {
6151        RadioResponseInfo responseInfo = {};
6152        populateResponseInfo(responseInfo, serial, responseType, e);
6153
6154        LceDataInfo result = {};
6155        if (response == NULL || responseLen != sizeof(RIL_LceDataInfo)) {
6156            RLOGE("pullLceDataResponse: Invalid response");
6157            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
6158        } else {
6159            convertRilLceDataInfoToHal(response, responseLen, result);
6160        }
6161
6162        Return<void> retStatus = radioService[slotId]->mRadioResponse->pullLceDataResponse(
6163                responseInfo, result);
6164        radioService[slotId]->checkReturnStatus(retStatus);
6165    } else {
6166        RLOGE("pullLceDataResponse: radioService[%d]->mRadioResponse == NULL", slotId);
6167    }
6168
6169    return 0;
6170}
6171
6172int radio::getModemActivityInfoResponse(int slotId,
6173                                        int responseType, int serial, RIL_Errno e,
6174                                        void *response, size_t responseLen) {
6175#if VDBG
6176    RLOGD("getModemActivityInfoResponse: serial %d", serial);
6177#endif
6178
6179    if (radioService[slotId]->mRadioResponse != NULL) {
6180        RadioResponseInfo responseInfo = {};
6181        populateResponseInfo(responseInfo, serial, responseType, e);
6182        ActivityStatsInfo info;
6183        if (response == NULL || responseLen != sizeof(RIL_ActivityStatsInfo)) {
6184            RLOGE("getModemActivityInfoResponse Invalid response: NULL");
6185            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
6186        } else {
6187            RIL_ActivityStatsInfo *resp = (RIL_ActivityStatsInfo *)response;
6188            info.sleepModeTimeMs = resp->sleep_mode_time_ms;
6189            info.idleModeTimeMs = resp->idle_mode_time_ms;
6190            for(int i = 0; i < RIL_NUM_TX_POWER_LEVELS; i++) {
6191                info.txmModetimeMs[i] = resp->tx_mode_time_ms[i];
6192            }
6193            info.rxModeTimeMs = resp->rx_mode_time_ms;
6194        }
6195
6196        Return<void> retStatus
6197                = radioService[slotId]->mRadioResponse->getModemActivityInfoResponse(responseInfo,
6198                info);
6199        radioService[slotId]->checkReturnStatus(retStatus);
6200    } else {
6201        RLOGE("getModemActivityInfoResponse: radioService[%d]->mRadioResponse == NULL",
6202                slotId);
6203    }
6204
6205    return 0;
6206}
6207
6208int radio::setAllowedCarriersResponse(int slotId,
6209                                      int responseType, int serial, RIL_Errno e,
6210                                      void *response, size_t responseLen) {
6211#if VDBG
6212    RLOGD("setAllowedCarriersResponse: serial %d", serial);
6213#endif
6214
6215    if (radioService[slotId]->mRadioResponse != NULL) {
6216        RadioResponseInfo responseInfo = {};
6217        int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen);
6218        Return<void> retStatus
6219                = radioService[slotId]->mRadioResponse->setAllowedCarriersResponse(responseInfo,
6220                ret);
6221        radioService[slotId]->checkReturnStatus(retStatus);
6222    } else {
6223        RLOGE("setAllowedCarriersResponse: radioService[%d]->mRadioResponse == NULL",
6224                slotId);
6225    }
6226
6227    return 0;
6228}
6229
6230int radio::getAllowedCarriersResponse(int slotId,
6231                                      int responseType, int serial, RIL_Errno e,
6232                                      void *response, size_t responseLen) {
6233#if VDBG
6234    RLOGD("getAllowedCarriersResponse: serial %d", serial);
6235#endif
6236
6237    if (radioService[slotId]->mRadioResponse != NULL) {
6238        RadioResponseInfo responseInfo = {};
6239        populateResponseInfo(responseInfo, serial, responseType, e);
6240        CarrierRestrictions carrierInfo = {};
6241        bool allAllowed = true;
6242        if (response == NULL) {
6243#if VDBG
6244            RLOGD("getAllowedCarriersResponse response is NULL: all allowed");
6245#endif
6246            carrierInfo.allowedCarriers.resize(0);
6247            carrierInfo.excludedCarriers.resize(0);
6248        } else if (responseLen != sizeof(RIL_CarrierRestrictions)) {
6249            RLOGE("getAllowedCarriersResponse Invalid response");
6250            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
6251        } else {
6252            RIL_CarrierRestrictions *pCr = (RIL_CarrierRestrictions *)response;
6253            if (pCr->len_allowed_carriers > 0 || pCr->len_excluded_carriers > 0) {
6254                allAllowed = false;
6255            }
6256
6257            carrierInfo.allowedCarriers.resize(pCr->len_allowed_carriers);
6258            for(int i = 0; i < pCr->len_allowed_carriers; i++) {
6259                RIL_Carrier *carrier = pCr->allowed_carriers + i;
6260                carrierInfo.allowedCarriers[i].mcc = convertCharPtrToHidlString(carrier->mcc);
6261                carrierInfo.allowedCarriers[i].mnc = convertCharPtrToHidlString(carrier->mnc);
6262                carrierInfo.allowedCarriers[i].matchType = (CarrierMatchType) carrier->match_type;
6263                carrierInfo.allowedCarriers[i].matchData =
6264                        convertCharPtrToHidlString(carrier->match_data);
6265            }
6266
6267            carrierInfo.excludedCarriers.resize(pCr->len_excluded_carriers);
6268            for(int i = 0; i < pCr->len_excluded_carriers; i++) {
6269                RIL_Carrier *carrier = pCr->excluded_carriers + i;
6270                carrierInfo.excludedCarriers[i].mcc = convertCharPtrToHidlString(carrier->mcc);
6271                carrierInfo.excludedCarriers[i].mnc = convertCharPtrToHidlString(carrier->mnc);
6272                carrierInfo.excludedCarriers[i].matchType = (CarrierMatchType) carrier->match_type;
6273                carrierInfo.excludedCarriers[i].matchData =
6274                        convertCharPtrToHidlString(carrier->match_data);
6275            }
6276        }
6277
6278        Return<void> retStatus
6279                = radioService[slotId]->mRadioResponse->getAllowedCarriersResponse(responseInfo,
6280                allAllowed, carrierInfo);
6281        radioService[slotId]->checkReturnStatus(retStatus);
6282    } else {
6283        RLOGE("getAllowedCarriersResponse: radioService[%d]->mRadioResponse == NULL",
6284                slotId);
6285    }
6286
6287    return 0;
6288}
6289
6290int radio::sendDeviceStateResponse(int slotId,
6291                              int responseType, int serial, RIL_Errno e,
6292                              void *response, size_t responselen) {
6293#if VDBG
6294    RLOGD("sendDeviceStateResponse: serial %d", serial);
6295#endif
6296
6297    if (radioService[slotId]->mRadioResponse != NULL) {
6298        RadioResponseInfo responseInfo = {};
6299        populateResponseInfo(responseInfo, serial, responseType, e);
6300        Return<void> retStatus
6301                = radioService[slotId]->mRadioResponse->sendDeviceStateResponse(responseInfo);
6302        radioService[slotId]->checkReturnStatus(retStatus);
6303    } else {
6304        RLOGE("sendDeviceStateResponse: radioService[%d]->mRadioResponse == NULL", slotId);
6305    }
6306
6307    return 0;
6308}
6309
6310int radio::setIndicationFilterResponse(int slotId,
6311                              int responseType, int serial, RIL_Errno e,
6312                              void *response, size_t responselen) {
6313#if VDBG
6314    RLOGD("setIndicationFilterResponse: serial %d", serial);
6315#endif
6316
6317    if (radioService[slotId]->mRadioResponse != NULL) {
6318        RadioResponseInfo responseInfo = {};
6319        populateResponseInfo(responseInfo, serial, responseType, e);
6320        Return<void> retStatus
6321                = radioService[slotId]->mRadioResponse->setIndicationFilterResponse(responseInfo);
6322        radioService[slotId]->checkReturnStatus(retStatus);
6323    } else {
6324        RLOGE("setIndicationFilterResponse: radioService[%d]->mRadioResponse == NULL",
6325                slotId);
6326    }
6327
6328    return 0;
6329}
6330
6331
6332int radio::setSimCardPowerResponse(int slotId,
6333                                   int responseType, int serial, RIL_Errno e,
6334                                   void *response, size_t responseLen) {
6335#if VDBG
6336    RLOGD("setSimCardPowerResponse: serial %d", serial);
6337#endif
6338
6339    if (radioService[slotId]->mRadioResponse != NULL) {
6340        RadioResponseInfo responseInfo = {};
6341        populateResponseInfo(responseInfo, serial, responseType, e);
6342        Return<void> retStatus
6343                = radioService[slotId]->mRadioResponse->setSimCardPowerResponse(responseInfo);
6344        radioService[slotId]->checkReturnStatus(retStatus);
6345    } else {
6346        RLOGE("setSimCardPowerResponse: radioService[%d]->mRadioResponse == NULL", slotId);
6347    }
6348
6349    return 0;
6350}
6351
6352int radio::sendRequestRawResponse(int slotId,
6353                                  int responseType, int serial, RIL_Errno e,
6354                                  void *response, size_t responseLen) {
6355#if VDBG
6356   RLOGD("sendRequestRawResponse: serial %d", serial);
6357#endif
6358
6359    if (oemHookService[slotId]->mOemHookResponse != NULL) {
6360        RadioResponseInfo responseInfo = {};
6361        populateResponseInfo(responseInfo, serial, responseType, e);
6362        hidl_vec<uint8_t> data;
6363
6364        if (response == NULL) {
6365            RLOGE("sendRequestRawResponse: Invalid response");
6366            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
6367        } else {
6368            data.setToExternal((uint8_t *) response, responseLen);
6369        }
6370        Return<void> retStatus = oemHookService[slotId]->mOemHookResponse->
6371                sendRequestRawResponse(responseInfo, data);
6372        checkReturnStatus(slotId, retStatus, false);
6373    } else {
6374        RLOGE("sendRequestRawResponse: oemHookService[%d]->mOemHookResponse == NULL",
6375                slotId);
6376    }
6377
6378    return 0;
6379}
6380
6381int radio::sendRequestStringsResponse(int slotId,
6382                                      int responseType, int serial, RIL_Errno e,
6383                                      void *response, size_t responseLen) {
6384#if VDBG
6385    RLOGD("sendRequestStringsResponse: serial %d", serial);
6386#endif
6387
6388    if (oemHookService[slotId]->mOemHookResponse != NULL) {
6389        RadioResponseInfo responseInfo = {};
6390        populateResponseInfo(responseInfo, serial, responseType, e);
6391        hidl_vec<hidl_string> data;
6392
6393        if (response == NULL || responseLen % sizeof(char *) != 0) {
6394            RLOGE("sendRequestStringsResponse Invalid response: NULL");
6395            if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE;
6396        } else {
6397            char **resp = (char **) response;
6398            int numStrings = responseLen / sizeof(char *);
6399            data.resize(numStrings);
6400            for (int i = 0; i < numStrings; i++) {
6401                data[i] = convertCharPtrToHidlString(resp[i]);
6402            }
6403        }
6404        Return<void> retStatus
6405                = oemHookService[slotId]->mOemHookResponse->sendRequestStringsResponse(
6406                responseInfo, data);
6407        checkReturnStatus(slotId, retStatus, false);
6408    } else {
6409        RLOGE("sendRequestStringsResponse: oemHookService[%d]->mOemHookResponse == "
6410                "NULL", slotId);
6411    }
6412
6413    return 0;
6414}
6415
6416// Radio Indication functions
6417
6418RadioIndicationType convertIntToRadioIndicationType(int indicationType) {
6419    return indicationType == RESPONSE_UNSOLICITED ? (RadioIndicationType::UNSOLICITED) :
6420            (RadioIndicationType::UNSOLICITED_ACK_EXP);
6421}
6422
6423int radio::radioStateChangedInd(int slotId,
6424                                 int indicationType, int token, RIL_Errno e, void *response,
6425                                 size_t responseLen) {
6426    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6427        RadioState radioState =
6428                (RadioState) CALL_ONSTATEREQUEST(slotId);
6429        RLOGD("radioStateChangedInd: radioState %d", radioState);
6430        Return<void> retStatus = radioService[slotId]->mRadioIndication->radioStateChanged(
6431                convertIntToRadioIndicationType(indicationType), radioState);
6432        radioService[slotId]->checkReturnStatus(retStatus);
6433    } else {
6434        RLOGE("radioStateChangedInd: radioService[%d]->mRadioIndication == NULL", slotId);
6435    }
6436
6437    return 0;
6438}
6439
6440int radio::callStateChangedInd(int slotId,
6441                               int indicationType, int token, RIL_Errno e, void *response,
6442                               size_t responseLen) {
6443    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6444#if VDBG
6445        RLOGD("callStateChangedInd");
6446#endif
6447        Return<void> retStatus = radioService[slotId]->mRadioIndication->callStateChanged(
6448                convertIntToRadioIndicationType(indicationType));
6449        radioService[slotId]->checkReturnStatus(retStatus);
6450    } else {
6451        RLOGE("callStateChangedInd: radioService[%d]->mRadioIndication == NULL", slotId);
6452    }
6453
6454    return 0;
6455}
6456
6457int radio::networkStateChangedInd(int slotId,
6458                                  int indicationType, int token, RIL_Errno e, void *response,
6459                                  size_t responseLen) {
6460    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6461#if VDBG
6462        RLOGD("networkStateChangedInd");
6463#endif
6464        Return<void> retStatus = radioService[slotId]->mRadioIndication->networkStateChanged(
6465                convertIntToRadioIndicationType(indicationType));
6466        radioService[slotId]->checkReturnStatus(retStatus);
6467    } else {
6468        RLOGE("networkStateChangedInd: radioService[%d]->mRadioIndication == NULL",
6469                slotId);
6470    }
6471
6472    return 0;
6473}
6474
6475uint8_t hexCharToInt(uint8_t c) {
6476    if (c >= '0' && c <= '9') return (c - '0');
6477    if (c >= 'A' && c <= 'F') return (c - 'A' + 10);
6478    if (c >= 'a' && c <= 'f') return (c - 'a' + 10);
6479
6480    return INVALID_HEX_CHAR;
6481}
6482
6483uint8_t * convertHexStringToBytes(void *response, size_t responseLen) {
6484    if (responseLen % 2 != 0) {
6485        return NULL;
6486    }
6487
6488    uint8_t *bytes = (uint8_t *)calloc(responseLen/2, sizeof(uint8_t));
6489    if (bytes == NULL) {
6490        RLOGE("convertHexStringToBytes: cannot allocate memory for bytes string");
6491        return NULL;
6492    }
6493    uint8_t *hexString = (uint8_t *)response;
6494
6495    for (size_t i = 0; i < responseLen; i += 2) {
6496        uint8_t hexChar1 = hexCharToInt(hexString[i]);
6497        uint8_t hexChar2 = hexCharToInt(hexString[i + 1]);
6498
6499        if (hexChar1 == INVALID_HEX_CHAR || hexChar2 == INVALID_HEX_CHAR) {
6500            RLOGE("convertHexStringToBytes: invalid hex char %d %d",
6501                    hexString[i], hexString[i + 1]);
6502            free(bytes);
6503            return NULL;
6504        }
6505        bytes[i/2] = ((hexChar1 << 4) | hexChar2);
6506    }
6507
6508    return bytes;
6509}
6510
6511int radio::newSmsInd(int slotId, int indicationType,
6512                     int token, RIL_Errno e, void *response, size_t responseLen) {
6513    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6514        if (response == NULL || responseLen == 0) {
6515            RLOGE("newSmsInd: invalid response");
6516            return 0;
6517        }
6518
6519        uint8_t *bytes = convertHexStringToBytes(response, responseLen);
6520        if (bytes == NULL) {
6521            RLOGE("newSmsInd: convertHexStringToBytes failed");
6522            return 0;
6523        }
6524
6525        hidl_vec<uint8_t> pdu;
6526        pdu.setToExternal(bytes, responseLen/2);
6527#if VDBG
6528        RLOGD("newSmsInd");
6529#endif
6530        Return<void> retStatus = radioService[slotId]->mRadioIndication->newSms(
6531                convertIntToRadioIndicationType(indicationType), pdu);
6532        radioService[slotId]->checkReturnStatus(retStatus);
6533        free(bytes);
6534    } else {
6535        RLOGE("newSmsInd: radioService[%d]->mRadioIndication == NULL", slotId);
6536    }
6537
6538    return 0;
6539}
6540
6541int radio::newSmsStatusReportInd(int slotId,
6542                                 int indicationType, int token, RIL_Errno e, void *response,
6543                                 size_t responseLen) {
6544    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6545        if (response == NULL || responseLen == 0) {
6546            RLOGE("newSmsStatusReportInd: invalid response");
6547            return 0;
6548        }
6549
6550        uint8_t *bytes = convertHexStringToBytes(response, responseLen);
6551        if (bytes == NULL) {
6552            RLOGE("newSmsStatusReportInd: convertHexStringToBytes failed");
6553            return 0;
6554        }
6555
6556        hidl_vec<uint8_t> pdu;
6557        pdu.setToExternal(bytes, responseLen/2);
6558#if VDBG
6559        RLOGD("newSmsStatusReportInd");
6560#endif
6561        Return<void> retStatus = radioService[slotId]->mRadioIndication->newSmsStatusReport(
6562                convertIntToRadioIndicationType(indicationType), pdu);
6563        radioService[slotId]->checkReturnStatus(retStatus);
6564        free(bytes);
6565    } else {
6566        RLOGE("newSmsStatusReportInd: radioService[%d]->mRadioIndication == NULL", slotId);
6567    }
6568
6569    return 0;
6570}
6571
6572int radio::newSmsOnSimInd(int slotId, int indicationType,
6573                          int token, RIL_Errno e, void *response, size_t responseLen) {
6574    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6575        if (response == NULL || responseLen != sizeof(int)) {
6576            RLOGE("newSmsOnSimInd: invalid response");
6577            return 0;
6578        }
6579        int32_t recordNumber = ((int32_t *) response)[0];
6580#if VDBG
6581        RLOGD("newSmsOnSimInd: slotIndex %d", recordNumber);
6582#endif
6583        Return<void> retStatus = radioService[slotId]->mRadioIndication->newSmsOnSim(
6584                convertIntToRadioIndicationType(indicationType), recordNumber);
6585        radioService[slotId]->checkReturnStatus(retStatus);
6586    } else {
6587        RLOGE("newSmsOnSimInd: radioService[%d]->mRadioIndication == NULL", slotId);
6588    }
6589
6590    return 0;
6591}
6592
6593int radio::onUssdInd(int slotId, int indicationType,
6594                     int token, RIL_Errno e, void *response, size_t responseLen) {
6595    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6596        if (response == NULL || responseLen != 2 * sizeof(char *)) {
6597            RLOGE("onUssdInd: invalid response");
6598            return 0;
6599        }
6600        char **strings = (char **) response;
6601        char *mode = strings[0];
6602        hidl_string msg = convertCharPtrToHidlString(strings[1]);
6603        UssdModeType modeType = (UssdModeType) atoi(mode);
6604#if VDBG
6605        RLOGD("onUssdInd: mode %s", mode);
6606#endif
6607        Return<void> retStatus = radioService[slotId]->mRadioIndication->onUssd(
6608                convertIntToRadioIndicationType(indicationType), modeType, msg);
6609        radioService[slotId]->checkReturnStatus(retStatus);
6610    } else {
6611        RLOGE("onUssdInd: radioService[%d]->mRadioIndication == NULL", slotId);
6612    }
6613
6614    return 0;
6615}
6616
6617int radio::nitzTimeReceivedInd(int slotId,
6618                               int indicationType, int token, RIL_Errno e, void *response,
6619                               size_t responseLen) {
6620    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6621        if (response == NULL || responseLen == 0) {
6622            RLOGE("nitzTimeReceivedInd: invalid response");
6623            return 0;
6624        }
6625        hidl_string nitzTime = convertCharPtrToHidlString((char *) response);
6626        int64_t timeReceived = android::elapsedRealtime();
6627#if VDBG
6628        RLOGD("nitzTimeReceivedInd: nitzTime %s receivedTime %" PRId64, nitzTime.c_str(),
6629                timeReceived);
6630#endif
6631        Return<void> retStatus = radioService[slotId]->mRadioIndication->nitzTimeReceived(
6632                convertIntToRadioIndicationType(indicationType), nitzTime, timeReceived);
6633        radioService[slotId]->checkReturnStatus(retStatus);
6634    } else {
6635        RLOGE("nitzTimeReceivedInd: radioService[%d]->mRadioIndication == NULL", slotId);
6636        return -1;
6637    }
6638
6639    return 0;
6640}
6641
6642void convertRilSignalStrengthToHal(void *response, size_t responseLen,
6643        SignalStrength& signalStrength) {
6644    RIL_SignalStrength_v10 *rilSignalStrength = (RIL_SignalStrength_v10 *) response;
6645
6646    // Fixup LTE for backwards compatibility
6647    // signalStrength: -1 -> 99
6648    if (rilSignalStrength->LTE_SignalStrength.signalStrength == -1) {
6649        rilSignalStrength->LTE_SignalStrength.signalStrength = 99;
6650    }
6651    // rsrp: -1 -> INT_MAX all other negative value to positive.
6652    // So remap here
6653    if (rilSignalStrength->LTE_SignalStrength.rsrp == -1) {
6654        rilSignalStrength->LTE_SignalStrength.rsrp = INT_MAX;
6655    } else if (rilSignalStrength->LTE_SignalStrength.rsrp < -1) {
6656        rilSignalStrength->LTE_SignalStrength.rsrp = -rilSignalStrength->LTE_SignalStrength.rsrp;
6657    }
6658    // rsrq: -1 -> INT_MAX
6659    if (rilSignalStrength->LTE_SignalStrength.rsrq == -1) {
6660        rilSignalStrength->LTE_SignalStrength.rsrq = INT_MAX;
6661    }
6662    // Not remapping rssnr is already using INT_MAX
6663    // cqi: -1 -> INT_MAX
6664    if (rilSignalStrength->LTE_SignalStrength.cqi == -1) {
6665        rilSignalStrength->LTE_SignalStrength.cqi = INT_MAX;
6666    }
6667
6668    signalStrength.gw.signalStrength = rilSignalStrength->GW_SignalStrength.signalStrength;
6669    signalStrength.gw.bitErrorRate = rilSignalStrength->GW_SignalStrength.bitErrorRate;
6670    signalStrength.cdma.dbm = rilSignalStrength->CDMA_SignalStrength.dbm;
6671    signalStrength.cdma.ecio = rilSignalStrength->CDMA_SignalStrength.ecio;
6672    signalStrength.evdo.dbm = rilSignalStrength->EVDO_SignalStrength.dbm;
6673    signalStrength.evdo.ecio = rilSignalStrength->EVDO_SignalStrength.ecio;
6674    signalStrength.evdo.signalNoiseRatio =
6675            rilSignalStrength->EVDO_SignalStrength.signalNoiseRatio;
6676    signalStrength.lte.signalStrength = rilSignalStrength->LTE_SignalStrength.signalStrength;
6677    signalStrength.lte.rsrp = rilSignalStrength->LTE_SignalStrength.rsrp;
6678    signalStrength.lte.rsrq = rilSignalStrength->LTE_SignalStrength.rsrq;
6679    signalStrength.lte.rssnr = rilSignalStrength->LTE_SignalStrength.rssnr;
6680    signalStrength.lte.cqi = rilSignalStrength->LTE_SignalStrength.cqi;
6681    signalStrength.lte.timingAdvance = rilSignalStrength->LTE_SignalStrength.timingAdvance;
6682    signalStrength.tdScdma.rscp = rilSignalStrength->TD_SCDMA_SignalStrength.rscp;
6683}
6684
6685int radio::currentSignalStrengthInd(int slotId,
6686                                    int indicationType, int token, RIL_Errno e,
6687                                    void *response, size_t responseLen) {
6688    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6689        if (response == NULL || responseLen != sizeof(RIL_SignalStrength_v10)) {
6690            RLOGE("currentSignalStrengthInd: invalid response");
6691            return 0;
6692        }
6693
6694        SignalStrength signalStrength = {};
6695        convertRilSignalStrengthToHal(response, responseLen, signalStrength);
6696
6697#if VDBG
6698        RLOGD("currentSignalStrengthInd");
6699#endif
6700        Return<void> retStatus = radioService[slotId]->mRadioIndication->currentSignalStrength(
6701                convertIntToRadioIndicationType(indicationType), signalStrength);
6702        radioService[slotId]->checkReturnStatus(retStatus);
6703    } else {
6704        RLOGE("currentSignalStrengthInd: radioService[%d]->mRadioIndication == NULL",
6705                slotId);
6706    }
6707
6708    return 0;
6709}
6710
6711void convertRilDataCallToHal(RIL_Data_Call_Response_v11 *dcResponse,
6712        SetupDataCallResult& dcResult) {
6713    dcResult.status = (DataCallFailCause) dcResponse->status;
6714    dcResult.suggestedRetryTime = dcResponse->suggestedRetryTime;
6715    dcResult.cid = dcResponse->cid;
6716    dcResult.active = dcResponse->active;
6717    dcResult.type = convertCharPtrToHidlString(dcResponse->type);
6718    dcResult.ifname = convertCharPtrToHidlString(dcResponse->ifname);
6719    dcResult.addresses = convertCharPtrToHidlString(dcResponse->addresses);
6720    dcResult.dnses = convertCharPtrToHidlString(dcResponse->dnses);
6721    dcResult.gateways = convertCharPtrToHidlString(dcResponse->gateways);
6722    dcResult.pcscf = convertCharPtrToHidlString(dcResponse->pcscf);
6723    dcResult.mtu = dcResponse->mtu;
6724}
6725
6726void convertRilDataCallListToHal(void *response, size_t responseLen,
6727        hidl_vec<SetupDataCallResult>& dcResultList) {
6728    int num = responseLen / sizeof(RIL_Data_Call_Response_v11);
6729
6730    RIL_Data_Call_Response_v11 *dcResponse = (RIL_Data_Call_Response_v11 *) response;
6731    dcResultList.resize(num);
6732    for (int i = 0; i < num; i++) {
6733        convertRilDataCallToHal(&dcResponse[i], dcResultList[i]);
6734    }
6735}
6736
6737int radio::dataCallListChangedInd(int slotId,
6738                                  int indicationType, int token, RIL_Errno e, void *response,
6739                                  size_t responseLen) {
6740    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6741        if (response == NULL || responseLen % sizeof(RIL_Data_Call_Response_v11) != 0) {
6742            RLOGE("dataCallListChangedInd: invalid response");
6743            return 0;
6744        }
6745        hidl_vec<SetupDataCallResult> dcList;
6746        convertRilDataCallListToHal(response, responseLen, dcList);
6747#if VDBG
6748        RLOGD("dataCallListChangedInd");
6749#endif
6750        Return<void> retStatus = radioService[slotId]->mRadioIndication->dataCallListChanged(
6751                convertIntToRadioIndicationType(indicationType), dcList);
6752        radioService[slotId]->checkReturnStatus(retStatus);
6753    } else {
6754        RLOGE("dataCallListChangedInd: radioService[%d]->mRadioIndication == NULL", slotId);
6755    }
6756
6757    return 0;
6758}
6759
6760int radio::suppSvcNotifyInd(int slotId, int indicationType,
6761                            int token, RIL_Errno e, void *response, size_t responseLen) {
6762    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6763        if (response == NULL || responseLen != sizeof(RIL_SuppSvcNotification)) {
6764            RLOGE("suppSvcNotifyInd: invalid response");
6765            return 0;
6766        }
6767
6768        SuppSvcNotification suppSvc = {};
6769        RIL_SuppSvcNotification *ssn = (RIL_SuppSvcNotification *) response;
6770        suppSvc.isMT = ssn->notificationType;
6771        suppSvc.code = ssn->code;
6772        suppSvc.index = ssn->index;
6773        suppSvc.type = ssn->type;
6774        suppSvc.number = convertCharPtrToHidlString(ssn->number);
6775
6776#if VDBG
6777        RLOGD("suppSvcNotifyInd: isMT %d code %d index %d type %d",
6778                suppSvc.isMT, suppSvc.code, suppSvc.index, suppSvc.type);
6779#endif
6780        Return<void> retStatus = radioService[slotId]->mRadioIndication->suppSvcNotify(
6781                convertIntToRadioIndicationType(indicationType), suppSvc);
6782        radioService[slotId]->checkReturnStatus(retStatus);
6783    } else {
6784        RLOGE("suppSvcNotifyInd: radioService[%d]->mRadioIndication == NULL", slotId);
6785    }
6786
6787    return 0;
6788}
6789
6790int radio::stkSessionEndInd(int slotId, int indicationType,
6791                            int token, RIL_Errno e, void *response, size_t responseLen) {
6792    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6793#if VDBG
6794        RLOGD("stkSessionEndInd");
6795#endif
6796        Return<void> retStatus = radioService[slotId]->mRadioIndication->stkSessionEnd(
6797                convertIntToRadioIndicationType(indicationType));
6798        radioService[slotId]->checkReturnStatus(retStatus);
6799    } else {
6800        RLOGE("stkSessionEndInd: radioService[%d]->mRadioIndication == NULL", slotId);
6801    }
6802
6803    return 0;
6804}
6805
6806int radio::stkProactiveCommandInd(int slotId,
6807                                  int indicationType, int token, RIL_Errno e, void *response,
6808                                  size_t responseLen) {
6809    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6810        if (response == NULL || responseLen == 0) {
6811            RLOGE("stkProactiveCommandInd: invalid response");
6812            return 0;
6813        }
6814#if VDBG
6815        RLOGD("stkProactiveCommandInd");
6816#endif
6817        Return<void> retStatus = radioService[slotId]->mRadioIndication->stkProactiveCommand(
6818                convertIntToRadioIndicationType(indicationType),
6819                convertCharPtrToHidlString((char *) response));
6820        radioService[slotId]->checkReturnStatus(retStatus);
6821    } else {
6822        RLOGE("stkProactiveCommandInd: radioService[%d]->mRadioIndication == NULL", slotId);
6823    }
6824
6825    return 0;
6826}
6827
6828int radio::stkEventNotifyInd(int slotId, int indicationType,
6829                             int token, RIL_Errno e, void *response, size_t responseLen) {
6830    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6831        if (response == NULL || responseLen == 0) {
6832            RLOGE("stkEventNotifyInd: invalid response");
6833            return 0;
6834        }
6835#if VDBG
6836        RLOGD("stkEventNotifyInd");
6837#endif
6838        Return<void> retStatus = radioService[slotId]->mRadioIndication->stkEventNotify(
6839                convertIntToRadioIndicationType(indicationType),
6840                convertCharPtrToHidlString((char *) response));
6841        radioService[slotId]->checkReturnStatus(retStatus);
6842    } else {
6843        RLOGE("stkEventNotifyInd: radioService[%d]->mRadioIndication == NULL", slotId);
6844    }
6845
6846    return 0;
6847}
6848
6849int radio::stkCallSetupInd(int slotId, int indicationType,
6850                           int token, RIL_Errno e, void *response, size_t responseLen) {
6851    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6852        if (response == NULL || responseLen != sizeof(int)) {
6853            RLOGE("stkCallSetupInd: invalid response");
6854            return 0;
6855        }
6856        int32_t timeout = ((int32_t *) response)[0];
6857#if VDBG
6858        RLOGD("stkCallSetupInd: timeout %d", timeout);
6859#endif
6860        Return<void> retStatus = radioService[slotId]->mRadioIndication->stkCallSetup(
6861                convertIntToRadioIndicationType(indicationType), timeout);
6862        radioService[slotId]->checkReturnStatus(retStatus);
6863    } else {
6864        RLOGE("stkCallSetupInd: radioService[%d]->mRadioIndication == NULL", slotId);
6865    }
6866
6867    return 0;
6868}
6869
6870int radio::simSmsStorageFullInd(int slotId,
6871                                int indicationType, int token, RIL_Errno e, void *response,
6872                                size_t responseLen) {
6873    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6874#if VDBG
6875        RLOGD("simSmsStorageFullInd");
6876#endif
6877        Return<void> retStatus = radioService[slotId]->mRadioIndication->simSmsStorageFull(
6878                convertIntToRadioIndicationType(indicationType));
6879        radioService[slotId]->checkReturnStatus(retStatus);
6880    } else {
6881        RLOGE("simSmsStorageFullInd: radioService[%d]->mRadioIndication == NULL", slotId);
6882    }
6883
6884    return 0;
6885}
6886
6887int radio::simRefreshInd(int slotId, int indicationType,
6888                         int token, RIL_Errno e, void *response, size_t responseLen) {
6889    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6890        if (response == NULL || responseLen != sizeof(RIL_SimRefreshResponse_v7)) {
6891            RLOGE("simRefreshInd: invalid response");
6892            return 0;
6893        }
6894
6895        SimRefreshResult refreshResult = {};
6896        RIL_SimRefreshResponse_v7 *simRefreshResponse = ((RIL_SimRefreshResponse_v7 *) response);
6897        refreshResult.type =
6898                (android::hardware::radio::V1_0::SimRefreshType) simRefreshResponse->result;
6899        refreshResult.efId = simRefreshResponse->ef_id;
6900        refreshResult.aid = convertCharPtrToHidlString(simRefreshResponse->aid);
6901
6902#if VDBG
6903        RLOGD("simRefreshInd: type %d efId %d", refreshResult.type, refreshResult.efId);
6904#endif
6905        Return<void> retStatus = radioService[slotId]->mRadioIndication->simRefresh(
6906                convertIntToRadioIndicationType(indicationType), refreshResult);
6907        radioService[slotId]->checkReturnStatus(retStatus);
6908    } else {
6909        RLOGE("simRefreshInd: radioService[%d]->mRadioIndication == NULL", slotId);
6910    }
6911
6912    return 0;
6913}
6914
6915void convertRilCdmaSignalInfoRecordToHal(RIL_CDMA_SignalInfoRecord *signalInfoRecord,
6916        CdmaSignalInfoRecord& record) {
6917    record.isPresent = signalInfoRecord->isPresent;
6918    record.signalType = signalInfoRecord->signalType;
6919    record.alertPitch = signalInfoRecord->alertPitch;
6920    record.signal = signalInfoRecord->signal;
6921}
6922
6923int radio::callRingInd(int slotId, int indicationType,
6924                       int token, RIL_Errno e, void *response, size_t responseLen) {
6925    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6926        bool isGsm;
6927        CdmaSignalInfoRecord record = {};
6928        if (response == NULL || responseLen == 0) {
6929            isGsm = true;
6930        } else {
6931            isGsm = false;
6932            if (responseLen != sizeof (RIL_CDMA_SignalInfoRecord)) {
6933                RLOGE("callRingInd: invalid response");
6934                return 0;
6935            }
6936            convertRilCdmaSignalInfoRecordToHal((RIL_CDMA_SignalInfoRecord *) response, record);
6937        }
6938
6939#if VDBG
6940        RLOGD("callRingInd: isGsm %d", isGsm);
6941#endif
6942        Return<void> retStatus = radioService[slotId]->mRadioIndication->callRing(
6943                convertIntToRadioIndicationType(indicationType), isGsm, record);
6944        radioService[slotId]->checkReturnStatus(retStatus);
6945    } else {
6946        RLOGE("callRingInd: radioService[%d]->mRadioIndication == NULL", slotId);
6947    }
6948
6949    return 0;
6950}
6951
6952int radio::simStatusChangedInd(int slotId,
6953                               int indicationType, int token, RIL_Errno e, void *response,
6954                               size_t responseLen) {
6955    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6956#if VDBG
6957        RLOGD("simStatusChangedInd");
6958#endif
6959        Return<void> retStatus = radioService[slotId]->mRadioIndication->simStatusChanged(
6960                convertIntToRadioIndicationType(indicationType));
6961        radioService[slotId]->checkReturnStatus(retStatus);
6962    } else {
6963        RLOGE("simStatusChangedInd: radioService[%d]->mRadioIndication == NULL", slotId);
6964    }
6965
6966    return 0;
6967}
6968
6969int radio::cdmaNewSmsInd(int slotId, int indicationType,
6970                         int token, RIL_Errno e, void *response, size_t responseLen) {
6971    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
6972        if (response == NULL || responseLen != sizeof(RIL_CDMA_SMS_Message)) {
6973            RLOGE("cdmaNewSmsInd: invalid response");
6974            return 0;
6975        }
6976
6977        CdmaSmsMessage msg = {};
6978        RIL_CDMA_SMS_Message *rilMsg = (RIL_CDMA_SMS_Message *) response;
6979        msg.teleserviceId = rilMsg->uTeleserviceID;
6980        msg.isServicePresent = rilMsg->bIsServicePresent;
6981        msg.serviceCategory = rilMsg->uServicecategory;
6982        msg.address.digitMode =
6983                (android::hardware::radio::V1_0::CdmaSmsDigitMode) rilMsg->sAddress.digit_mode;
6984        msg.address.numberMode =
6985                (android::hardware::radio::V1_0::CdmaSmsNumberMode) rilMsg->sAddress.number_mode;
6986        msg.address.numberType =
6987                (android::hardware::radio::V1_0::CdmaSmsNumberType) rilMsg->sAddress.number_type;
6988        msg.address.numberPlan =
6989                (android::hardware::radio::V1_0::CdmaSmsNumberPlan) rilMsg->sAddress.number_plan;
6990
6991        int digitLimit = MIN((rilMsg->sAddress.number_of_digits), RIL_CDMA_SMS_ADDRESS_MAX);
6992        msg.address.digits.setToExternal(rilMsg->sAddress.digits, digitLimit);
6993
6994        msg.subAddress.subaddressType = (android::hardware::radio::V1_0::CdmaSmsSubaddressType)
6995                rilMsg->sSubAddress.subaddressType;
6996        msg.subAddress.odd = rilMsg->sSubAddress.odd;
6997
6998        digitLimit= MIN((rilMsg->sSubAddress.number_of_digits), RIL_CDMA_SMS_SUBADDRESS_MAX);
6999        msg.subAddress.digits.setToExternal(rilMsg->sSubAddress.digits, digitLimit);
7000
7001        digitLimit = MIN((rilMsg->uBearerDataLen), RIL_CDMA_SMS_BEARER_DATA_MAX);
7002        msg.bearerData.setToExternal(rilMsg->aBearerData, digitLimit);
7003
7004#if VDBG
7005        RLOGD("cdmaNewSmsInd");
7006#endif
7007        Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaNewSms(
7008                convertIntToRadioIndicationType(indicationType), msg);
7009        radioService[slotId]->checkReturnStatus(retStatus);
7010    } else {
7011        RLOGE("cdmaNewSmsInd: radioService[%d]->mRadioIndication == NULL", slotId);
7012    }
7013
7014    return 0;
7015}
7016
7017int radio::newBroadcastSmsInd(int slotId,
7018                              int indicationType, int token, RIL_Errno e, void *response,
7019                              size_t responseLen) {
7020    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7021        if (response == NULL || responseLen == 0) {
7022            RLOGE("newBroadcastSmsInd: invalid response");
7023            return 0;
7024        }
7025
7026        hidl_vec<uint8_t> data;
7027        data.setToExternal((uint8_t *) response, responseLen);
7028#if VDBG
7029        RLOGD("newBroadcastSmsInd");
7030#endif
7031        Return<void> retStatus = radioService[slotId]->mRadioIndication->newBroadcastSms(
7032                convertIntToRadioIndicationType(indicationType), data);
7033        radioService[slotId]->checkReturnStatus(retStatus);
7034    } else {
7035        RLOGE("newBroadcastSmsInd: radioService[%d]->mRadioIndication == NULL", slotId);
7036    }
7037
7038    return 0;
7039}
7040
7041int radio::cdmaRuimSmsStorageFullInd(int slotId,
7042                                     int indicationType, int token, RIL_Errno e, void *response,
7043                                     size_t responseLen) {
7044    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7045#if VDBG
7046        RLOGD("cdmaRuimSmsStorageFullInd");
7047#endif
7048        Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaRuimSmsStorageFull(
7049                convertIntToRadioIndicationType(indicationType));
7050        radioService[slotId]->checkReturnStatus(retStatus);
7051    } else {
7052        RLOGE("cdmaRuimSmsStorageFullInd: radioService[%d]->mRadioIndication == NULL",
7053                slotId);
7054    }
7055
7056    return 0;
7057}
7058
7059int radio::restrictedStateChangedInd(int slotId,
7060                                     int indicationType, int token, RIL_Errno e, void *response,
7061                                     size_t responseLen) {
7062    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7063        if (response == NULL || responseLen != sizeof(int)) {
7064            RLOGE("restrictedStateChangedInd: invalid response");
7065            return 0;
7066        }
7067        int32_t state = ((int32_t *) response)[0];
7068#if VDBG
7069        RLOGD("restrictedStateChangedInd: state %d", state);
7070#endif
7071        Return<void> retStatus = radioService[slotId]->mRadioIndication->restrictedStateChanged(
7072                convertIntToRadioIndicationType(indicationType), (PhoneRestrictedState) state);
7073        radioService[slotId]->checkReturnStatus(retStatus);
7074    } else {
7075        RLOGE("restrictedStateChangedInd: radioService[%d]->mRadioIndication == NULL",
7076                slotId);
7077    }
7078
7079    return 0;
7080}
7081
7082int radio::enterEmergencyCallbackModeInd(int slotId,
7083                                         int indicationType, int token, RIL_Errno e, void *response,
7084                                         size_t responseLen) {
7085    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7086#if VDBG
7087        RLOGD("enterEmergencyCallbackModeInd");
7088#endif
7089        Return<void> retStatus = radioService[slotId]->mRadioIndication->enterEmergencyCallbackMode(
7090                convertIntToRadioIndicationType(indicationType));
7091        radioService[slotId]->checkReturnStatus(retStatus);
7092    } else {
7093        RLOGE("enterEmergencyCallbackModeInd: radioService[%d]->mRadioIndication == NULL",
7094                slotId);
7095    }
7096
7097    return 0;
7098}
7099
7100int radio::cdmaCallWaitingInd(int slotId,
7101                              int indicationType, int token, RIL_Errno e, void *response,
7102                              size_t responseLen) {
7103    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7104        if (response == NULL || responseLen != sizeof(RIL_CDMA_CallWaiting_v6)) {
7105            RLOGE("cdmaCallWaitingInd: invalid response");
7106            return 0;
7107        }
7108
7109        CdmaCallWaiting callWaitingRecord = {};
7110        RIL_CDMA_CallWaiting_v6 *callWaitingRil = ((RIL_CDMA_CallWaiting_v6 *) response);
7111        callWaitingRecord.number = convertCharPtrToHidlString(callWaitingRil->number);
7112        callWaitingRecord.numberPresentation =
7113                (CdmaCallWaitingNumberPresentation) callWaitingRil->numberPresentation;
7114        callWaitingRecord.name = convertCharPtrToHidlString(callWaitingRil->name);
7115        convertRilCdmaSignalInfoRecordToHal(&callWaitingRil->signalInfoRecord,
7116                callWaitingRecord.signalInfoRecord);
7117        callWaitingRecord.numberType = (CdmaCallWaitingNumberType) callWaitingRil->number_type;
7118        callWaitingRecord.numberPlan = (CdmaCallWaitingNumberPlan) callWaitingRil->number_plan;
7119
7120#if VDBG
7121        RLOGD("cdmaCallWaitingInd");
7122#endif
7123        Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaCallWaiting(
7124                convertIntToRadioIndicationType(indicationType), callWaitingRecord);
7125        radioService[slotId]->checkReturnStatus(retStatus);
7126    } else {
7127        RLOGE("cdmaCallWaitingInd: radioService[%d]->mRadioIndication == NULL", slotId);
7128    }
7129
7130    return 0;
7131}
7132
7133int radio::cdmaOtaProvisionStatusInd(int slotId,
7134                                     int indicationType, int token, RIL_Errno e, void *response,
7135                                     size_t responseLen) {
7136    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7137        if (response == NULL || responseLen != sizeof(int)) {
7138            RLOGE("cdmaOtaProvisionStatusInd: invalid response");
7139            return 0;
7140        }
7141        int32_t status = ((int32_t *) response)[0];
7142#if VDBG
7143        RLOGD("cdmaOtaProvisionStatusInd: status %d", status);
7144#endif
7145        Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaOtaProvisionStatus(
7146                convertIntToRadioIndicationType(indicationType), (CdmaOtaProvisionStatus) status);
7147        radioService[slotId]->checkReturnStatus(retStatus);
7148    } else {
7149        RLOGE("cdmaOtaProvisionStatusInd: radioService[%d]->mRadioIndication == NULL",
7150                slotId);
7151    }
7152
7153    return 0;
7154}
7155
7156int radio::cdmaInfoRecInd(int slotId,
7157                          int indicationType, int token, RIL_Errno e, void *response,
7158                          size_t responseLen) {
7159    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7160        if (response == NULL || responseLen != sizeof(RIL_CDMA_InformationRecords)) {
7161            RLOGE("cdmaInfoRecInd: invalid response");
7162            return 0;
7163        }
7164
7165        CdmaInformationRecords records = {};
7166        RIL_CDMA_InformationRecords *recordsRil = (RIL_CDMA_InformationRecords *) response;
7167
7168        char* string8 = NULL;
7169        int num = MIN(recordsRil->numberOfInfoRecs, RIL_CDMA_MAX_NUMBER_OF_INFO_RECS);
7170        if (recordsRil->numberOfInfoRecs > RIL_CDMA_MAX_NUMBER_OF_INFO_RECS) {
7171            RLOGE("cdmaInfoRecInd: received %d recs which is more than %d, dropping "
7172                    "additional ones", recordsRil->numberOfInfoRecs,
7173                    RIL_CDMA_MAX_NUMBER_OF_INFO_RECS);
7174        }
7175        records.infoRec.resize(num);
7176        for (int i = 0 ; i < num ; i++) {
7177            CdmaInformationRecord *record = &records.infoRec[i];
7178            RIL_CDMA_InformationRecord *infoRec = &recordsRil->infoRec[i];
7179            record->name = (CdmaInfoRecName) infoRec->name;
7180            // All vectors should be size 0 except one which will be size 1. Set everything to
7181            // size 0 initially.
7182            record->display.resize(0);
7183            record->number.resize(0);
7184            record->signal.resize(0);
7185            record->redir.resize(0);
7186            record->lineCtrl.resize(0);
7187            record->clir.resize(0);
7188            record->audioCtrl.resize(0);
7189            switch (infoRec->name) {
7190                case RIL_CDMA_DISPLAY_INFO_REC:
7191                case RIL_CDMA_EXTENDED_DISPLAY_INFO_REC: {
7192                    if (infoRec->rec.display.alpha_len > CDMA_ALPHA_INFO_BUFFER_LENGTH) {
7193                        RLOGE("cdmaInfoRecInd: invalid display info response length %d "
7194                                "expected not more than %d", (int) infoRec->rec.display.alpha_len,
7195                                CDMA_ALPHA_INFO_BUFFER_LENGTH);
7196                        return 0;
7197                    }
7198                    string8 = (char*) malloc((infoRec->rec.display.alpha_len + 1) * sizeof(char));
7199                    if (string8 == NULL) {
7200                        RLOGE("cdmaInfoRecInd: Memory allocation failed for "
7201                                "responseCdmaInformationRecords");
7202                        return 0;
7203                    }
7204                    memcpy(string8, infoRec->rec.display.alpha_buf, infoRec->rec.display.alpha_len);
7205                    string8[(int)infoRec->rec.display.alpha_len] = '\0';
7206
7207                    record->display.resize(1);
7208                    record->display[0].alphaBuf = string8;
7209                    free(string8);
7210                    string8 = NULL;
7211                    break;
7212                }
7213
7214                case RIL_CDMA_CALLED_PARTY_NUMBER_INFO_REC:
7215                case RIL_CDMA_CALLING_PARTY_NUMBER_INFO_REC:
7216                case RIL_CDMA_CONNECTED_NUMBER_INFO_REC: {
7217                    if (infoRec->rec.number.len > CDMA_NUMBER_INFO_BUFFER_LENGTH) {
7218                        RLOGE("cdmaInfoRecInd: invalid display info response length %d "
7219                                "expected not more than %d", (int) infoRec->rec.number.len,
7220                                CDMA_NUMBER_INFO_BUFFER_LENGTH);
7221                        return 0;
7222                    }
7223                    string8 = (char*) malloc((infoRec->rec.number.len + 1) * sizeof(char));
7224                    if (string8 == NULL) {
7225                        RLOGE("cdmaInfoRecInd: Memory allocation failed for "
7226                                "responseCdmaInformationRecords");
7227                        return 0;
7228                    }
7229                    memcpy(string8, infoRec->rec.number.buf, infoRec->rec.number.len);
7230                    string8[(int)infoRec->rec.number.len] = '\0';
7231
7232                    record->number.resize(1);
7233                    record->number[0].number = string8;
7234                    free(string8);
7235                    string8 = NULL;
7236                    record->number[0].numberType = infoRec->rec.number.number_type;
7237                    record->number[0].numberPlan = infoRec->rec.number.number_plan;
7238                    record->number[0].pi = infoRec->rec.number.pi;
7239                    record->number[0].si = infoRec->rec.number.si;
7240                    break;
7241                }
7242
7243                case RIL_CDMA_SIGNAL_INFO_REC: {
7244                    record->signal.resize(1);
7245                    record->signal[0].isPresent = infoRec->rec.signal.isPresent;
7246                    record->signal[0].signalType = infoRec->rec.signal.signalType;
7247                    record->signal[0].alertPitch = infoRec->rec.signal.alertPitch;
7248                    record->signal[0].signal = infoRec->rec.signal.signal;
7249                    break;
7250                }
7251
7252                case RIL_CDMA_REDIRECTING_NUMBER_INFO_REC: {
7253                    if (infoRec->rec.redir.redirectingNumber.len >
7254                                                  CDMA_NUMBER_INFO_BUFFER_LENGTH) {
7255                        RLOGE("cdmaInfoRecInd: invalid display info response length %d "
7256                                "expected not more than %d\n",
7257                                (int)infoRec->rec.redir.redirectingNumber.len,
7258                                CDMA_NUMBER_INFO_BUFFER_LENGTH);
7259                        return 0;
7260                    }
7261                    string8 = (char*) malloc((infoRec->rec.redir.redirectingNumber.len + 1) *
7262                            sizeof(char));
7263                    if (string8 == NULL) {
7264                        RLOGE("cdmaInfoRecInd: Memory allocation failed for "
7265                                "responseCdmaInformationRecords");
7266                        return 0;
7267                    }
7268                    memcpy(string8, infoRec->rec.redir.redirectingNumber.buf,
7269                            infoRec->rec.redir.redirectingNumber.len);
7270                    string8[(int)infoRec->rec.redir.redirectingNumber.len] = '\0';
7271
7272                    record->redir.resize(1);
7273                    record->redir[0].redirectingNumber.number = string8;
7274                    free(string8);
7275                    string8 = NULL;
7276                    record->redir[0].redirectingNumber.numberType =
7277                            infoRec->rec.redir.redirectingNumber.number_type;
7278                    record->redir[0].redirectingNumber.numberPlan =
7279                            infoRec->rec.redir.redirectingNumber.number_plan;
7280                    record->redir[0].redirectingNumber.pi = infoRec->rec.redir.redirectingNumber.pi;
7281                    record->redir[0].redirectingNumber.si = infoRec->rec.redir.redirectingNumber.si;
7282                    record->redir[0].redirectingReason =
7283                            (CdmaRedirectingReason) infoRec->rec.redir.redirectingReason;
7284                    break;
7285                }
7286
7287                case RIL_CDMA_LINE_CONTROL_INFO_REC: {
7288                    record->lineCtrl.resize(1);
7289                    record->lineCtrl[0].lineCtrlPolarityIncluded =
7290                            infoRec->rec.lineCtrl.lineCtrlPolarityIncluded;
7291                    record->lineCtrl[0].lineCtrlToggle = infoRec->rec.lineCtrl.lineCtrlToggle;
7292                    record->lineCtrl[0].lineCtrlReverse = infoRec->rec.lineCtrl.lineCtrlReverse;
7293                    record->lineCtrl[0].lineCtrlPowerDenial =
7294                            infoRec->rec.lineCtrl.lineCtrlPowerDenial;
7295                    break;
7296                }
7297
7298                case RIL_CDMA_T53_CLIR_INFO_REC: {
7299                    record->clir.resize(1);
7300                    record->clir[0].cause = infoRec->rec.clir.cause;
7301                    break;
7302                }
7303
7304                case RIL_CDMA_T53_AUDIO_CONTROL_INFO_REC: {
7305                    record->audioCtrl.resize(1);
7306                    record->audioCtrl[0].upLink = infoRec->rec.audioCtrl.upLink;
7307                    record->audioCtrl[0].downLink = infoRec->rec.audioCtrl.downLink;
7308                    break;
7309                }
7310
7311                case RIL_CDMA_T53_RELEASE_INFO_REC:
7312                    RLOGE("cdmaInfoRecInd: RIL_CDMA_T53_RELEASE_INFO_REC: INVALID");
7313                    return 0;
7314
7315                default:
7316                    RLOGE("cdmaInfoRecInd: Incorrect name value");
7317                    return 0;
7318            }
7319        }
7320
7321#if VDBG
7322        RLOGD("cdmaInfoRecInd");
7323#endif
7324        Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaInfoRec(
7325                convertIntToRadioIndicationType(indicationType), records);
7326        radioService[slotId]->checkReturnStatus(retStatus);
7327    } else {
7328        RLOGE("cdmaInfoRecInd: radioService[%d]->mRadioIndication == NULL", slotId);
7329    }
7330
7331    return 0;
7332}
7333
7334int radio::indicateRingbackToneInd(int slotId,
7335                                   int indicationType, int token, RIL_Errno e, void *response,
7336                                   size_t responseLen) {
7337    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7338        if (response == NULL || responseLen != sizeof(int)) {
7339            RLOGE("indicateRingbackToneInd: invalid response");
7340            return 0;
7341        }
7342        bool start = ((int32_t *) response)[0];
7343#if VDBG
7344        RLOGD("indicateRingbackToneInd: start %d", start);
7345#endif
7346        Return<void> retStatus = radioService[slotId]->mRadioIndication->indicateRingbackTone(
7347                convertIntToRadioIndicationType(indicationType), start);
7348        radioService[slotId]->checkReturnStatus(retStatus);
7349    } else {
7350        RLOGE("indicateRingbackToneInd: radioService[%d]->mRadioIndication == NULL", slotId);
7351    }
7352
7353    return 0;
7354}
7355
7356int radio::resendIncallMuteInd(int slotId,
7357                               int indicationType, int token, RIL_Errno e, void *response,
7358                               size_t responseLen) {
7359    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7360#if VDBG
7361        RLOGD("resendIncallMuteInd");
7362#endif
7363        Return<void> retStatus = radioService[slotId]->mRadioIndication->resendIncallMute(
7364                convertIntToRadioIndicationType(indicationType));
7365        radioService[slotId]->checkReturnStatus(retStatus);
7366    } else {
7367        RLOGE("resendIncallMuteInd: radioService[%d]->mRadioIndication == NULL", slotId);
7368    }
7369
7370    return 0;
7371}
7372
7373int radio::cdmaSubscriptionSourceChangedInd(int slotId,
7374                                            int indicationType, int token, RIL_Errno e,
7375                                            void *response, size_t responseLen) {
7376    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7377        if (response == NULL || responseLen != sizeof(int)) {
7378            RLOGE("cdmaSubscriptionSourceChangedInd: invalid response");
7379            return 0;
7380        }
7381        int32_t cdmaSource = ((int32_t *) response)[0];
7382#if VDBG
7383        RLOGD("cdmaSubscriptionSourceChangedInd: cdmaSource %d", cdmaSource);
7384#endif
7385        Return<void> retStatus = radioService[slotId]->mRadioIndication->
7386                cdmaSubscriptionSourceChanged(convertIntToRadioIndicationType(indicationType),
7387                (CdmaSubscriptionSource) cdmaSource);
7388        radioService[slotId]->checkReturnStatus(retStatus);
7389    } else {
7390        RLOGE("cdmaSubscriptionSourceChangedInd: radioService[%d]->mRadioIndication == NULL",
7391                slotId);
7392    }
7393
7394    return 0;
7395}
7396
7397int radio::cdmaPrlChangedInd(int slotId,
7398                             int indicationType, int token, RIL_Errno e, void *response,
7399                             size_t responseLen) {
7400    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7401        if (response == NULL || responseLen != sizeof(int)) {
7402            RLOGE("cdmaPrlChangedInd: invalid response");
7403            return 0;
7404        }
7405        int32_t version = ((int32_t *) response)[0];
7406#if VDBG
7407        RLOGD("cdmaPrlChangedInd: version %d", version);
7408#endif
7409        Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaPrlChanged(
7410                convertIntToRadioIndicationType(indicationType), version);
7411        radioService[slotId]->checkReturnStatus(retStatus);
7412    } else {
7413        RLOGE("cdmaPrlChangedInd: radioService[%d]->mRadioIndication == NULL", slotId);
7414    }
7415
7416    return 0;
7417}
7418
7419int radio::exitEmergencyCallbackModeInd(int slotId,
7420                                        int indicationType, int token, RIL_Errno e, void *response,
7421                                        size_t responseLen) {
7422    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7423#if VDBG
7424        RLOGD("exitEmergencyCallbackModeInd");
7425#endif
7426        Return<void> retStatus = radioService[slotId]->mRadioIndication->exitEmergencyCallbackMode(
7427                convertIntToRadioIndicationType(indicationType));
7428        radioService[slotId]->checkReturnStatus(retStatus);
7429    } else {
7430        RLOGE("exitEmergencyCallbackModeInd: radioService[%d]->mRadioIndication == NULL",
7431                slotId);
7432    }
7433
7434    return 0;
7435}
7436
7437int radio::rilConnectedInd(int slotId,
7438                           int indicationType, int token, RIL_Errno e, void *response,
7439                           size_t responseLen) {
7440    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7441        RLOGD("rilConnectedInd");
7442        Return<void> retStatus = radioService[slotId]->mRadioIndication->rilConnected(
7443                convertIntToRadioIndicationType(indicationType));
7444        radioService[slotId]->checkReturnStatus(retStatus);
7445    } else {
7446        RLOGE("rilConnectedInd: radioService[%d]->mRadioIndication == NULL", slotId);
7447    }
7448
7449    return 0;
7450}
7451
7452int radio::voiceRadioTechChangedInd(int slotId,
7453                                    int indicationType, int token, RIL_Errno e, void *response,
7454                                    size_t responseLen) {
7455    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7456        if (response == NULL || responseLen != sizeof(int)) {
7457            RLOGE("voiceRadioTechChangedInd: invalid response");
7458            return 0;
7459        }
7460        int32_t rat = ((int32_t *) response)[0];
7461#if VDBG
7462        RLOGD("voiceRadioTechChangedInd: rat %d", rat);
7463#endif
7464        Return<void> retStatus = radioService[slotId]->mRadioIndication->voiceRadioTechChanged(
7465                convertIntToRadioIndicationType(indicationType), (RadioTechnology) rat);
7466        radioService[slotId]->checkReturnStatus(retStatus);
7467    } else {
7468        RLOGE("voiceRadioTechChangedInd: radioService[%d]->mRadioIndication == NULL",
7469                slotId);
7470    }
7471
7472    return 0;
7473}
7474
7475void convertRilCellInfoListToHal(void *response, size_t responseLen, hidl_vec<CellInfo>& records) {
7476    int num = responseLen / sizeof(RIL_CellInfo_v12);
7477    records.resize(num);
7478
7479    RIL_CellInfo_v12 *rillCellInfo = (RIL_CellInfo_v12 *) response;
7480    for (int i = 0; i < num; i++) {
7481        records[i].cellInfoType = (CellInfoType) rillCellInfo->cellInfoType;
7482        records[i].registered = rillCellInfo->registered;
7483        records[i].timeStampType = (TimeStampType) rillCellInfo->timeStampType;
7484        records[i].timeStamp = rillCellInfo->timeStamp;
7485        // All vectors should be size 0 except one which will be size 1. Set everything to
7486        // size 0 initially.
7487        records[i].gsm.resize(0);
7488        records[i].wcdma.resize(0);
7489        records[i].cdma.resize(0);
7490        records[i].lte.resize(0);
7491        records[i].tdscdma.resize(0);
7492        switch(rillCellInfo->cellInfoType) {
7493            case RIL_CELL_INFO_TYPE_GSM: {
7494                records[i].gsm.resize(1);
7495                CellInfoGsm *cellInfoGsm = &records[i].gsm[0];
7496                cellInfoGsm->cellIdentityGsm.mcc =
7497                        std::to_string(rillCellInfo->CellInfo.gsm.cellIdentityGsm.mcc);
7498                cellInfoGsm->cellIdentityGsm.mnc =
7499                        std::to_string(rillCellInfo->CellInfo.gsm.cellIdentityGsm.mnc);
7500                cellInfoGsm->cellIdentityGsm.lac =
7501                        rillCellInfo->CellInfo.gsm.cellIdentityGsm.lac;
7502                cellInfoGsm->cellIdentityGsm.cid =
7503                        rillCellInfo->CellInfo.gsm.cellIdentityGsm.cid;
7504                cellInfoGsm->cellIdentityGsm.arfcn =
7505                        rillCellInfo->CellInfo.gsm.cellIdentityGsm.arfcn;
7506                cellInfoGsm->cellIdentityGsm.bsic =
7507                        rillCellInfo->CellInfo.gsm.cellIdentityGsm.bsic;
7508                cellInfoGsm->signalStrengthGsm.signalStrength =
7509                        rillCellInfo->CellInfo.gsm.signalStrengthGsm.signalStrength;
7510                cellInfoGsm->signalStrengthGsm.bitErrorRate =
7511                        rillCellInfo->CellInfo.gsm.signalStrengthGsm.bitErrorRate;
7512                cellInfoGsm->signalStrengthGsm.timingAdvance =
7513                        rillCellInfo->CellInfo.gsm.signalStrengthGsm.timingAdvance;
7514                break;
7515            }
7516
7517            case RIL_CELL_INFO_TYPE_WCDMA: {
7518                records[i].wcdma.resize(1);
7519                CellInfoWcdma *cellInfoWcdma = &records[i].wcdma[0];
7520                cellInfoWcdma->cellIdentityWcdma.mcc =
7521                        std::to_string(rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.mcc);
7522                cellInfoWcdma->cellIdentityWcdma.mnc =
7523                        std::to_string(rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.mnc);
7524                cellInfoWcdma->cellIdentityWcdma.lac =
7525                        rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.lac;
7526                cellInfoWcdma->cellIdentityWcdma.cid =
7527                        rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.cid;
7528                cellInfoWcdma->cellIdentityWcdma.psc =
7529                        rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.psc;
7530                cellInfoWcdma->cellIdentityWcdma.uarfcn =
7531                        rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.uarfcn;
7532                cellInfoWcdma->signalStrengthWcdma.signalStrength =
7533                        rillCellInfo->CellInfo.wcdma.signalStrengthWcdma.signalStrength;
7534                cellInfoWcdma->signalStrengthWcdma.bitErrorRate =
7535                        rillCellInfo->CellInfo.wcdma.signalStrengthWcdma.bitErrorRate;
7536                break;
7537            }
7538
7539            case RIL_CELL_INFO_TYPE_CDMA: {
7540                records[i].cdma.resize(1);
7541                CellInfoCdma *cellInfoCdma = &records[i].cdma[0];
7542                cellInfoCdma->cellIdentityCdma.networkId =
7543                        rillCellInfo->CellInfo.cdma.cellIdentityCdma.networkId;
7544                cellInfoCdma->cellIdentityCdma.systemId =
7545                        rillCellInfo->CellInfo.cdma.cellIdentityCdma.systemId;
7546                cellInfoCdma->cellIdentityCdma.baseStationId =
7547                        rillCellInfo->CellInfo.cdma.cellIdentityCdma.basestationId;
7548                cellInfoCdma->cellIdentityCdma.longitude =
7549                        rillCellInfo->CellInfo.cdma.cellIdentityCdma.longitude;
7550                cellInfoCdma->cellIdentityCdma.latitude =
7551                        rillCellInfo->CellInfo.cdma.cellIdentityCdma.latitude;
7552                cellInfoCdma->signalStrengthCdma.dbm =
7553                        rillCellInfo->CellInfo.cdma.signalStrengthCdma.dbm;
7554                cellInfoCdma->signalStrengthCdma.ecio =
7555                        rillCellInfo->CellInfo.cdma.signalStrengthCdma.ecio;
7556                cellInfoCdma->signalStrengthEvdo.dbm =
7557                        rillCellInfo->CellInfo.cdma.signalStrengthEvdo.dbm;
7558                cellInfoCdma->signalStrengthEvdo.ecio =
7559                        rillCellInfo->CellInfo.cdma.signalStrengthEvdo.ecio;
7560                cellInfoCdma->signalStrengthEvdo.signalNoiseRatio =
7561                        rillCellInfo->CellInfo.cdma.signalStrengthEvdo.signalNoiseRatio;
7562                break;
7563            }
7564
7565            case RIL_CELL_INFO_TYPE_LTE: {
7566                records[i].lte.resize(1);
7567                CellInfoLte *cellInfoLte = &records[i].lte[0];
7568                cellInfoLte->cellIdentityLte.mcc =
7569                        std::to_string(rillCellInfo->CellInfo.lte.cellIdentityLte.mcc);
7570                cellInfoLte->cellIdentityLte.mnc =
7571                        std::to_string(rillCellInfo->CellInfo.lte.cellIdentityLte.mnc);
7572                cellInfoLte->cellIdentityLte.ci =
7573                        rillCellInfo->CellInfo.lte.cellIdentityLte.ci;
7574                cellInfoLte->cellIdentityLte.pci =
7575                        rillCellInfo->CellInfo.lte.cellIdentityLte.pci;
7576                cellInfoLte->cellIdentityLte.tac =
7577                        rillCellInfo->CellInfo.lte.cellIdentityLte.tac;
7578                cellInfoLte->cellIdentityLte.earfcn =
7579                        rillCellInfo->CellInfo.lte.cellIdentityLte.earfcn;
7580                cellInfoLte->signalStrengthLte.signalStrength =
7581                        rillCellInfo->CellInfo.lte.signalStrengthLte.signalStrength;
7582                cellInfoLte->signalStrengthLte.rsrp =
7583                        rillCellInfo->CellInfo.lte.signalStrengthLte.rsrp;
7584                cellInfoLte->signalStrengthLte.rsrq =
7585                        rillCellInfo->CellInfo.lte.signalStrengthLte.rsrq;
7586                cellInfoLte->signalStrengthLte.rssnr =
7587                        rillCellInfo->CellInfo.lte.signalStrengthLte.rssnr;
7588                cellInfoLte->signalStrengthLte.cqi =
7589                        rillCellInfo->CellInfo.lte.signalStrengthLte.cqi;
7590                cellInfoLte->signalStrengthLte.timingAdvance =
7591                        rillCellInfo->CellInfo.lte.signalStrengthLte.timingAdvance;
7592                break;
7593            }
7594
7595            case RIL_CELL_INFO_TYPE_TD_SCDMA: {
7596                records[i].tdscdma.resize(1);
7597                CellInfoTdscdma *cellInfoTdscdma = &records[i].tdscdma[0];
7598                cellInfoTdscdma->cellIdentityTdscdma.mcc =
7599                        std::to_string(rillCellInfo->CellInfo.tdscdma.cellIdentityTdscdma.mcc);
7600                cellInfoTdscdma->cellIdentityTdscdma.mnc =
7601                        std::to_string(rillCellInfo->CellInfo.tdscdma.cellIdentityTdscdma.mnc);
7602                cellInfoTdscdma->cellIdentityTdscdma.lac =
7603                        rillCellInfo->CellInfo.tdscdma.cellIdentityTdscdma.lac;
7604                cellInfoTdscdma->cellIdentityTdscdma.cid =
7605                        rillCellInfo->CellInfo.tdscdma.cellIdentityTdscdma.cid;
7606                cellInfoTdscdma->cellIdentityTdscdma.cpid =
7607                        rillCellInfo->CellInfo.tdscdma.cellIdentityTdscdma.cpid;
7608                cellInfoTdscdma->signalStrengthTdscdma.rscp =
7609                        rillCellInfo->CellInfo.tdscdma.signalStrengthTdscdma.rscp;
7610                break;
7611            }
7612            default: {
7613                break;
7614            }
7615        }
7616        rillCellInfo += 1;
7617    }
7618}
7619
7620int radio::cellInfoListInd(int slotId,
7621                           int indicationType, int token, RIL_Errno e, void *response,
7622                           size_t responseLen) {
7623    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7624        if (response == NULL || responseLen % sizeof(RIL_CellInfo_v12) != 0) {
7625            RLOGE("cellInfoListInd: invalid response");
7626            return 0;
7627        }
7628
7629        hidl_vec<CellInfo> records;
7630        convertRilCellInfoListToHal(response, responseLen, records);
7631
7632#if VDBG
7633        RLOGD("cellInfoListInd");
7634#endif
7635        Return<void> retStatus = radioService[slotId]->mRadioIndication->cellInfoList(
7636                convertIntToRadioIndicationType(indicationType), records);
7637        radioService[slotId]->checkReturnStatus(retStatus);
7638    } else {
7639        RLOGE("cellInfoListInd: radioService[%d]->mRadioIndication == NULL", slotId);
7640    }
7641
7642    return 0;
7643}
7644
7645int radio::imsNetworkStateChangedInd(int slotId,
7646                                     int indicationType, int token, RIL_Errno e, void *response,
7647                                     size_t responseLen) {
7648    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7649#if VDBG
7650        RLOGD("imsNetworkStateChangedInd");
7651#endif
7652        Return<void> retStatus = radioService[slotId]->mRadioIndication->imsNetworkStateChanged(
7653                convertIntToRadioIndicationType(indicationType));
7654        radioService[slotId]->checkReturnStatus(retStatus);
7655    } else {
7656        RLOGE("imsNetworkStateChangedInd: radioService[%d]->mRadioIndication == NULL",
7657                slotId);
7658    }
7659
7660    return 0;
7661}
7662
7663int radio::subscriptionStatusChangedInd(int slotId,
7664                                        int indicationType, int token, RIL_Errno e, void *response,
7665                                        size_t responseLen) {
7666    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7667        if (response == NULL || responseLen != sizeof(int)) {
7668            RLOGE("subscriptionStatusChangedInd: invalid response");
7669            return 0;
7670        }
7671        bool activate = ((int32_t *) response)[0];
7672#if VDBG
7673        RLOGD("subscriptionStatusChangedInd: activate %d", activate);
7674#endif
7675        Return<void> retStatus = radioService[slotId]->mRadioIndication->subscriptionStatusChanged(
7676                convertIntToRadioIndicationType(indicationType), activate);
7677        radioService[slotId]->checkReturnStatus(retStatus);
7678    } else {
7679        RLOGE("subscriptionStatusChangedInd: radioService[%d]->mRadioIndication == NULL",
7680                slotId);
7681    }
7682
7683    return 0;
7684}
7685
7686int radio::srvccStateNotifyInd(int slotId,
7687                               int indicationType, int token, RIL_Errno e, void *response,
7688                               size_t responseLen) {
7689    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7690        if (response == NULL || responseLen != sizeof(int)) {
7691            RLOGE("srvccStateNotifyInd: invalid response");
7692            return 0;
7693        }
7694        int32_t state = ((int32_t *) response)[0];
7695#if VDBG
7696        RLOGD("srvccStateNotifyInd: rat %d", state);
7697#endif
7698        Return<void> retStatus = radioService[slotId]->mRadioIndication->srvccStateNotify(
7699                convertIntToRadioIndicationType(indicationType), (SrvccState) state);
7700        radioService[slotId]->checkReturnStatus(retStatus);
7701    } else {
7702        RLOGE("srvccStateNotifyInd: radioService[%d]->mRadioIndication == NULL", slotId);
7703    }
7704
7705    return 0;
7706}
7707
7708void convertRilHardwareConfigListToHal(void *response, size_t responseLen,
7709        hidl_vec<HardwareConfig>& records) {
7710    int num = responseLen / sizeof(RIL_HardwareConfig);
7711    records.resize(num);
7712
7713    RIL_HardwareConfig *rilHardwareConfig = (RIL_HardwareConfig *) response;
7714    for (int i = 0; i < num; i++) {
7715        records[i].type = (HardwareConfigType) rilHardwareConfig[i].type;
7716        records[i].uuid = convertCharPtrToHidlString(rilHardwareConfig[i].uuid);
7717        records[i].state = (HardwareConfigState) rilHardwareConfig[i].state;
7718        switch (rilHardwareConfig[i].type) {
7719            case RIL_HARDWARE_CONFIG_MODEM: {
7720                records[i].modem.resize(1);
7721                records[i].sim.resize(0);
7722                HardwareConfigModem *hwConfigModem = &records[i].modem[0];
7723                hwConfigModem->rat = rilHardwareConfig[i].cfg.modem.rat;
7724                hwConfigModem->maxVoice = rilHardwareConfig[i].cfg.modem.maxVoice;
7725                hwConfigModem->maxData = rilHardwareConfig[i].cfg.modem.maxData;
7726                hwConfigModem->maxStandby = rilHardwareConfig[i].cfg.modem.maxStandby;
7727                break;
7728            }
7729
7730            case RIL_HARDWARE_CONFIG_SIM: {
7731                records[i].sim.resize(1);
7732                records[i].modem.resize(0);
7733                records[i].sim[0].modemUuid =
7734                        convertCharPtrToHidlString(rilHardwareConfig[i].cfg.sim.modemUuid);
7735                break;
7736            }
7737        }
7738    }
7739}
7740
7741int radio::hardwareConfigChangedInd(int slotId,
7742                                    int indicationType, int token, RIL_Errno e, void *response,
7743                                    size_t responseLen) {
7744    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7745        if (response == NULL || responseLen % sizeof(RIL_HardwareConfig) != 0) {
7746            RLOGE("hardwareConfigChangedInd: invalid response");
7747            return 0;
7748        }
7749
7750        hidl_vec<HardwareConfig> configs;
7751        convertRilHardwareConfigListToHal(response, responseLen, configs);
7752
7753#if VDBG
7754        RLOGD("hardwareConfigChangedInd");
7755#endif
7756        Return<void> retStatus = radioService[slotId]->mRadioIndication->hardwareConfigChanged(
7757                convertIntToRadioIndicationType(indicationType), configs);
7758        radioService[slotId]->checkReturnStatus(retStatus);
7759    } else {
7760        RLOGE("hardwareConfigChangedInd: radioService[%d]->mRadioIndication == NULL",
7761                slotId);
7762    }
7763
7764    return 0;
7765}
7766
7767void convertRilRadioCapabilityToHal(void *response, size_t responseLen, RadioCapability& rc) {
7768    RIL_RadioCapability *rilRadioCapability = (RIL_RadioCapability *) response;
7769    rc.session = rilRadioCapability->session;
7770    rc.phase = (android::hardware::radio::V1_0::RadioCapabilityPhase) rilRadioCapability->phase;
7771    rc.raf = rilRadioCapability->rat;
7772    rc.logicalModemUuid = convertCharPtrToHidlString(rilRadioCapability->logicalModemUuid);
7773    rc.status = (android::hardware::radio::V1_0::RadioCapabilityStatus) rilRadioCapability->status;
7774}
7775
7776int radio::radioCapabilityIndicationInd(int slotId,
7777                                        int indicationType, int token, RIL_Errno e, void *response,
7778                                        size_t responseLen) {
7779    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7780        if (response == NULL || responseLen != sizeof(RIL_RadioCapability)) {
7781            RLOGE("radioCapabilityIndicationInd: invalid response");
7782            return 0;
7783        }
7784
7785        RadioCapability rc = {};
7786        convertRilRadioCapabilityToHal(response, responseLen, rc);
7787
7788#if VDBG
7789        RLOGD("radioCapabilityIndicationInd");
7790#endif
7791        Return<void> retStatus = radioService[slotId]->mRadioIndication->radioCapabilityIndication(
7792                convertIntToRadioIndicationType(indicationType), rc);
7793        radioService[slotId]->checkReturnStatus(retStatus);
7794    } else {
7795        RLOGE("radioCapabilityIndicationInd: radioService[%d]->mRadioIndication == NULL",
7796                slotId);
7797    }
7798
7799    return 0;
7800}
7801
7802bool isServiceTypeCfQuery(RIL_SsServiceType serType, RIL_SsRequestType reqType) {
7803    if ((reqType == SS_INTERROGATION) &&
7804        (serType == SS_CFU ||
7805         serType == SS_CF_BUSY ||
7806         serType == SS_CF_NO_REPLY ||
7807         serType == SS_CF_NOT_REACHABLE ||
7808         serType == SS_CF_ALL ||
7809         serType == SS_CF_ALL_CONDITIONAL)) {
7810        return true;
7811    }
7812    return false;
7813}
7814
7815int radio::onSupplementaryServiceIndicationInd(int slotId,
7816                                               int indicationType, int token, RIL_Errno e,
7817                                               void *response, size_t responseLen) {
7818    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7819        if (response == NULL || responseLen != sizeof(RIL_StkCcUnsolSsResponse)) {
7820            RLOGE("onSupplementaryServiceIndicationInd: invalid response");
7821            return 0;
7822        }
7823
7824        RIL_StkCcUnsolSsResponse *rilSsResponse = (RIL_StkCcUnsolSsResponse *) response;
7825        StkCcUnsolSsResult ss = {};
7826        ss.serviceType = (SsServiceType) rilSsResponse->serviceType;
7827        ss.requestType = (SsRequestType) rilSsResponse->requestType;
7828        ss.teleserviceType = (SsTeleserviceType) rilSsResponse->teleserviceType;
7829        ss.serviceClass = rilSsResponse->serviceClass;
7830        ss.result = (RadioError) rilSsResponse->result;
7831
7832        if (isServiceTypeCfQuery(rilSsResponse->serviceType, rilSsResponse->requestType)) {
7833#if VDBG
7834            RLOGD("onSupplementaryServiceIndicationInd CF type, num of Cf elements %d",
7835                    rilSsResponse->cfData.numValidIndexes);
7836#endif
7837            if (rilSsResponse->cfData.numValidIndexes > NUM_SERVICE_CLASSES) {
7838                RLOGE("onSupplementaryServiceIndicationInd numValidIndexes is greater than "
7839                        "max value %d, truncating it to max value", NUM_SERVICE_CLASSES);
7840                rilSsResponse->cfData.numValidIndexes = NUM_SERVICE_CLASSES;
7841            }
7842
7843            ss.cfData.resize(1);
7844            ss.ssInfo.resize(0);
7845
7846            /* number of call info's */
7847            ss.cfData[0].cfInfo.resize(rilSsResponse->cfData.numValidIndexes);
7848
7849            for (int i = 0; i < rilSsResponse->cfData.numValidIndexes; i++) {
7850                 RIL_CallForwardInfo cf = rilSsResponse->cfData.cfInfo[i];
7851                 CallForwardInfo *cfInfo = &ss.cfData[0].cfInfo[i];
7852
7853                 cfInfo->status = (CallForwardInfoStatus) cf.status;
7854                 cfInfo->reason = cf.reason;
7855                 cfInfo->serviceClass = cf.serviceClass;
7856                 cfInfo->toa = cf.toa;
7857                 cfInfo->number = convertCharPtrToHidlString(cf.number);
7858                 cfInfo->timeSeconds = cf.timeSeconds;
7859#if VDBG
7860                 RLOGD("onSupplementaryServiceIndicationInd: "
7861                        "Data: %d,reason=%d,cls=%d,toa=%d,num=%s,tout=%d],", cf.status,
7862                        cf.reason, cf.serviceClass, cf.toa, (char*)cf.number, cf.timeSeconds);
7863#endif
7864            }
7865        } else {
7866            ss.ssInfo.resize(1);
7867            ss.cfData.resize(0);
7868
7869            /* each int */
7870            ss.ssInfo[0].ssInfo.resize(SS_INFO_MAX);
7871            for (int i = 0; i < SS_INFO_MAX; i++) {
7872#if VDBG
7873                 RLOGD("onSupplementaryServiceIndicationInd: Data: %d",
7874                        rilSsResponse->ssInfo[i]);
7875#endif
7876                 ss.ssInfo[0].ssInfo[i] = rilSsResponse->ssInfo[i];
7877            }
7878        }
7879
7880#if VDBG
7881        RLOGD("onSupplementaryServiceIndicationInd");
7882#endif
7883        Return<void> retStatus = radioService[slotId]->mRadioIndication->
7884                onSupplementaryServiceIndication(convertIntToRadioIndicationType(indicationType),
7885                ss);
7886        radioService[slotId]->checkReturnStatus(retStatus);
7887    } else {
7888        RLOGE("onSupplementaryServiceIndicationInd: "
7889                "radioService[%d]->mRadioIndication == NULL", slotId);
7890    }
7891
7892    return 0;
7893}
7894
7895int radio::stkCallControlAlphaNotifyInd(int slotId,
7896                                        int indicationType, int token, RIL_Errno e, void *response,
7897                                        size_t responseLen) {
7898    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7899        if (response == NULL || responseLen == 0) {
7900            RLOGE("stkCallControlAlphaNotifyInd: invalid response");
7901            return 0;
7902        }
7903#if VDBG
7904        RLOGD("stkCallControlAlphaNotifyInd");
7905#endif
7906        Return<void> retStatus = radioService[slotId]->mRadioIndication->stkCallControlAlphaNotify(
7907                convertIntToRadioIndicationType(indicationType),
7908                convertCharPtrToHidlString((char *) response));
7909        radioService[slotId]->checkReturnStatus(retStatus);
7910    } else {
7911        RLOGE("stkCallControlAlphaNotifyInd: radioService[%d]->mRadioIndication == NULL",
7912                slotId);
7913    }
7914
7915    return 0;
7916}
7917
7918void convertRilLceDataInfoToHal(void *response, size_t responseLen, LceDataInfo& lce) {
7919    RIL_LceDataInfo *rilLceDataInfo = (RIL_LceDataInfo *)response;
7920    lce.lastHopCapacityKbps = rilLceDataInfo->last_hop_capacity_kbps;
7921    lce.confidenceLevel = rilLceDataInfo->confidence_level;
7922    lce.lceSuspended = rilLceDataInfo->lce_suspended;
7923}
7924
7925int radio::lceDataInd(int slotId,
7926                      int indicationType, int token, RIL_Errno e, void *response,
7927                      size_t responseLen) {
7928    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7929        if (response == NULL || responseLen != sizeof(RIL_LceDataInfo)) {
7930            RLOGE("lceDataInd: invalid response");
7931            return 0;
7932        }
7933
7934        LceDataInfo lce = {};
7935        convertRilLceDataInfoToHal(response, responseLen, lce);
7936#if VDBG
7937        RLOGD("lceDataInd");
7938#endif
7939        Return<void> retStatus = radioService[slotId]->mRadioIndication->lceData(
7940                convertIntToRadioIndicationType(indicationType), lce);
7941        radioService[slotId]->checkReturnStatus(retStatus);
7942    } else {
7943        RLOGE("lceDataInd: radioService[%d]->mRadioIndication == NULL", slotId);
7944    }
7945
7946    return 0;
7947}
7948
7949int radio::pcoDataInd(int slotId,
7950                      int indicationType, int token, RIL_Errno e, void *response,
7951                      size_t responseLen) {
7952    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7953        if (response == NULL || responseLen != sizeof(RIL_PCO_Data)) {
7954            RLOGE("pcoDataInd: invalid response");
7955            return 0;
7956        }
7957
7958        PcoDataInfo pco = {};
7959        RIL_PCO_Data *rilPcoData = (RIL_PCO_Data *)response;
7960        pco.cid = rilPcoData->cid;
7961        pco.bearerProto = convertCharPtrToHidlString(rilPcoData->bearer_proto);
7962        pco.pcoId = rilPcoData->pco_id;
7963        pco.contents.setToExternal((uint8_t *) rilPcoData->contents, rilPcoData->contents_length);
7964
7965#if VDBG
7966        RLOGD("pcoDataInd");
7967#endif
7968        Return<void> retStatus = radioService[slotId]->mRadioIndication->pcoData(
7969                convertIntToRadioIndicationType(indicationType), pco);
7970        radioService[slotId]->checkReturnStatus(retStatus);
7971    } else {
7972        RLOGE("pcoDataInd: radioService[%d]->mRadioIndication == NULL", slotId);
7973    }
7974
7975    return 0;
7976}
7977
7978int radio::modemResetInd(int slotId,
7979                         int indicationType, int token, RIL_Errno e, void *response,
7980                         size_t responseLen) {
7981    if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) {
7982        if (response == NULL || responseLen == 0) {
7983            RLOGE("modemResetInd: invalid response");
7984            return 0;
7985        }
7986#if VDBG
7987        RLOGD("modemResetInd");
7988#endif
7989        Return<void> retStatus = radioService[slotId]->mRadioIndication->modemReset(
7990                convertIntToRadioIndicationType(indicationType),
7991                convertCharPtrToHidlString((char *) response));
7992        radioService[slotId]->checkReturnStatus(retStatus);
7993    } else {
7994        RLOGE("modemResetInd: radioService[%d]->mRadioIndication == NULL", slotId);
7995    }
7996
7997    return 0;
7998}
7999
8000int radio::oemHookRawInd(int slotId,
8001                         int indicationType, int token, RIL_Errno e, void *response,
8002                         size_t responseLen) {
8003    if (oemHookService[slotId] != NULL && oemHookService[slotId]->mOemHookIndication != NULL) {
8004        if (response == NULL || responseLen == 0) {
8005            RLOGE("oemHookRawInd: invalid response");
8006            return 0;
8007        }
8008
8009        hidl_vec<uint8_t> data;
8010        data.setToExternal((uint8_t *) response, responseLen);
8011#if VDBG
8012        RLOGD("oemHookRawInd");
8013#endif
8014        Return<void> retStatus = oemHookService[slotId]->mOemHookIndication->oemHookRaw(
8015                convertIntToRadioIndicationType(indicationType), data);
8016        checkReturnStatus(slotId, retStatus, false);
8017    } else {
8018        RLOGE("oemHookRawInd: oemHookService[%d]->mOemHookIndication == NULL", slotId);
8019    }
8020
8021    return 0;
8022}
8023
8024void radio::registerService(RIL_RadioFunctions *callbacks, CommandInfo *commands) {
8025    using namespace android::hardware;
8026    int simCount = 1;
8027    const char *serviceNames[] = {
8028            android::RIL_getServiceName()
8029            #if (SIM_COUNT >= 2)
8030            , RIL2_SERVICE_NAME
8031            #if (SIM_COUNT >= 3)
8032            , RIL3_SERVICE_NAME
8033            #if (SIM_COUNT >= 4)
8034            , RIL4_SERVICE_NAME
8035            #endif
8036            #endif
8037            #endif
8038            };
8039
8040    #if (SIM_COUNT >= 2)
8041    simCount = SIM_COUNT;
8042    #endif
8043
8044    configureRpcThreadpool(1, true /* callerWillJoin */);
8045    for (int i = 0; i < simCount; i++) {
8046        pthread_rwlock_t *radioServiceRwlockPtr = getRadioServiceRwlock(i);
8047        int ret = pthread_rwlock_wrlock(radioServiceRwlockPtr);
8048        assert(ret == 0);
8049
8050        radioService[i] = new RadioImpl;
8051        radioService[i]->mSlotId = i;
8052        oemHookService[i] = new OemHookImpl;
8053        oemHookService[i]->mSlotId = i;
8054        RLOGD("registerService: starting IRadio %s", serviceNames[i]);
8055        android::status_t status = radioService[i]->registerAsService(serviceNames[i]);
8056        status = oemHookService[i]->registerAsService(serviceNames[i]);
8057
8058        ret = pthread_rwlock_unlock(radioServiceRwlockPtr);
8059        assert(ret == 0);
8060    }
8061
8062    s_vendorFunctions = callbacks;
8063    s_commands = commands;
8064}
8065
8066void rilc_thread_pool() {
8067    joinRpcThreadpool();
8068}
8069
8070pthread_rwlock_t * radio::getRadioServiceRwlock(int slotId) {
8071    pthread_rwlock_t *radioServiceRwlockPtr = &radioServiceRwlock;
8072
8073    #if (SIM_COUNT >= 2)
8074    if (slotId == 2) radioServiceRwlockPtr = &radioServiceRwlock2;
8075    #if (SIM_COUNT >= 3)
8076    if (slotId == 3) radioServiceRwlockPtr = &radioServiceRwlock3;
8077    #if (SIM_COUNT >= 4)
8078    if (slotId == 4) radioServiceRwlockPtr = &radioServiceRwlock4;
8079    #endif
8080    #endif
8081    #endif
8082
8083    return radioServiceRwlockPtr;
8084}
8085