1 /*
2 * Copyright (C) 2021 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 "sim_sms_controller.h"
17
18 #include "core_service_errors.h"
19
20 namespace OHOS {
21 namespace Telephony {
22 std::mutex SimSmsController::mtx_;
23 constexpr static const int32_t WAIT_TIME_SECOND = 1;
24 constexpr static const int32_t WAIT_TIME_TEN_SECOND = 10;
25
SimSmsController(std::shared_ptr<SimStateManager> simStateManager)26 SimSmsController::SimSmsController(std::shared_ptr<SimStateManager> simStateManager)
27 : TelEventHandler("SimSmsController"), stateManager_(simStateManager)
28 {}
29
ProcessEvent(const AppExecFwk::InnerEvent::Pointer & event)30 void SimSmsController::ProcessEvent(const AppExecFwk::InnerEvent::Pointer &event)
31 {
32 if (event == nullptr) {
33 TELEPHONY_LOGE("SimSmsController ProcessEvent event is nullptr");
34 return;
35 }
36 uint32_t id = event->GetInnerEventId();
37 TELEPHONY_LOGD("SimSmsController ProcessEvent Id is %{public}d", id);
38 switch (id) {
39 case SIM_SMS_GET_COMPLETED:
40 ProcessLoadDone(event);
41 break;
42 case SIM_SMS_UPDATE_COMPLETED:
43 TELEPHONY_LOGI("ProcessEvent update");
44 ProcessUpdateDone(event);
45 break;
46 case SIM_SMS_WRITE_COMPLETED:
47 TELEPHONY_LOGI("ProcessEvent write");
48 ProcessWriteDone(event);
49 break;
50 case SIM_SMS_DELETE_COMPLETED:
51 ProcessDeleteDone(event);
52 break;
53 default:
54 break;
55 }
56 }
57
ProcessLoadDone(const AppExecFwk::InnerEvent::Pointer & event)58 void SimSmsController::ProcessLoadDone(const AppExecFwk::InnerEvent::Pointer &event)
59 {
60 TELEPHONY_LOGI("SimSmsController::ProcessLoadDone: start");
61 if (event == nullptr) {
62 TELEPHONY_LOGE("SimSmsController ProcessLoadDone event is nullptr");
63 return;
64 }
65 std::unique_ptr<ControllerToFileMsg> fd = event->GetUniqueObject<ControllerToFileMsg>();
66 if (fd != nullptr) {
67 if (fd->exception != nullptr) {
68 TELEPHONY_LOGE("ProcessLoadDone: get error result");
69 std::vector<std::string> nullVector;
70 smsList_.swap(nullVector);
71 }
72 } else {
73 std::shared_ptr<MultiRecordResult> object = event->GetSharedObject<MultiRecordResult>();
74 if (object != nullptr) {
75 TELEPHONY_LOGI("SimSmsController::ProcessLoadDone: %{public}d", object->resultLength);
76 if (object->exception == nullptr) {
77 smsList_.assign(object->fileResults.begin(), object->fileResults.end());
78 }
79 } else {
80 TELEPHONY_LOGE("ProcessLoadDone: get null pointer!!!");
81 }
82 }
83 loadDone_ = true;
84 processWait_.notify_all();
85 }
86
ProcessUpdateDone(const AppExecFwk::InnerEvent::Pointer & event)87 void SimSmsController::ProcessUpdateDone(const AppExecFwk::InnerEvent::Pointer &event)
88 {
89 if (event == nullptr) {
90 TELEPHONY_LOGE("SimSmsController ProcessUpdateDone event is nullptr");
91 return;
92 }
93 responseReady_ = true;
94 std::shared_ptr<RadioResponseInfo> responseInfo = event->GetSharedObject<RadioResponseInfo>();
95 if (responseInfo != nullptr) {
96 TELEPHONY_LOGE("SimSmsController::ProcessUpdateDone error %{public}d", responseInfo->error);
97 responseReady_ = (responseInfo->error == ErrType::NONE);
98 }
99 TELEPHONY_LOGI("SimSmsController::ProcessUpdateDone: end");
100 processWait_.notify_all();
101 }
102
ProcessWriteDone(const AppExecFwk::InnerEvent::Pointer & event)103 void SimSmsController::ProcessWriteDone(const AppExecFwk::InnerEvent::Pointer &event)
104 {
105 if (event == nullptr) {
106 TELEPHONY_LOGE("SimSmsController ProcessWriteDone event is nullptr");
107 return;
108 }
109 responseReady_ = true;
110 std::shared_ptr<RadioResponseInfo> responseInfo = event->GetSharedObject<RadioResponseInfo>();
111 if (responseInfo != nullptr) {
112 TELEPHONY_LOGE("SimSmsController::ProcessWriteDone error %{public}d", responseInfo->error);
113 responseReady_ = (responseInfo->error == ErrType::NONE);
114 }
115 TELEPHONY_LOGI("SimSmsController::ProcessWriteDone: end");
116 processWait_.notify_all();
117 }
118
ProcessDeleteDone(const AppExecFwk::InnerEvent::Pointer & event)119 void SimSmsController::ProcessDeleteDone(const AppExecFwk::InnerEvent::Pointer &event)
120 {
121 if (event == nullptr) {
122 TELEPHONY_LOGE("SimSmsController ProcessDeleteDone event is nullptr");
123 return;
124 }
125 responseReady_ = true;
126 std::shared_ptr<RadioResponseInfo> responseInfo = event->GetSharedObject<RadioResponseInfo>();
127 if (responseInfo != nullptr) {
128 TELEPHONY_LOGE("SimSmsController::ProcessDeleteDone error %{public}d", responseInfo->error);
129 responseReady_ = (responseInfo->error == ErrType::NONE);
130 }
131 TELEPHONY_LOGI("SimSmsController::ProcessDeleteDone: end");
132 processWait_.notify_all();
133 }
134
UpdateSmsIcc(int index,int status,std::string & pduData,std::string & smsc)135 int32_t SimSmsController::UpdateSmsIcc(int index, int status, std::string &pduData, std::string &smsc)
136 {
137 std::unique_lock<std::mutex> lock(mtx_);
138 bool isCDMA = IsCdmaCardType();
139 TELEPHONY_LOGI("UpdateSmsIcc start: %{public}d, %{public}d", index, isCDMA);
140 responseReady_ = false;
141 if (!isCDMA) {
142 AppExecFwk::InnerEvent::Pointer response = BuildCallerInfo(SIM_SMS_UPDATE_COMPLETED);
143 SimMessageParam param { index, status, smsc, pduData };
144 telRilManager_->UpdateSimMessage(slotId_, param, response);
145 } else {
146 AppExecFwk::InnerEvent::Pointer response = BuildCallerInfo(SIM_SMS_UPDATE_COMPLETED);
147 CdmaSimMessageParam param { index, status, pduData };
148 telRilManager_->UpdateCdmaSimMessage(slotId_, param, response);
149 }
150 while (!responseReady_) {
151 TELEPHONY_LOGI("UpdateSmsIcc::wait(), response = false");
152 if (processWait_.wait_for(lock, std::chrono::seconds(WAIT_TIME_SECOND)) == std::cv_status::timeout) {
153 break;
154 }
155 }
156 TELEPHONY_LOGI("SimSmsController::UpdateSmsIcc OK return %{public}d", responseReady_);
157 if (responseReady_) {
158 return TELEPHONY_ERR_SUCCESS;
159 } else {
160 return CORE_ERR_SIM_CARD_UPDATE_FAILED;
161 }
162 }
163
DelSmsIcc(int index)164 int32_t SimSmsController::DelSmsIcc(int index)
165 {
166 std::unique_lock<std::mutex> lock(mtx_);
167 bool isCDMA = IsCdmaCardType();
168 TELEPHONY_LOGI("DelSmsIcc start: %{public}d, %{public}d", index, isCDMA);
169 responseReady_ = false;
170 if (!isCDMA) {
171 AppExecFwk::InnerEvent::Pointer response = BuildCallerInfo(SIM_SMS_DELETE_COMPLETED);
172 telRilManager_->DelSimMessage(slotId_, index, response);
173 TELEPHONY_LOGI("SimSmsController::DelSmsIcc OK return %{public}d", responseReady_);
174 } else {
175 AppExecFwk::InnerEvent::Pointer response = BuildCallerInfo(SIM_SMS_DELETE_COMPLETED);
176 telRilManager_->DelCdmaSimMessage(slotId_, index, response);
177 TELEPHONY_LOGI("SimSmsController::DelCdmaSimMessage OK return %{public}d", responseReady_);
178 }
179 while (!responseReady_) {
180 TELEPHONY_LOGI("DelSmsIcc::wait(), response = false");
181 if (processWait_.wait_for(lock, std::chrono::seconds(WAIT_TIME_SECOND)) == std::cv_status::timeout) {
182 break;
183 }
184 }
185 if (responseReady_) {
186 return TELEPHONY_ERR_SUCCESS;
187 } else {
188 return CORE_ERR_SIM_CARD_UPDATE_FAILED;
189 }
190 }
191
AddSmsToIcc(int status,std::string & pdu,std::string & smsc)192 int32_t SimSmsController::AddSmsToIcc(int status, std::string &pdu, std::string &smsc)
193 {
194 std::unique_lock<std::mutex> lock(mtx_);
195 bool isCDMA = IsCdmaCardType();
196 TELEPHONY_LOGI("AddSmsToIcc start: %{public}d, %{public}d", status, isCDMA);
197 responseReady_ = false;
198 if (!isCDMA) {
199 AppExecFwk::InnerEvent::Pointer response = BuildCallerInfo(SIM_SMS_WRITE_COMPLETED);
200 SimMessageParam param { 0, status, smsc, pdu };
201 telRilManager_->AddSimMessage(slotId_, param, response);
202 } else {
203 AppExecFwk::InnerEvent::Pointer response = BuildCallerInfo(SIM_SMS_WRITE_COMPLETED);
204 telRilManager_->AddCdmaSimMessage(slotId_, status, pdu, response);
205 }
206 while (!responseReady_) {
207 TELEPHONY_LOGI("AddSmsToIcc::wait(), response = false");
208 if (processWait_.wait_for(lock, std::chrono::seconds(WAIT_TIME_SECOND)) == std::cv_status::timeout) {
209 break;
210 }
211 }
212 TELEPHONY_LOGI("SimSmsController::AddSmsToIcc OK return %{public}d", responseReady_);
213 if (responseReady_) {
214 return TELEPHONY_ERR_SUCCESS;
215 } else {
216 return CORE_ERR_SIM_CARD_UPDATE_FAILED;
217 }
218 }
219
Init(int slodId)220 void SimSmsController::Init(int slodId)
221 {
222 slotId_ = slodId;
223 }
224
ObtainAllSmsOfIcc()225 std::vector<std::string> SimSmsController::ObtainAllSmsOfIcc()
226 {
227 std::unique_lock<std::mutex> lock(mtx_);
228 std::shared_ptr<IccFileController> fileController = fileManager_->GetIccFileController();
229 loadDone_ = false;
230 if (fileController == nullptr) {
231 TELEPHONY_LOGE("Cannot load Sms records. No icc card?");
232 std::vector<std::string> nullVector;
233 smsList_.swap(nullVector);
234 return smsList_;
235 }
236 TELEPHONY_LOGI("ObtainAllSmsOfIcc start!!");
237 AppExecFwk::InnerEvent::Pointer event = BuildCallerInfo(SIM_SMS_GET_COMPLETED);
238 fileController->ObtainAllLinearFixedFile(ELEMENTARY_FILE_SMS, event);
239 while (!loadDone_) {
240 TELEPHONY_LOGI("ObtainAllSmsOfIcc::wait(), response = false");
241 if (processWait_.wait_for(lock, std::chrono::seconds(WAIT_TIME_TEN_SECOND)) == std::cv_status::timeout) {
242 break;
243 }
244 }
245 TELEPHONY_LOGI("SimSmsController::ObtainAllSmsOfIcc: end");
246 return smsList_;
247 }
248
SetRilAndFileManager(std::shared_ptr<Telephony::ITelRilManager> ril,std::shared_ptr<SimFileManager> fileMgr)249 void SimSmsController::SetRilAndFileManager(
250 std::shared_ptr<Telephony::ITelRilManager> ril, std::shared_ptr<SimFileManager> fileMgr)
251 {
252 telRilManager_ = ril;
253 if (telRilManager_ == nullptr) {
254 TELEPHONY_LOGE("SimSmsController rilmanager get null pointer");
255 }
256 fileManager_ = fileMgr;
257 if (fileManager_ == nullptr) {
258 TELEPHONY_LOGE("SimSmsController fileManager get null pointer");
259 }
260 }
261
BuildCallerInfo(int eventId)262 AppExecFwk::InnerEvent::Pointer SimSmsController::BuildCallerInfo(int eventId)
263 {
264 std::unique_ptr<FileToControllerMsg> object = std::make_unique<FileToControllerMsg>();
265 int eventParam = 0;
266 AppExecFwk::InnerEvent::Pointer event = AppExecFwk::InnerEvent::Get(eventId, object, eventParam);
267 if (event == nullptr) {
268 TELEPHONY_LOGE("event is nullptr!");
269 return AppExecFwk::InnerEvent::Pointer(nullptr, nullptr);
270 }
271 event->SetOwner(shared_from_this());
272 return event;
273 }
274
IsCdmaCardType() const275 bool SimSmsController::IsCdmaCardType() const
276 {
277 bool isCdmaType = false;
278 if (stateManager_ != nullptr) {
279 CardType type = stateManager_->GetCardType();
280 TELEPHONY_LOGI("IsCdmaCardType card type id %{public}d", type);
281 if (type == CardType::SINGLE_MODE_RUIM_CARD) {
282 isCdmaType = true; // cdma
283 }
284 }
285 TELEPHONY_LOGI("IsCdmaCardType result %{public}d", isCdmaType);
286 return isCdmaType;
287 }
288
~SimSmsController()289 SimSmsController::~SimSmsController() {}
290 } // namespace Telephony
291 } // namespace OHOS
292