• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2021-2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "cellular_call_supplement.h"
17 
18 #include "cellular_call_register.h"
19 #include "cellular_call_service.h"
20 #include "securec.h"
21 #include "standardize_utils.h"
22 #include "telephony_errors.h"
23 #include "telephony_log_wrapper.h"
24 
25 namespace OHOS {
26 namespace Telephony {
27 const int32_t ACTIVATE_ACTION = 1;
28 const int32_t DEACTIVATE_ACTION = 2;
29 const int32_t USSD_MODE_NOTIFY = 0;
30 const int32_t USSD_MODE_REQUEST = 1;
31 const int32_t USSD_MODE_NW_RELEASE = 2;
32 const int32_t USSD_SUCCESS = 0;
33 const int32_t USSD_FAILED = 1;
34 const int32_t RESULT_SUCCESS = 0;
35 const int32_t MMI_CODE_FAILED = 1;
36 const int32_t PIN_PUK_MIN = 4;
37 const int32_t PIN_PUK_MAX = 8;
38 const std::string BARR_ALL_OUTGOING_CALLS = "AO";
39 const std::string BARR_OUTGOING_INTERNATIONAL_CALLS = "OI";
40 const std::string BARR_OUTGOING_INTERNATIONAL_CALLS_EXCLUDING_HOME = "OX";
41 const std::string BARR_ALL_INCOMING_CALLS = "AI";
42 const std::string BARR_INCOMING_CALLS_OUTSIDE_HOME = "IR";
43 const std::string ALL_BARRING_SERVICES = "AB";
44 const std::string ALL_OUTGOING_BARRING_SERVICES = "AG";
45 const std::string ALL_INCOMING_BARRING_SERVICES = "AC";
46 const std::string TRANSFER_UNCONDITIONAL_SUCCESS = "Transfer unconditional success";
47 const std::string TRANSFER_BUSY_SUCCESS = "Transfer busy success";
48 const std::string TRANSFER_NO_REPLYL_SUCCESS = "Transfer no replay success";
49 const std::string TRANSFER_NOT_REACHABLE_SUCCESS = "Transfer not reachable success";
50 const std::string QUERY_SS_SUCCESS = "Query SS success";
51 const std::string QUERY_SS_FAILED = "Query SS failed";
52 const std::string INVALID_MMI_CODE = "Invalid MMI code";
53 const std::string GET_CALL_WAITING_SUCCESS = "Get call waiting success";
54 const std::string GET_CALL_WAITING_FAILED = "Get call waiting failed";
55 const std::string SET_CALL_WAITING_SUCCESS = "Set call waiting success";
56 const std::string SET_CALL_WAITING_FAILED = "Set call waiting failed";
57 const std::string GET_CALL_TRANSFER_SUCCESS = "Get call transfer success";
58 const std::string GET_CALL_TRANSFER_FAILED = "Get call transfer failed";
59 const std::string SET_CALL_TRANSFER_SUCCESS = "Set call transfer success";
60 const std::string SET_CALL_TRANSFER_FAILED = "Set call transfer failed";
61 const std::string GET_CALL_RESTRICTION_SUCCESS = "Get call restriction success";
62 const std::string GET_CALL_RESTRICTION_FAILED = "Get call restriction failed";
63 const std::string SET_CALL_RESTRICTION_SUCCESS = "Set call restriction success";
64 const std::string SET_CALL_RESTRICTION_FAILED = "Set call restriction failed";
65 const std::string GET_CLIP_SUCCESS = "Get clip success";
66 const std::string GET_CLIP_FAILED = "Get clip failed";
67 const std::string SET_CLIP_SUCCESS = "Set clip success";
68 const std::string SET_CLIP_FAILED = "Set clip failed";
69 const std::string GET_CLIR_SUCCESS = "Get clir success";
70 const std::string GET_CLIR_FAILED = "Get clir failed";
71 const std::string SET_CLIR_SUCCESS = "Set clir success";
72 const std::string SET_CLIR_FAILED = "Set clir failed";
73 const std::string GET_COLR_SUCCESS = "Get colr success";
74 const std::string GET_COLR_FAILED = "Get colr failed";
75 const std::string SET_COLR_SUCCESS = "Set colr success";
76 const std::string SET_COLR_FAILED = "Set colr failed";
77 const std::string GET_COLP_SUCCESS = "Get colp success";
78 const std::string GET_COLP_FAILED = "Get colp failed";
79 const std::string SET_COLP_SUCCESS = "Set colp success";
80 const std::string SET_COLP_FAILED = "Set colp failed";
81 const std::string MIS_MATCH_PIN_PUK = "PIN or PUK don\'t match";
82 const std::string INVAILD_PIN_PUK = "Invaild PIN or PUK numbers";
83 const std::string SEND_USSD_SUCCESS = "Send ussd success";
84 
operator ""_hash(char const * p,size_t s)85 constexpr unsigned long long operator"" _hash(char const *p, size_t s)
86 {
87     return StandardizeUtils::HashCompileTime(p);
88 }
89 
GetClip(int32_t slotId,const MMIData & mmiData)90 void CellularCallSupplement::GetClip(int32_t slotId, const MMIData &mmiData)
91 {
92     const std::string interrogate = "*#";
93     if (!mmiData.actionString.empty() && mmiData.actionString == interrogate) {
94         supplementRequest_.GetClipRequest(slotId);
95     }
96 }
97 
GetClir(int32_t slotId,const MMIData & mmiData)98 void CellularCallSupplement::GetClir(int32_t slotId, const MMIData &mmiData)
99 {
100     const std::string interrogate = "*#";
101     const std::string activate = "*";
102     const std::string deactivate = "#";
103     if (mmiData.actionString.empty()) {
104         TELEPHONY_LOGE("GetClir return, actionString is empty!");
105         return;
106     }
107     if (mmiData.actionString == activate) {
108         supplementRequest_.SetClirRequest(slotId, ACTIVATE_ACTION);
109     } else if (mmiData.actionString == deactivate) {
110         supplementRequest_.SetClirRequest(slotId, DEACTIVATE_ACTION);
111     } else if (mmiData.actionString == interrogate) {
112         supplementRequest_.GetClirRequest(slotId);
113     }
114 }
115 
DealCallTransfer(int32_t slotId,const MMIData & mmiData)116 void CellularCallSupplement::DealCallTransfer(int32_t slotId, const MMIData &mmiData)
117 {
118     const std::string interrogate = "*#";
119     int32_t serviceCode = ObtainServiceCode(mmiData.serviceInfoB);
120     int32_t cause = ObtainCause(mmiData.serviceCode);
121     if (!mmiData.actionString.empty() && mmiData.actionString == interrogate) {
122         supplementRequest_.GetCallTransferRequest(slotId, cause);
123         return;
124     }
125     std::string phoneNumber = mmiData.serviceInfoA;
126     int32_t callForwardAction;
127     if (mmiData.actionString.empty()) {
128         TELEPHONY_LOGE("DealCallTransfer return, actionString is empty!");
129         return;
130     }
131 
132     // 3GPP TS 24.082 V4.0.0 (2001-03) 1 Call Forwarding Unconditional (CFU)
133     // 3GPP TS 24.082 V4.0.0 (2001-03) 2 Call Forwarding on mobile subscriber Busy (CFB)
134     // 3GPP TS 24.082 V4.0.0 (2001-03) 3 Call Forwarding on No Reply (CFNRy)
135     // 3GPP TS 24.082 V4.0.0 (2001-03) 4 Call Forwarding on mobile subscriber Not Reachable (CFNRc)
136     switch (StandardizeUtils::Hash_(mmiData.actionString.c_str())) {
137         case "*"_hash:
138             if (phoneNumber.empty()) {
139                 callForwardAction = (int32_t)CallTransferSettingType::CALL_TRANSFER_ENABLE;
140             } else {
141                 callForwardAction = (int32_t)CallTransferSettingType::CALL_TRANSFER_REGISTRATION;
142             }
143             break;
144         case "#"_hash:
145             callForwardAction = (int32_t)CallTransferSettingType::CALL_TRANSFER_DISABLE;
146             break;
147         case "**"_hash:
148             callForwardAction = (int32_t)CallTransferSettingType::CALL_TRANSFER_REGISTRATION;
149             break;
150         case "##"_hash:
151             callForwardAction = (int32_t)CallTransferSettingType::CALL_TRANSFER_ERASURE;
152             break;
153         default:
154             TELEPHONY_LOGE("DealCallTransfer return, actionString out of range, please check!");
155             return;
156     }
157     supplementRequest_.SetCallTransferRequest(slotId, callForwardAction, cause, phoneNumber, serviceCode);
158 }
159 
ObtainServiceCode(const std::string & serviceInfoB)160 int32_t CellularCallSupplement::ObtainServiceCode(const std::string &serviceInfoB)
161 {
162     if (serviceInfoB.empty()) {
163         TELEPHONY_LOGE("ObtainServiceCode return, serviceInfoB is empty!");
164         return NONE;
165     }
166     int32_t intServiceInfoB = atoi(serviceInfoB.c_str());
167     switch (intServiceInfoB) {
168         case ALL_TELE_SERVICES:
169             return SHORT_MESSAGE_SERVICE + FAX + VOICE;
170         case TELE_SERVICES:
171             return VOICE;
172         case ALL_DATA_TELE_SERVICES:
173             return SHORT_MESSAGE_SERVICE + FAX;
174         case FACSIMILE_SERVICES:
175             return FAX;
176         case SHORT_MESSAGE_SERVICES:
177             return SHORT_MESSAGE_SERVICE;
178         case ALL_TELE_SERVICES_EXCEPT_SMS:
179             return FAX + VOICE;
180         case ALL_BEARER_SERVICES:
181             return DATA_CIRCUIT_ASYNC + DATA_CIRCUIT_SYNC;
182         case ALL_ASYNC_SERVICES:
183             return DEDICATED_PAD_ACCESS + DATA_CIRCUIT_ASYNC;
184         case ALL_SYNC_SERVICES:
185             return DEDICATED_PACKET_ACCESS + DATA_CIRCUIT_SYNC;
186         case ALL_DATA_CIRCUIT_SYNC:
187             return DATA_CIRCUIT_SYNC;
188         case ALL_DATA_CIRCUIT_ASYNC:
189             return DATA_CIRCUIT_ASYNC;
190         case ALL_GPRS_BEARER_SERVICES:
191             return DEDICATED_PACKET_ACCESS;
192         default:
193             TELEPHONY_LOGE("ObtainServiceCode return, serviceInfoB out of range, please check!");
194             return NONE;
195     }
196 }
197 
ObtainCause(const std::string & actionStr)198 int32_t CellularCallSupplement::ObtainCause(const std::string &actionStr)
199 {
200     if (actionStr.empty()) {
201         TELEPHONY_LOGE("ObtainCause return, actionStr is empty!");
202         return TELEPHONY_ERROR;
203     }
204 
205     /*
206      * 3GPP TS 22.030 V4.0.0 (2001-03) Annex B (normative): Codes for defined Supplementary Services
207      * CFU	                21
208      * CF Busy	            67
209      * CF No Reply	        61
210      * CF Not Reachable 	62
211      * all CF		        002
212      * all conditional CF	004
213      */
214     switch (StandardizeUtils::Hash_(actionStr.c_str())) {
215         case "21"_hash:
216             return (int32_t)CallTransferType::TRANSFER_TYPE_UNCONDITIONAL;
217         case "67"_hash:
218             return (int32_t)CallTransferType::TRANSFER_TYPE_BUSY;
219         case "62"_hash:
220             return (int32_t)CallTransferType::TRANSFER_TYPE_NO_REPLY;
221         case "61"_hash:
222             return (int32_t)CallTransferType::TRANSFER_TYPE_NOT_REACHABLE;
223         default:
224             TELEPHONY_LOGE("ObtainCause return, actionStr out of range!");
225             return TELEPHONY_ERROR;
226     }
227 }
228 
DealCallRestriction(int32_t slotId,const MMIData & mmiData)229 void CellularCallSupplement::DealCallRestriction(int32_t slotId, const MMIData &mmiData)
230 {
231     std::string infoA = mmiData.serviceInfoA;
232     std::string facType = ObtainBarringInstallation(mmiData.serviceInfoC);
233     const std::string interrogate = "*#";
234     const std::string activate = "*";
235     const std::string deactivate = "#";
236     if (mmiData.actionString.empty()) {
237         TELEPHONY_LOGE("DealCallRestriction return, actionString is empty!");
238         return;
239     }
240     if (mmiData.actionString == interrogate) {
241         supplementRequest_.GetCallRestrictionRequest(slotId, facType);
242     } else if (mmiData.actionString == activate || mmiData.actionString == deactivate) {
243         supplementRequest_.SetCallRestrictionRequest(slotId, facType, mmiData.actionString == activate, infoA);
244     }
245 }
246 
ObtainBarringInstallation(const std::string & serviceInfoC)247 std::string CellularCallSupplement::ObtainBarringInstallation(const std::string &serviceInfoC)
248 {
249     if (serviceInfoC.empty()) {
250         TELEPHONY_LOGE("ObtainBarringInstallation return, serviceInfoC is empty!");
251         return std::string();
252     }
253 
254     /*
255      * 27007-430_2001 7.4	Facility lock +CLCK
256      *  Supplementary	Service Service	Code	SIA	SIB	SIC
257      * 	22.088
258      * 	BAOC	            33	                 PW	BS	-
259      * 	BAOIC	            331	                 PW	BS	-
260      * 	BAOIC exc home	    332	                 PW	BS	-
261      * 	BAIC	            35	                 PW	BS	-
262      * 	BAIC roaming	    351	                 PW	BS	-
263      *  all Barring Serv.   330	                 PW	BS	-
264      *  Outg. Barr. Serv.   333	                 PW	BS
265      *  Inc. Barr. Serv.	353	                 PW	BS
266      */
267     switch (StandardizeUtils::Hash_(serviceInfoC.c_str())) {
268         case "33"_hash:
269             // "AO"	BAOC (Barr All Outgoing Calls) (refer 3GPP TS 22.088 [6] clause 1)
270             return BARR_ALL_OUTGOING_CALLS;
271         case "331"_hash:
272             // "OI"	BOIC (Barr Outgoing International Calls) (refer 3GPP TS 22.088 [6] clause 1)
273             return BARR_OUTGOING_INTERNATIONAL_CALLS;
274         case "332"_hash:
275             // "OX"	BOIC exHC (Barr Outgoing International Calls except to Home Country)
276             // (refer 3GPP TS 22.088 [6] clause 1)
277             return BARR_OUTGOING_INTERNATIONAL_CALLS_EXCLUDING_HOME;
278         case "351"_hash:
279             // "IR"	BIC Roam (Barr Incoming Calls when Roaming outside the home country)
280             // (refer 3GPP TS 22.088 [6] clause 2)
281             return BARR_INCOMING_CALLS_OUTSIDE_HOME;
282         case "35"_hash:
283             // "AI"	BAIC (Barr All Incoming Calls) (refer 3GPP TS 22.088 [6] clause 2)
284             return BARR_ALL_INCOMING_CALLS;
285         case "330"_hash:
286             // "AB"	All Barring services (refer 3GPP TS 22.030 [19]) (applicable only for <mode>=0)
287             return ALL_BARRING_SERVICES;
288         case "333"_hash:
289             // "AG"	All outGoing barring services (refer 3GPP TS 22.030 [19]) (applicable only for <mode>=0)
290             return ALL_OUTGOING_BARRING_SERVICES;
291         case "353"_hash:
292             // "AC"	All inComing barring services (refer 3GPP TS 22.030 [19]) (applicable only for <mode>=0)
293             return ALL_INCOMING_BARRING_SERVICES;
294         default:
295             TELEPHONY_LOGE("ObtainBarringInstallation return, serviceInfoC out of range!");
296             return std::string();
297     }
298 }
299 
DealCallWaiting(int32_t slotId,const MMIData & mmiData)300 void CellularCallSupplement::DealCallWaiting(int32_t slotId, const MMIData &mmiData)
301 {
302     if (mmiData.actionString.empty()) {
303         TELEPHONY_LOGE("DealCallWaiting return, actionString is empty!");
304         return;
305     }
306     const std::string activate = "*";
307     const std::string deactivate = "#";
308     const std::string interrogate = "*#";
309     int32_t classType = ObtainServiceCode(mmiData.serviceInfoA);
310     if (mmiData.actionString == activate || mmiData.actionString == deactivate) {
311         supplementRequest_.SetCallWaitingRequest(slotId, mmiData.actionString == activate, classType);
312     } else if (mmiData.actionString == interrogate) {
313         supplementRequest_.GetCallWaitingRequest(slotId);
314     }
315 }
316 
EventGetCallWaiting(CallWaitResult & waitingInfo)317 void CellularCallSupplement::EventGetCallWaiting(CallWaitResult &waitingInfo)
318 {
319     CallWaitResponse callWaitResponse;
320     callWaitResponse.result = waitingInfo.result;
321 
322     /*
323      * <n> (sets/shows the result code presentation status in the TA):
324      * 0	disable
325      * 1	enable
326      */
327     callWaitResponse.status = waitingInfo.status;
328     callWaitResponse.classCw = waitingInfo.classCw;
329     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
330         TELEPHONY_LOGE("EventGetCallWaiting return, GetInstance is nullptr.");
331         return;
332     }
333     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportGetWaitingResult(callWaitResponse);
334 
335     ReportMmiCodeMessage(waitingInfo.result, GET_CALL_WAITING_SUCCESS, GET_CALL_WAITING_FAILED);
336 }
337 
EventSetCallWaiting(HRilRadioResponseInfo & responseInfo)338 void CellularCallSupplement::EventSetCallWaiting(HRilRadioResponseInfo &responseInfo)
339 {
340     CallWaitResponse callWaitResponse;
341     callWaitResponse.result = static_cast<int32_t>(responseInfo.error);
342     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
343         TELEPHONY_LOGE("EventSetCallWaiting return, GetInstance is nullptr.");
344         return;
345     }
346     int32_t result = static_cast<int32_t>(responseInfo.error);
347     if (result != TELEPHONY_SUCCESS) {
348         result = TELEPHONY_ERR_RIL_CMD_FAIL;
349     }
350     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportSetWaitingResult(result);
351 
352     ReportMmiCodeMessage(result, SET_CALL_WAITING_SUCCESS, SET_CALL_WAITING_FAILED);
353 }
354 
EventGetCallTransferInfo(CallForwardQueryInfoList & cFQueryList)355 void CellularCallSupplement::EventGetCallTransferInfo(CallForwardQueryInfoList &cFQueryList)
356 {
357     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
358         TELEPHONY_LOGE("EventGetCallTransferInfo return, GetInstance is nullptr.");
359         return;
360     }
361 
362     for (auto queryResult : cFQueryList.calls) {
363         TELEPHONY_LOGI("EventGetCallTransferInfo , data: status %{public}d, classx %{public}d, type %{public}d",
364             queryResult.status, queryResult.classx, queryResult.type);
365         BuildCallForwardQueryInfo(queryResult);
366     }
367 }
368 
BuildCallForwardQueryInfo(const CallForwardQueryResult & queryResult)369 void CellularCallSupplement::BuildCallForwardQueryInfo(const CallForwardQueryResult &queryResult)
370 {
371     // 3GPP TS 27.007 V3.9.0 (2001-06) 7.11	Call forwarding number and conditions +CCFC
372     CallTransferResponse response;
373     if (memset_s(&response, sizeof(response), 0, sizeof(response)) != EOK) {
374         TELEPHONY_LOGE("EventGetCallTransferInfo return, memset_s fail.");
375         return;
376     }
377 
378     // <number>: string type phone number of forwarding address in format specified by <type>
379     size_t cpyLen = strlen(queryResult.number.c_str()) + 1;
380     if (strcpy_s(response.number, cpyLen, queryResult.number.c_str()) != EOK) {
381         TELEPHONY_LOGE("EventGetCallTransferInfo return, strcpy_s fail.");
382         return;
383     }
384 
385     response.result = queryResult.result;
386 
387     /*
388      * <status>:0	not active;    1	  active
389      * */
390     response.status = queryResult.status;
391 
392     /*
393      * <classx> is a sum of integers each representing a class of information (default 7):
394      * 1	voice (telephony)
395      * 2	data (refers to all bearer services)
396      * 4	fax (facsimile services)
397      * 8	short message service
398      * 16	data circuit sync
399      * 32	data circuit async
400      * 64	dedicated packet access
401      * 128	dedicated PAD access
402      */
403     response.classx = queryResult.classx;
404     // <type>: type of address octet in integer format (refer GSM 04.08 [8] subclause 10.5.4.7);
405     // default 145 when dialling string includes international access code character "+", otherwise 129
406     response.type = queryResult.type;
407 
408     response.reason = queryResult.reason;
409     response.time = queryResult.time;
410 
411     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportGetTransferResult(response);
412 
413     ReportMmiCodeMessage(queryResult.result, GET_CALL_TRANSFER_SUCCESS, GET_CALL_TRANSFER_FAILED);
414 }
415 
EventSetCallTransferInfo(HRilRadioResponseInfo & responseInfo)416 void CellularCallSupplement::EventSetCallTransferInfo(HRilRadioResponseInfo &responseInfo)
417 {
418     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
419         TELEPHONY_LOGE("EventSetCallTransferInfo return, GetInstance is nullptr.");
420         return;
421     }
422     int32_t result = static_cast<int32_t>(responseInfo.error);
423     if (result != TELEPHONY_SUCCESS) {
424         result = TELEPHONY_ERR_RIL_CMD_FAIL;
425     }
426     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportSetTransferResult(result);
427 
428     ReportMmiCodeMessage(result, SET_CALL_TRANSFER_SUCCESS, SET_CALL_TRANSFER_FAILED);
429 }
430 
EventGetCallRestriction(const CallRestrictionResult & result)431 void CellularCallSupplement::EventGetCallRestriction(const CallRestrictionResult &result)
432 {
433     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
434         TELEPHONY_LOGE("EventGetCallRestriction return, GetInstance is nullptr.");
435         return;
436     }
437     CallRestrictionResponse response;
438     response.result = result.result;
439 
440     /*
441      * <status>:0	not active    1	  active
442      */
443     response.status = result.status;
444     response.classCw = result.classCw;
445 
446     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportGetRestrictionResult(response);
447 
448     ReportMmiCodeMessage(result.result, GET_CALL_RESTRICTION_SUCCESS, GET_CALL_RESTRICTION_FAILED);
449 }
450 
EventSetCallRestriction(HRilRadioResponseInfo & info)451 void CellularCallSupplement::EventSetCallRestriction(HRilRadioResponseInfo &info)
452 {
453     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
454         TELEPHONY_LOGE("EventSetCallRestriction return, GetInstance is nullptr.");
455         return;
456     }
457     int32_t result = static_cast<int32_t>(info.error);
458     if (result != TELEPHONY_SUCCESS) {
459         result = TELEPHONY_ERR_RIL_CMD_FAIL;
460     }
461     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportSetRestrictionResult(result);
462 
463     ReportMmiCodeMessage(result, SET_CALL_RESTRICTION_SUCCESS, SET_CALL_RESTRICTION_FAILED);
464 }
465 
SetCallTransferInfo(int32_t slotId,const CallTransferInfo & cfInfo)466 int32_t CellularCallSupplement::SetCallTransferInfo(int32_t slotId, const CallTransferInfo &cfInfo)
467 {
468     if (!PhoneTypeGsmOrNot(slotId)) {
469         TELEPHONY_LOGE("SetCallTransferInfo return, network type is not supported!");
470         return CALL_ERR_UNSUPPORTED_NETWORK_TYPE;
471     }
472     if (strlen(cfInfo.transferNum) == 0) {
473         TELEPHONY_LOGE("transferNum is empty!");
474         return TELEPHONY_ERR_ARGUMENT_INVALID;
475     }
476 
477     /*
478      * <reason>:
479      * 0   unconditional
480      * 1   mobile busy
481      * 2   no reply
482      * 3   not reachable
483      * 4   all call forwarding (refer 3GPP TS 22.030 [19])
484      * 5   all conditional call forwarding (refer 3GPP TS 22.030 [19])
485      * <mode>:
486      * 0   disable
487      * 1   enable
488      * 2   query status
489      * 3   registration
490      * 4   erasure
491      */
492     if (cfInfo.type > CallTransferType::TRANSFER_TYPE_NOT_REACHABLE ||
493         cfInfo.type < CallTransferType::TRANSFER_TYPE_UNCONDITIONAL ||
494         cfInfo.settingType > CallTransferSettingType::CALL_TRANSFER_ERASURE ||
495         cfInfo.settingType < CallTransferSettingType::CALL_TRANSFER_DISABLE) {
496         TELEPHONY_LOGE("SetCallTransferInfo return, parameter out of range!");
497         return CALL_ERR_PARAMETER_OUT_OF_RANGE;
498     }
499 
500     std::string dialString(cfInfo.transferNum);
501     return supplementRequest_.SetCallTransferRequest(
502         slotId, static_cast<int32_t>(cfInfo.settingType), static_cast<int32_t>(cfInfo.type), dialString, 1);
503 }
504 
GetCallTransferInfo(int32_t slotId,CallTransferType type)505 int32_t CellularCallSupplement::GetCallTransferInfo(int32_t slotId, CallTransferType type)
506 {
507     if (!PhoneTypeGsmOrNot(slotId)) {
508         TELEPHONY_LOGE("GetCallTransferInfo return, network type is not supported!");
509         return CALL_ERR_UNSUPPORTED_NETWORK_TYPE;
510     }
511 
512     /*
513      * When querying the status of a network service (<mode>=2) the response line for 'not active' case
514      * (<status>=0) should be returned only if service is not active for any <class>
515      */
516     return supplementRequest_.GetCallTransferRequest(slotId, (int32_t)type);
517 }
518 
PhoneTypeGsmOrNot(int32_t slotId)519 bool CellularCallSupplement::PhoneTypeGsmOrNot(int32_t slotId)
520 {
521     return moduleServiceUtils_.GetNetworkStatus(slotId) == PhoneType::PHONE_TYPE_IS_GSM;
522 }
523 
SetCallWaiting(int32_t slotId,bool activate)524 int32_t CellularCallSupplement::SetCallWaiting(int32_t slotId, bool activate)
525 {
526     /*
527      * <n> (sets/shows the result code presentation status in the TA):
528      * 0	disable
529      * 1	enable
530      */
531     if (!PhoneTypeGsmOrNot(slotId)) {
532         TELEPHONY_LOGE("SetCallWaiting return, network type is not supported!");
533         return CALL_ERR_UNSUPPORTED_NETWORK_TYPE;
534     }
535     int32_t classType = ServiceClassType::VOICE;
536     CellularCallConfig config;
537     classType = config.GetCallWaitingServiceClassConfig(slotId);
538     return supplementRequest_.SetCallWaitingRequest(slotId, activate, classType);
539 }
540 
GetCallWaiting(int32_t slotId)541 int32_t CellularCallSupplement::GetCallWaiting(int32_t slotId)
542 {
543     if (!PhoneTypeGsmOrNot(slotId)) {
544         TELEPHONY_LOGE("GetCallWaiting return, network type is not supported!");
545         return CALL_ERR_UNSUPPORTED_NETWORK_TYPE;
546     }
547     return supplementRequest_.GetCallWaitingRequest(slotId);
548 }
549 
SetCallRestriction(int32_t slotId,const CallRestrictionInfo & cRInfo)550 int32_t CellularCallSupplement::SetCallRestriction(int32_t slotId, const CallRestrictionInfo &cRInfo)
551 {
552     /*
553      * <fac> values reserved by the present document:
554      * "SC"	SIM (lock SIM/UICC card) (SIM/UICC asks password in ME power up and when this lock command issued)
555      * "AO"	BAOC (Barr All Outgoing Calls) (refer 3GPP TS 22.088 [6] clause 1)
556      * "OI"	BOIC (Barr Outgoing International Calls) (refer 3GPP TS 22.088 [6] clause 1)
557      * "OX"	BOIC exHC (Barr Outgoing International Calls except to Home Country) (refer 3GPP TS 22.088 [6] clause 1)
558      * "AI"	BAIC (Barr All Incoming Calls) (refer 3GPP TS 22.088 [6] clause 2)
559      * "IR"	BIC Roam (Barr Incoming Calls when Roaming outside the home country) (refer 3GPP TS 22.088 [6] clause 2)
560      * "AB"	All Barring services (refer 3GPP TS 22.030 [19]) (applicable only for <mode>=0)
561      * "AG"	All outGoing barring services (refer 3GPP TS 22.030 [19]) (applicable only for <mode>=0)
562      * "AC"	All inComing barring services (refer 3GPP TS 22.030 [19]) (applicable only for <mode>=0)
563      */
564     if (!PhoneTypeGsmOrNot(slotId)) {
565         TELEPHONY_LOGE("SetCallRestriction return, network type is not supported!");
566         return CALL_ERR_UNSUPPORTED_NETWORK_TYPE;
567     }
568 
569     std::string fac;
570     switch (cRInfo.fac) {
571         case CallRestrictionType::RESTRICTION_TYPE_ALL_OUTGOING:
572             fac = BARR_ALL_OUTGOING_CALLS;
573             break;
574         case CallRestrictionType::RESTRICTION_TYPE_INTERNATIONAL:
575             fac = BARR_OUTGOING_INTERNATIONAL_CALLS;
576             break;
577         case CallRestrictionType::RESTRICTION_TYPE_INTERNATIONAL_EXCLUDING_HOME:
578             fac = BARR_OUTGOING_INTERNATIONAL_CALLS_EXCLUDING_HOME;
579             break;
580         case CallRestrictionType::RESTRICTION_TYPE_ALL_INCOMING:
581             fac = BARR_ALL_INCOMING_CALLS;
582             break;
583         case CallRestrictionType::RESTRICTION_TYPE_ROAMING_INCOMING:
584             fac = BARR_INCOMING_CALLS_OUTSIDE_HOME;
585             break;
586         case CallRestrictionType::RESTRICTION_TYPE_ALL_CALLS:
587             fac = ALL_BARRING_SERVICES;
588             break;
589         case CallRestrictionType::RESTRICTION_TYPE_OUTGOING_SERVICES:
590             fac = ALL_OUTGOING_BARRING_SERVICES;
591             break;
592         case CallRestrictionType::RESTRICTION_TYPE_INCOMING_SERVICES:
593             fac = ALL_INCOMING_BARRING_SERVICES;
594             break;
595         default:
596             TELEPHONY_LOGE("SetCallRestriction return, fac parameter out of range!");
597             return CALL_ERR_PARAMETER_OUT_OF_RANGE;
598     }
599     if (cRInfo.mode < CallRestrictionMode::RESTRICTION_MODE_DEACTIVATION ||
600         cRInfo.mode > CallRestrictionMode::RESTRICTION_MODE_ACTIVATION) {
601         TELEPHONY_LOGE("SetCallRestriction return, mode parameter out of range!");
602         return CALL_ERR_PARAMETER_OUT_OF_RANGE;
603     }
604     std::string info(cRInfo.password);
605     return supplementRequest_.SetCallRestrictionRequest(slotId, fac, (int32_t)cRInfo.mode, info);
606 }
607 
GetCallRestriction(int32_t slotId,CallRestrictionType facType)608 int32_t CellularCallSupplement::GetCallRestriction(int32_t slotId, CallRestrictionType facType)
609 {
610     if (!PhoneTypeGsmOrNot(slotId)) {
611         TELEPHONY_LOGE("GetCallRestriction return, network type is not supported!");
612         return CALL_ERR_UNSUPPORTED_NETWORK_TYPE;
613     }
614     std::string fac;
615     switch (facType) {
616         case CallRestrictionType::RESTRICTION_TYPE_ALL_OUTGOING:
617             fac = BARR_ALL_OUTGOING_CALLS;
618             break;
619         case CallRestrictionType::RESTRICTION_TYPE_INTERNATIONAL:
620             fac = BARR_OUTGOING_INTERNATIONAL_CALLS;
621             break;
622         case CallRestrictionType::RESTRICTION_TYPE_INTERNATIONAL_EXCLUDING_HOME:
623             fac = BARR_OUTGOING_INTERNATIONAL_CALLS_EXCLUDING_HOME;
624             break;
625         case CallRestrictionType::RESTRICTION_TYPE_ALL_INCOMING:
626             fac = BARR_ALL_INCOMING_CALLS;
627             break;
628         case CallRestrictionType::RESTRICTION_TYPE_ROAMING_INCOMING:
629             fac = BARR_INCOMING_CALLS_OUTSIDE_HOME;
630             break;
631         case CallRestrictionType::RESTRICTION_TYPE_ALL_CALLS:
632             fac = ALL_BARRING_SERVICES;
633             break;
634         case CallRestrictionType::RESTRICTION_TYPE_OUTGOING_SERVICES:
635             fac = ALL_OUTGOING_BARRING_SERVICES;
636             break;
637         case CallRestrictionType::RESTRICTION_TYPE_INCOMING_SERVICES:
638             fac = ALL_INCOMING_BARRING_SERVICES;
639             break;
640         default:
641             TELEPHONY_LOGE("GetCallRestriction return, parameter out of range!");
642             return CALL_ERR_PARAMETER_OUT_OF_RANGE;
643     }
644     return supplementRequest_.GetCallRestrictionRequest(slotId, fac);
645 }
646 
EventGetClip(GetClipResult & getClipResult)647 void CellularCallSupplement::EventGetClip(GetClipResult &getClipResult)
648 {
649     ClipResponse clipResponse;
650     clipResponse.result = getClipResult.result;
651     clipResponse.action = getClipResult.action;
652     clipResponse.clipStat = getClipResult.clipStat;
653     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
654         TELEPHONY_LOGE("EventGetClip return, GetInstance is nullptr.");
655         return;
656     }
657     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportGetClipResult(clipResponse);
658 
659     ReportMmiCodeMessage(getClipResult.result, GET_CLIP_SUCCESS, GET_CLIP_FAILED);
660 }
661 
EventGetClir(GetClirResult & result)662 void CellularCallSupplement::EventGetClir(GetClirResult &result)
663 {
664     ClirResponse response;
665     // 3GPP TS 27.007 V3.9.0 (2001-06) 7.7	Calling line identification restriction +CLIR
666     response.result = result.result;
667     response.action = result.action;
668     response.clirStat = result.clirStat;
669     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
670         TELEPHONY_LOGE("EventGetClir return, GetInstance is nullptr.");
671         return;
672     }
673     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportGetClirResult(response);
674 
675     ReportMmiCodeMessage(result.result, GET_CLIR_SUCCESS, GET_CLIR_FAILED);
676 }
677 
EventSetClir(HRilRadioResponseInfo & info)678 void CellularCallSupplement::EventSetClir(HRilRadioResponseInfo &info)
679 {
680     TELEPHONY_LOGI("CellularCallSupplement::EventSetClir entry");
681     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
682         TELEPHONY_LOGE("EventSetClir return, GetInstance is nullptr.");
683         return;
684     }
685     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportSetClirResult(static_cast<int32_t>(info.error));
686 
687     ReportMmiCodeMessage(static_cast<int32_t>(info.error), SET_CLIR_SUCCESS, SET_CLIR_FAILED);
688 }
689 
SendUssd(int32_t slotId,const std::string & msg)690 int32_t CellularCallSupplement::SendUssd(int32_t slotId, const std::string &msg)
691 {
692     TELEPHONY_LOGI("CellularCallSupplement::SendUssd entry");
693     if (!PhoneTypeGsmOrNot(slotId)) {
694         TELEPHONY_LOGE("SendUssd return, network type is not supported!");
695         return CALL_ERR_UNSUPPORTED_NETWORK_TYPE;
696     }
697     return supplementRequest_.SendUssdRequest(slotId, msg);
698 }
699 
EventSendUssd(HRilRadioResponseInfo & responseInfo)700 void CellularCallSupplement::EventSendUssd(HRilRadioResponseInfo &responseInfo)
701 {
702     TELEPHONY_LOGI("CellularCallSupplement::EventSendUssd entry");
703     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
704         TELEPHONY_LOGE("EventSendUssd return, GetInstance is nullptr.");
705         return;
706     }
707     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportSendUssdResult(
708         static_cast<int32_t>(responseInfo.error));
709     ReportMmiCodeMessage(static_cast<int32_t>(responseInfo.error), SEND_USSD_SUCCESS, INVALID_MMI_CODE);
710 }
711 
EventSsNotify(SsNoticeInfo & ssNoticeInfo)712 void CellularCallSupplement::EventSsNotify(SsNoticeInfo &ssNoticeInfo)
713 {
714     TELEPHONY_LOGI("CellularCallSupplement::EventSsNotify entry");
715     MmiCodeInfo mmiCodeInfo;
716     mmiCodeInfo.result = ssNoticeInfo.result;
717     switch (ssNoticeInfo.requestType) {
718         case static_cast<int32_t>(SsRequestType::SS_ACTIVATION):
719         case static_cast<int32_t>(SsRequestType::SS_DEACTIVATION):
720         case static_cast<int32_t>(SsRequestType::SS_REGISTRATION):
721         case static_cast<int32_t>(SsRequestType::SS_ERASURE):
722         case static_cast<int32_t>(SsRequestType::SS_INTERROGATION):
723             GetMessage(mmiCodeInfo, ssNoticeInfo);
724             break;
725         default:
726             TELEPHONY_LOGE("Invaid requestType in SS Data!");
727             return;
728     }
729 
730     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
731         TELEPHONY_LOGE("EventSsNotify return, GetInstance is nullptr.");
732         return;
733     }
734     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportMmiCodeResult(mmiCodeInfo);
735 }
736 
GetMessage(MmiCodeInfo & mmiCodeInfo,const SsNoticeInfo & ssNoticeInfo)737 void CellularCallSupplement::GetMessage(MmiCodeInfo &mmiCodeInfo, const SsNoticeInfo &ssNoticeInfo)
738 {
739     if (ssNoticeInfo.result != 0) {
740         size_t cpyLen = strlen(QUERY_SS_FAILED.c_str()) + 1;
741         if (strcpy_s(mmiCodeInfo.message, cpyLen, QUERY_SS_FAILED.c_str()) != EOK) {
742             TELEPHONY_LOGE("ReportGetClirResult return, strcpy_s QUERY_SS_FAILED fail.");
743         }
744         return;
745     }
746     switch (ssNoticeInfo.serviceType) {
747         case (unsigned int)CallTransferType::TRANSFER_TYPE_UNCONDITIONAL: {
748             size_t cpyLen = strlen(TRANSFER_UNCONDITIONAL_SUCCESS.c_str()) + 1;
749             if (strcpy_s(mmiCodeInfo.message, cpyLen, TRANSFER_UNCONDITIONAL_SUCCESS.c_str()) != EOK) {
750                 TELEPHONY_LOGE("ReportGetClirResult return, strcpy_s TRANSFER_UNCONDITIONAL_SUCCESS fail.");
751                 return;
752             }
753             break;
754         }
755         case (unsigned int)CallTransferType::TRANSFER_TYPE_BUSY: {
756             size_t cpyLen = strlen(TRANSFER_BUSY_SUCCESS.c_str()) + 1;
757             if (strcpy_s(mmiCodeInfo.message, cpyLen, TRANSFER_BUSY_SUCCESS.c_str()) != EOK) {
758                 TELEPHONY_LOGE("ReportGetClirResult return, strcpy_s TRANSFER_BUSY_SUCCESS fail.");
759                 return;
760             }
761             break;
762         }
763         case (unsigned int)CallTransferType::TRANSFER_TYPE_NO_REPLY: {
764             size_t cpyLen = strlen(TRANSFER_NO_REPLYL_SUCCESS.c_str()) + 1;
765             if (strcpy_s(mmiCodeInfo.message, cpyLen, TRANSFER_NO_REPLYL_SUCCESS.c_str()) != EOK) {
766                 TELEPHONY_LOGE("ReportGetClirResult return, strcpy_s TRANSFER_NO_REPLYL_SUCCESS fail.");
767                 return;
768             }
769             break;
770         }
771         case (unsigned int)CallTransferType::TRANSFER_TYPE_NOT_REACHABLE: {
772             size_t cpyLen = strlen(TRANSFER_NOT_REACHABLE_SUCCESS.c_str()) + 1;
773             if (strcpy_s(mmiCodeInfo.message, cpyLen, TRANSFER_NOT_REACHABLE_SUCCESS.c_str()) != EOK) {
774                 TELEPHONY_LOGE("ReportGetClirResult return, strcpy_s TRANSFER_NOT_REACHABLE_SUCCESS fail.");
775                 return;
776             }
777             break;
778         }
779         default: {
780             size_t cpyLen = strlen(QUERY_SS_SUCCESS.c_str()) + 1;
781             if (strcpy_s(mmiCodeInfo.message, cpyLen, QUERY_SS_SUCCESS.c_str()) != EOK) {
782                 TELEPHONY_LOGE("ReportGetClirResult return, strcpy_s QUERY_SS_SUCCESS fail.");
783                 return;
784             }
785         }
786     }
787 }
788 
EventUssdNotify(UssdNoticeInfo & ussdNoticeInfo)789 void CellularCallSupplement::EventUssdNotify(UssdNoticeInfo &ussdNoticeInfo)
790 {
791     TELEPHONY_LOGI("CellularCallSupplement::EventUssdNotify entry");
792     MmiCodeInfo mmiCodeInfo;
793     bool isUssdError = ussdNoticeInfo.m != USSD_MODE_NOTIFY && ussdNoticeInfo.m != USSD_MODE_REQUEST;
794     if (!isUssdError && !ussdNoticeInfo.str.empty()) {
795         mmiCodeInfo.result = USSD_SUCCESS;
796         size_t cpyLen = strlen(ussdNoticeInfo.str.c_str()) + 1;
797         if (strcpy_s(mmiCodeInfo.message, cpyLen, ussdNoticeInfo.str.c_str()) != EOK) {
798             TELEPHONY_LOGE("EventUssdNotify return, strcpy_s ussdNoticeInfo.str fail.");
799             return;
800         }
801     } else if (isUssdError && !(ussdNoticeInfo.m == USSD_MODE_NW_RELEASE)) {
802         mmiCodeInfo.result = USSD_FAILED;
803         size_t cpyLen = strlen(INVALID_MMI_CODE.c_str()) + 1;
804         if (strcpy_s(mmiCodeInfo.message, cpyLen, INVALID_MMI_CODE.c_str()) != EOK) {
805             TELEPHONY_LOGE("EventUssdNotify return, strcpy_s INVALID_MMI_CODE fail.");
806             return;
807         }
808     } else {
809         TELEPHONY_LOGE("Invaild ussd notify.");
810     }
811 
812     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
813         TELEPHONY_LOGE("EventUssdNotify return, GetInstance is nullptr.");
814         return;
815     }
816     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportMmiCodeResult(mmiCodeInfo);
817 }
818 
EventSetPinPuk(const PinPukResponse & pinPukResponse)819 void CellularCallSupplement::EventSetPinPuk(const PinPukResponse &pinPukResponse)
820 {
821     TELEPHONY_LOGI("CellularCallSupplement::EventSetPinPuk entry");
822     MmiCodeInfo mmiCodeInfo;
823     mmiCodeInfo.result = pinPukResponse.result;
824     std::string messageTemp = std::to_string(pinPukResponse.remain);
825     size_t cpyLen = strlen(messageTemp.c_str()) + 1;
826     if (strcpy_s(mmiCodeInfo.message, cpyLen, messageTemp.c_str()) != EOK) {
827         TELEPHONY_LOGE("EventUssdNotify return, strcpy_s messageTemp fail.");
828     }
829     if (DelayedSingleton<CellularCallRegister>::GetInstance() == nullptr) {
830         TELEPHONY_LOGE("EventSetPinPuk return, GetInstance is nullptr.");
831         return;
832     }
833     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportMmiCodeResult(mmiCodeInfo);
834 }
835 
AlterPinPassword(int32_t slotId,const MMIData & mmiData)836 void CellularCallSupplement::AlterPinPassword(int32_t slotId, const MMIData &mmiData)
837 {
838     TELEPHONY_LOGI("CellularCallSupplement::AlterPinPassword entry");
839     auto serviceInstance_ = DelayedSingleton<CellularCallService>::GetInstance();
840     if (serviceInstance_ == nullptr) {
841         TELEPHONY_LOGE("CellularCallSupplement::AlterPinPassword return, GetInstance is nullptr");
842         return;
843     }
844 
845     if (mmiData.actionString.empty()) {
846         TELEPHONY_LOGE("AlterPinPassword return, actionString is empty!");
847         return;
848     }
849 
850     std::string oldPin = mmiData.serviceInfoA;
851     std::string newPin = mmiData.serviceInfoB;
852     std::string newPinCheck = mmiData.serviceInfoC;
853     if (!IsVaildPinOrPuk(newPin, newPinCheck)) {
854         return;
855     }
856     supplementRequest_.AlterPinPassword(slotId, newPin, oldPin);
857 }
858 
UnlockPuk(int32_t slotId,const MMIData & mmiData)859 void CellularCallSupplement::UnlockPuk(int32_t slotId, const MMIData &mmiData)
860 {
861     TELEPHONY_LOGI("CellularCallSupplement::UnlockPuk entry");
862     auto serviceInstance_ = DelayedSingleton<CellularCallService>::GetInstance();
863     if (serviceInstance_ == nullptr) {
864         TELEPHONY_LOGE("CellularCallSupplement::UnlockPuk return, GetInstance is nullptr");
865         return;
866     }
867 
868     if (mmiData.actionString.empty()) {
869         TELEPHONY_LOGE("UnlockPuk return, actionString is empty!");
870         return;
871     }
872     std::string puk = mmiData.serviceInfoA;
873     std::string newPin = mmiData.serviceInfoB;
874     std::string newPinCheck = mmiData.serviceInfoC;
875     if (!IsVaildPinOrPuk(newPin, newPinCheck)) {
876         return;
877     }
878     supplementRequest_.UnlockPuk(slotId, newPin, puk);
879 }
880 
AlterPin2Password(int32_t slotId,const MMIData & mmiData)881 void CellularCallSupplement::AlterPin2Password(int32_t slotId, const MMIData &mmiData)
882 {
883     TELEPHONY_LOGI("CellularCallSupplement::AlterPin2Password entry");
884     auto serviceInstance_ = DelayedSingleton<CellularCallService>::GetInstance();
885     if (serviceInstance_ == nullptr) {
886         TELEPHONY_LOGE("CellularCallSupplement::AlterPin2Password return, GetInstance is nullptr");
887         return;
888     }
889 
890     if (mmiData.actionString.empty()) {
891         TELEPHONY_LOGE("AlterPin2Password return, actionString is empty!");
892         return;
893     }
894 
895     std::string oldPin2 = mmiData.serviceInfoA;
896     std::string newPin2 = mmiData.serviceInfoB;
897     std::string newPin2Check = mmiData.serviceInfoC;
898     if (!IsVaildPinOrPuk(newPin2, newPin2Check)) {
899         return;
900     }
901     supplementRequest_.AlterPin2Password(slotId, newPin2, oldPin2);
902 }
903 
UnlockPuk2(int32_t slotId,const MMIData & mmiData)904 void CellularCallSupplement::UnlockPuk2(int32_t slotId, const MMIData &mmiData)
905 {
906     TELEPHONY_LOGI("CellularCallSupplement::UnlockPuk2 entry");
907     auto serviceInstance_ = DelayedSingleton<CellularCallService>::GetInstance();
908     if (serviceInstance_ == nullptr) {
909         TELEPHONY_LOGE("CellularCallSupplement::UnlockPuk2 return, GetInstance is nullptr");
910         return;
911     }
912 
913     if (mmiData.actionString.empty()) {
914         TELEPHONY_LOGE("UnlockPuk2 return, actionString is empty!");
915         return;
916     }
917 
918     std::string puk2 = mmiData.serviceInfoA;
919     std::string newPin2 = mmiData.serviceInfoB;
920     std::string newPin2Check = mmiData.serviceInfoC;
921     if (!IsVaildPinOrPuk(newPin2, newPin2Check)) {
922         return;
923     }
924     supplementRequest_.UnlockPuk2(slotId, newPin2, puk2);
925 }
926 
IsVaildPinOrPuk(std::string newPinOrPuk,std::string newPinOrPukCheck)927 bool CellularCallSupplement::IsVaildPinOrPuk(std::string newPinOrPuk, std::string newPinOrPukCheck)
928 {
929     if (newPinOrPuk != newPinOrPukCheck) {
930         ReportMmiCodeMessage(MMI_CODE_FAILED, "", MIS_MATCH_PIN_PUK);
931         return false;
932     } else if (static_cast<int32_t>(newPinOrPuk.length()) < PIN_PUK_MIN ||
933                static_cast<int32_t>(newPinOrPuk.length()) > PIN_PUK_MAX) {
934         ReportMmiCodeMessage(MMI_CODE_FAILED, "", INVAILD_PIN_PUK);
935         return false;
936     } else {
937         TELEPHONY_LOGI("Check Pin or Puk success.");
938     }
939     return true;
940 }
941 
ReportMmiCodeMessage(int32_t result,const std::string successMsg,const std::string failedMsg)942 void CellularCallSupplement::ReportMmiCodeMessage(
943     int32_t result, const std::string successMsg, const std::string failedMsg)
944 {
945     MmiCodeInfo mmiCodeInfo;
946     mmiCodeInfo.result = result;
947     if (result == RESULT_SUCCESS) {
948         size_t cpyLen = strlen(successMsg.c_str()) + 1;
949         if (strcpy_s(mmiCodeInfo.message, cpyLen, successMsg.c_str()) != EOK) {
950             TELEPHONY_LOGE("ReportSetRestrictionResult return, strcpy_s fail.");
951             return;
952         }
953     } else {
954         size_t cpyLen = strlen(failedMsg.c_str()) + 1;
955         if (strcpy_s(mmiCodeInfo.message, cpyLen, failedMsg.c_str()) != EOK) {
956             TELEPHONY_LOGE("ReportSetRestrictionResult return, strcpy_s fail.");
957             return;
958         }
959     }
960     DelayedSingleton<CellularCallRegister>::GetInstance()->ReportMmiCodeResult(mmiCodeInfo);
961 }
962 } // namespace Telephony
963 } // namespace OHOS
964