• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2025 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 "want_params.h"
17 #ifndef WANT_PARAM_USE_LONG
18 #define WANT_PARAM_USE_LONG
19 #endif
20 
21 #include "ability_base_log_wrapper.h"
22 #include "array_wrapper.h"
23 #include "base_interfaces.h"
24 #include "base_obj.h"
25 #include "bool_wrapper.h"
26 #include "byte_wrapper.h"
27 #include "double_wrapper.h"
28 #include "float_wrapper.h"
29 #include "int_wrapper.h"
30 #include "long_wrapper.h"
31 #include "parcel.h"
32 #include "remote_object_wrapper.h"
33 #include "securec.h"
34 #include "short_wrapper.h"
35 #include "string_ex.h"
36 #include "string_wrapper.h"
37 #include "want_params_wrapper.h"
38 #include "zchar_wrapper.h"
39 
40 namespace OHOS {
41 namespace AAFwk {
42 namespace {
HandleArrayObjectFromJson(const std::vector<nlohmann::json> & arrayObject)43 sptr<IArray> HandleArrayObjectFromJson(const std::vector<nlohmann::json> &arrayObject)
44 {
45     size_t size = arrayObject.size();
46     sptr<IArray> ao = new (std::nothrow) Array(size, g_IID_IWantParams);
47     if (ao != nullptr) {
48         for (size_t i = 0; i < size; i++) {
49             auto wp = arrayObject[i].get<WantParams>();
50             sptr<IWantParams> pWantParams = WantParamWrapper::Box(wp);
51             ao->Set(i, WantParamWrapper::Box(wp));
52         }
53         return ao;
54     } else {
55         return nullptr;
56     }
57 }
58 
HandleArrayStringFromJson(const std::vector<std::string> & arrayString)59 sptr<IArray> HandleArrayStringFromJson(const std::vector<std::string> &arrayString)
60 {
61     size_t size = arrayString.size();
62     sptr<IArray> ao = new (std::nothrow) Array(size, g_IID_IString);
63     if (ao != nullptr) {
64         for (size_t i = 0; i < size; i++) {
65             ao->Set(i, String::Box(arrayString[i]));
66         }
67         return ao;
68     } else {
69         return nullptr;
70     }
71 }
72 
HandleArrayInt32FromJson(const std::vector<int32_t> & arrayInt32)73 sptr<IArray> HandleArrayInt32FromJson(const std::vector<int32_t> &arrayInt32)
74 {
75     size_t size = arrayInt32.size();
76     sptr<IArray> ao = new (std::nothrow) Array(size, g_IID_IInteger);
77     if (ao != nullptr) {
78         for (size_t i = 0; i < size; i++) {
79             ao->Set(i, Integer::Box(arrayInt32[i]));
80         }
81         return ao;
82     } else {
83         return nullptr;
84     }
85 }
86 
HandleArrayBoolFromJson(const std::vector<bool> & arrayBool)87 sptr<IArray> HandleArrayBoolFromJson(const std::vector<bool> &arrayBool)
88 {
89     size_t size = arrayBool.size();
90     sptr<IArray> ao = new (std::nothrow) Array(size, g_IID_IBoolean);
91     if (ao != nullptr) {
92         for (size_t i = 0; i < size; i++) {
93             ao->Set(i, Boolean::Box(arrayBool[i]));
94         }
95         return ao;
96     } else {
97         return nullptr;
98     }
99 }
100 
HandleArrayDoubleFromJson(const std::vector<double> & arrayDouble)101 sptr<IArray> HandleArrayDoubleFromJson(const std::vector<double> &arrayDouble)
102 {
103     size_t size = arrayDouble.size();
104     sptr<IArray> ao = new (std::nothrow) Array(size, g_IID_IDouble);
105     if (ao != nullptr) {
106         for (size_t i = 0; i < size; i++) {
107             ao->Set(i, Double::Box(arrayDouble[i]));
108         }
109         return ao;
110     } else {
111         return nullptr;
112     }
113 }
114 
HandleArrayNumberFromJson(const nlohmann::json & jsonObject,std::vector<int32_t> & arrayInt32,std::vector<double> & arrayDouble)115 void HandleArrayNumberFromJson(
116     const nlohmann::json &jsonObject, std::vector<int32_t> &arrayInt32, std::vector<double> &arrayDouble)
117 {
118     int32_t natValue32 = 0;
119     int64_t natValue64 = 0;
120     double natValueDouble = 0.0;
121 
122     if (jsonObject.is_number_float()) {
123         natValueDouble = jsonObject.get<double>();
124         arrayDouble.push_back(natValueDouble);
125     }
126 
127     if (!jsonObject.is_number_integer()) {
128         return;
129     }
130     natValue32 = jsonObject.get<int32_t>();
131     natValue64 = jsonObject.get<int64_t>();
132     if (natValue32 == natValue64) {
133         arrayInt32.push_back(natValue32);
134         return;
135     }
136     natValueDouble = natValue64 * 1.0;
137     arrayDouble.push_back(natValueDouble);
138 }
139 
HandleArrayFromJson(const nlohmann::json & jsonObject)140 sptr<IArray> HandleArrayFromJson(const nlohmann::json &jsonObject)
141 {
142     std::vector<std::string> arrayStr;
143     std::vector<bool> arrayBool;
144     std::vector<int32_t> arrayInt32;
145     std::vector<double> arrayDouble;
146     std::vector<nlohmann::json> arrayObject;
147     for (const auto &it : jsonObject) {
148         if (it.is_string()) {
149             std::string natValue = it.get<std::string>();
150             arrayStr.emplace_back(natValue);
151             continue;
152         }
153         if (it.is_boolean()) {
154             bool natValue = it.get<bool>();
155             arrayBool.emplace_back(natValue);
156             continue;
157         }
158         if (it.is_number()) {
159             HandleArrayNumberFromJson(it, arrayInt32, arrayDouble);
160             continue;
161         }
162         if (it.is_array()) {
163             arrayObject.emplace_back(it);
164             continue;
165         }
166         if (it.is_object()) {
167             arrayObject.emplace_back(it);
168         }
169     }
170 
171     if (!arrayObject.empty()) {
172         return HandleArrayObjectFromJson(arrayObject);
173     }
174     if (!arrayStr.empty()) {
175         return HandleArrayStringFromJson(arrayStr);
176     }
177     if (!arrayInt32.empty()) {
178         return HandleArrayInt32FromJson(arrayInt32);
179     }
180     if (!arrayBool.empty()) {
181         return HandleArrayBoolFromJson(arrayBool);
182     }
183     if (!arrayDouble.empty()) {
184         return HandleArrayDoubleFromJson(arrayDouble);
185     }
186     return nullptr;
187 }
188 
BlackListFilter(const std::string & strProName)189 bool BlackListFilter(const std::string &strProName)
190 {
191     if (strProName == "ohos.aafwk.param.windowMode") {
192         return true;
193     }
194     if (strProName == "ohos.aafwk.param.displayId") {
195         return true;
196     }
197     return false;
198 }
199 } // namespace
200 const char* FD = "FD";
201 const char* REMOTE_OBJECT = "RemoteObject";
202 const char* TYPE_PROPERTY = "type";
203 const char* VALUE_PROPERTY = "value";
204 constexpr int32_t MAX_RECURSION_DEPTH = 100;
~UnsupportedData()205 UnsupportedData::~UnsupportedData()
206 {
207     if (buffer != nullptr) {
208         delete[] buffer;
209         buffer = nullptr;
210     }
211 }
212 
213 UnsupportedData::UnsupportedData() = default;
214 
UnsupportedData(const UnsupportedData & other)215 UnsupportedData::UnsupportedData(const UnsupportedData &other) : key(other.key), type(other.type), size(other.size)
216 {
217     buffer = new uint8_t[size];
218     if (memcpy_s(buffer, size, other.buffer, size) != EOK) {
219         ABILITYBASE_LOGE("memcpy failed");
220 
221         key.clear();
222         type = 0;
223         size = 0;
224         delete[] buffer;
225         buffer = nullptr;
226     }
227 }
228 
UnsupportedData(UnsupportedData && other)229 UnsupportedData::UnsupportedData(UnsupportedData &&other)
230     : key(std::move(other.key)), type(other.type), size(other.size), buffer(other.buffer)
231 {
232     other.type = 0;
233     other.size = 0;
234     other.buffer = nullptr;
235 }
236 
operator =(const UnsupportedData & other)237 UnsupportedData &UnsupportedData::operator=(const UnsupportedData &other)
238 {
239     if (this == &other) {
240         return *this;
241     }
242     key = other.key;
243     type = other.type;
244     size = other.size;
245     if (buffer != nullptr) {
246         ABILITYBASE_LOGI("clean buffer");
247         delete[] buffer;
248         buffer = nullptr;
249     }
250     buffer = new uint8_t[size];
251     if (memcpy_s(buffer, size, other.buffer, size) != EOK) {
252         ABILITYBASE_LOGE("memcpy failed");
253 
254         key.clear();
255         type = 0;
256         size = 0;
257         delete[] buffer;
258         buffer = nullptr;
259     }
260     return *this;
261 }
262 
operator =(UnsupportedData && other)263 UnsupportedData &UnsupportedData::operator=(UnsupportedData &&other)
264 {
265     key = std::move(other.key);
266     type = other.type;
267     size = other.size;
268     std::swap(buffer, other.buffer);
269 
270     other.type = 0;
271     other.size = 0;
272     if (other.buffer) {
273         delete[] other.buffer;
274         other.buffer = nullptr;
275     }
276     return *this;
277 }
278 
GetStringByType(const sptr<IInterface> iIt,int typeId)279 std::string WantParams::GetStringByType(const sptr<IInterface> iIt, int typeId)
280 {
281     if (GetDataType(iIt) != typeId) {
282         return "";
283     }
284     if (typeId == VALUE_TYPE_BOOLEAN) {
285         return static_cast<Boolean *>(IBoolean::Query(iIt))->ToString();
286     } else if (typeId == VALUE_TYPE_BYTE) {
287         return static_cast<Byte *>(IByte::Query(iIt))->ToString();
288     } else if (typeId == VALUE_TYPE_CHAR) {
289         return static_cast<Char *>(IChar::Query(iIt))->ToString();
290     } else if (typeId == VALUE_TYPE_SHORT) {
291         return static_cast<Short *>(IShort::Query(iIt))->ToString();
292     } else if (typeId == VALUE_TYPE_INT) {
293         return static_cast<Integer *>(IInteger::Query(iIt))->ToString();
294     } else if (typeId == VALUE_TYPE_LONG) {
295         return static_cast<Long *>(ILong::Query(iIt))->ToString();
296     } else if (typeId == VALUE_TYPE_FLOAT) {
297         return static_cast<Float *>(IFloat::Query(iIt))->ToString();
298     } else if (typeId == VALUE_TYPE_DOUBLE) {
299         return static_cast<Double *>(IDouble::Query(iIt))->ToString();
300     } else if (typeId == VALUE_TYPE_STRING) {
301         return static_cast<String *>(IString::Query(iIt))->ToString();
302     } else if (typeId == VALUE_TYPE_ARRAY) {
303         return static_cast<Array *>(IArray::Query(iIt))->ToString();
304     } else if (typeId == VALUE_TYPE_WANTPARAMS) {
305         return static_cast<WantParamWrapper *>(IWantParams::Query(iIt))->ToString();
306     } else {
307         return "";
308     }
309     return "";
310 }
311 template<typename T1, typename T2, typename T3>
312 static void SetNewArray(const AAFwk::InterfaceID &id, AAFwk::IArray *orgIArray, sptr<AAFwk::IArray> &ao);
313 /**
314  * @description: A constructor used to create an WantParams instance by using the parameters of an existing
315  * WantParams object.
316  * @param wantParams  Indicates the existing WantParams object.
317  */
WantParams(const WantParams & wantParams)318 WantParams::WantParams(const WantParams &wantParams)
319 {
320     params_.clear();
321     NewParams(wantParams, *this);
322 }
323 
WantParams(WantParams && other)324 WantParams::WantParams(WantParams && other) noexcept
325 {
326     *this = std::move(other);
327 }
328 
329 // inner use function
NewFds(const WantParams & source,WantParams & dest)330 bool WantParams::NewFds(const WantParams &source, WantParams &dest)
331 {
332     // Deep copy
333     for (auto it : source.fds_) {
334         dest.fds_[it.first] = it.second;
335     }
336     return true;
337 }  // namespace AAFwk
338 
339 // inner use function
NewParams(const WantParams & source,WantParams & dest)340 bool WantParams::NewParams(const WantParams &source, WantParams &dest)
341 {
342     // Deep copy
343     for (auto it = source.params_.begin(); it != source.params_.end(); it++) {
344         sptr<IInterface> o = it->second;
345         if (IString::Query(o) != nullptr) {
346             dest.params_[it->first] = String::Box(String::Unbox(IString::Query(o)));
347         } else if (IBoolean::Query(o) != nullptr) {
348             dest.params_[it->first] = Boolean::Box(Boolean::Unbox(IBoolean::Query(o)));
349         } else if (IByte::Query(o) != nullptr) {
350             dest.params_[it->first] = Byte::Box(Byte::Unbox(IByte::Query(o)));
351         } else if (IChar::Query(o) != nullptr) {
352             dest.params_[it->first] = Char::Box(Char::Unbox(IChar::Query(o)));
353         } else if (IShort::Query(o) != nullptr) {
354             dest.params_[it->first] = Short::Box(Short::Unbox(IShort::Query(o)));
355         } else if (IInteger::Query(o) != nullptr) {
356             dest.params_[it->first] = Integer::Box(Integer::Unbox(IInteger::Query(o)));
357         } else if (ILong::Query(o) != nullptr) {
358             dest.params_[it->first] = Long::Box(Long::Unbox(ILong::Query(o)));
359         } else if (IFloat::Query(o) != nullptr) {
360             dest.params_[it->first] = Float::Box(Float::Unbox(IFloat::Query(o)));
361         } else if (IDouble::Query(o) != nullptr) {
362             dest.params_[it->first] = Double::Box(Double::Unbox(IDouble::Query(o)));
363         } else if (IRemoteObjectWrap::Query(o) != nullptr) {
364             dest.params_[it->first] = RemoteObjectWrap::Box(RemoteObjectWrap::UnBox(IRemoteObjectWrap::Query(o)));
365         } else if (IWantParams::Query(o) != nullptr) {
366             dest.params_[it->first] = WantParamWrapper::Box(WantParamWrapper::Unbox(IWantParams::Query(o)));
367         } else if (IArray::Query(o) != nullptr) {
368             sptr<IArray> destAO = nullptr;
369             if (!NewArrayData(IArray::Query(o), destAO)) {
370                 continue;
371             }
372             dest.params_[it->first] = destAO;
373         }
374     }
375     return true;
376 }  // namespace AAFwk
377 // inner use
NewArrayData(IArray * source,sptr<IArray> & dest)378 bool WantParams::NewArrayData(IArray *source, sptr<IArray> &dest)
379 {
380     if (Array::IsBooleanArray(source)) {
381         SetNewArray<bool, AAFwk::Boolean, AAFwk::IBoolean>(AAFwk::g_IID_IBoolean, source, dest);
382     } else if (Array::IsCharArray(source)) {
383         SetNewArray<char, AAFwk::Char, AAFwk::IChar>(AAFwk::g_IID_IChar, source, dest);
384     } else if (Array::IsByteArray(source)) {
385         SetNewArray<byte, AAFwk::Byte, AAFwk::IByte>(AAFwk::g_IID_IByte, source, dest);
386     } else if (Array::IsShortArray(source)) {
387         SetNewArray<short, AAFwk::Short, AAFwk::IShort>(AAFwk::g_IID_IShort, source, dest);
388     } else if (Array::IsIntegerArray(source)) {
389         SetNewArray<int, AAFwk::Integer, AAFwk::IInteger>(AAFwk::g_IID_IInteger, source, dest);
390     } else if (Array::IsLongArray(source)) {
391         SetNewArray<long, AAFwk::Long, AAFwk::ILong>(AAFwk::g_IID_ILong, source, dest);
392     } else if (Array::IsFloatArray(source)) {
393         SetNewArray<float, AAFwk::Float, AAFwk::IFloat>(AAFwk::g_IID_IFloat, source, dest);
394     } else if (Array::IsDoubleArray(source)) {
395         SetNewArray<double, AAFwk::Double, AAFwk::IDouble>(AAFwk::g_IID_IDouble, source, dest);
396     } else if (Array::IsStringArray(source)) {
397         SetNewArray<std::string, AAFwk::String, AAFwk::IString>(AAFwk::g_IID_IString, source, dest);
398     } else if (Array::IsWantParamsArray(source)) {
399         SetNewArray<WantParams, AAFwk::WantParamWrapper, AAFwk::IWantParams>(AAFwk::g_IID_IWantParams, source, dest);
400     } else {
401         return false;
402     }
403 
404     if (dest == nullptr) {
405         return false;
406     }
407 
408     return true;
409 }
410 /**
411  * @description: A WantParams used to
412  *
413  * @param other  Indicates the existing WantParams object.
414  */
operator =(const WantParams & other)415 WantParams &WantParams::operator=(const WantParams &other)
416 {
417     if (this != &other) {
418         params_.clear();
419         fds_.clear();
420         NewParams(other, *this);
421         NewFds(other, *this);
422         cachedUnsupportedData_.clear();
423         cachedUnsupportedData_ = other.cachedUnsupportedData_;
424     }
425     return *this;
426 }
427 
operator =(WantParams && other)428 WantParams &WantParams::operator=(WantParams &&other) noexcept
429 {
430     if (this != &other) {
431         // free existing resources.
432         params_.clear();
433         params_ = other.params_;
434         // free other resources.
435         other.params_.clear();
436         fds_.clear();
437         fds_ = other.fds_;
438         other.fds_.clear();
439         cachedUnsupportedData_.clear();
440         cachedUnsupportedData_ = other.cachedUnsupportedData_;
441         other.cachedUnsupportedData_.clear();
442     }
443     return *this;
444 }
445 
operator ==(const WantParams & other)446 bool WantParams::operator==(const WantParams &other)
447 {
448     if (this->params_.size() != other.params_.size()) {
449         return false;
450     }
451     for (auto itthis : this->params_) {
452         auto itother = other.params_.find(itthis.first);
453         if (itother == other.params_.end()) {
454             return false;
455         }
456         int type1 = WantParams::GetDataType(itthis.second);
457         int type2 = WantParams::GetDataType(itother->second);
458         if (type1 != type2) {
459             return false;
460         }
461         if (!CompareInterface(itother->second, itthis.second, type1)) {
462             return false;
463         }
464     }
465     return true;
466 }
467 
GetDataType(const sptr<IInterface> iIt)468 int WantParams::GetDataType(const sptr<IInterface> iIt)
469 {
470     if (iIt == nullptr) {
471         return VALUE_TYPE_NULL;
472     }
473     if (IBoolean::Query(iIt) != nullptr) {
474         return VALUE_TYPE_BOOLEAN;
475     } else if (IByte::Query(iIt) != nullptr) {
476         return VALUE_TYPE_BYTE;
477     } else if (IChar::Query(iIt) != nullptr) {
478         return VALUE_TYPE_CHAR;
479     } else if (IShort::Query(iIt) != nullptr) {
480         return VALUE_TYPE_SHORT;
481     } else if (IInteger::Query(iIt) != nullptr) {
482         return VALUE_TYPE_INT;
483     } else if (ILong::Query(iIt) != nullptr) {
484         return VALUE_TYPE_LONG;
485     } else if (IFloat::Query(iIt) != nullptr) {
486         return VALUE_TYPE_FLOAT;
487     } else if (IDouble::Query(iIt) != nullptr) {
488         return VALUE_TYPE_DOUBLE;
489     } else if (IString::Query(iIt) != nullptr) {
490         return VALUE_TYPE_STRING;
491     } else if (IArray::Query(iIt) != nullptr) {
492         return VALUE_TYPE_ARRAY;
493     } else if (IWantParams::Query(iIt) != nullptr) {
494         return VALUE_TYPE_WANTPARAMS;
495     }
496 
497     return VALUE_TYPE_NULL;
498 }
499 
GetInterfaceByType(int typeId,const std::string & value)500 sptr<IInterface> WantParams::GetInterfaceByType(int typeId, const std::string &value)
501 {
502     if (typeId == VALUE_TYPE_BOOLEAN) {
503         return Boolean::Parse(value);
504     } else if (typeId == VALUE_TYPE_BYTE) {
505         return Byte::Parse(value);
506     } else if (typeId == VALUE_TYPE_CHAR) {
507         return Char::Parse(value);
508     } else if (typeId == VALUE_TYPE_SHORT) {
509         return Short::Parse(value);
510     } else if (typeId == VALUE_TYPE_INT) {
511         return Integer::Parse(value);
512     } else if (typeId == VALUE_TYPE_LONG) {
513         return Long::Parse(value);
514     } else if (typeId == VALUE_TYPE_FLOAT) {
515         return Float::Parse(value);
516     } else if (typeId == VALUE_TYPE_DOUBLE) {
517         return Double::Parse(value);
518     } else if (typeId == VALUE_TYPE_STRING) {
519         return String::Parse(value);
520     } else if (typeId == VALUE_TYPE_ARRAY) {
521         return Array::Parse(value);
522     }
523 
524     return nullptr;
525 }
526 
CompareInterface(const sptr<IInterface> iIt1,const sptr<IInterface> iIt2,int typeId)527 bool WantParams::CompareInterface(const sptr<IInterface> iIt1, const sptr<IInterface> iIt2, int typeId)
528 {
529     auto typeId1 = GetDataType(iIt1);
530     if (typeId1 != GetDataType(iIt2) || typeId1 != typeId) {
531         return false;
532     }
533     bool flag = true;
534     switch (typeId) {
535         case VALUE_TYPE_BOOLEAN:
536             flag =
537                 static_cast<Boolean *>(IBoolean::Query(iIt1))->Equals(*(static_cast<Boolean *>(IBoolean::Query(iIt2))));
538             break;
539         case VALUE_TYPE_BYTE:
540             flag = static_cast<Byte *>(IByte::Query(iIt1))->Equals(*(static_cast<Byte *>(IByte::Query(iIt2))));
541             break;
542         case VALUE_TYPE_CHAR:
543             flag = static_cast<Char *>(IChar::Query(iIt1))->Equals(*(static_cast<Char *>(IChar::Query(iIt2))));
544             break;
545         case VALUE_TYPE_SHORT:
546             flag = static_cast<Short *>(IShort::Query(iIt1))->Equals(*(static_cast<Short *>(IShort::Query(iIt2))));
547             break;
548         case VALUE_TYPE_INT:
549             flag =
550                 static_cast<Integer *>(IInteger::Query(iIt1))->Equals(*(static_cast<Integer *>(IInteger::Query(iIt2))));
551             break;
552         case VALUE_TYPE_LONG:
553             flag = static_cast<Long *>(ILong::Query(iIt1))->Equals(*(static_cast<Long *>(ILong::Query(iIt2))));
554             break;
555         case VALUE_TYPE_FLOAT:
556             flag = static_cast<Float *>(IFloat::Query(iIt1))->Equals(*(static_cast<Float *>(IFloat::Query(iIt2))));
557             break;
558         case VALUE_TYPE_DOUBLE:
559             flag = static_cast<Double *>(IDouble::Query(iIt1))->Equals(*(static_cast<Double *>(IDouble::Query(iIt2))));
560             break;
561         case VALUE_TYPE_STRING:
562             flag = static_cast<String *>(IString::Query(iIt1))->Equals(*(static_cast<String *>(IString::Query(iIt2))));
563             break;
564         case VALUE_TYPE_ARRAY:
565             flag = static_cast<Array *>(IArray::Query(iIt1))->Equals(*(static_cast<Array *>(IArray::Query(iIt2))));
566             break;
567         case VALUE_TYPE_WANTPARAMS:
568             flag = static_cast<WantParamWrapper *>(IWantParams::Query(iIt1))->
569                 Equals(*(static_cast<WantParamWrapper *>(IWantParams::Query(iIt2))));
570             break;
571         default:
572             break;
573     }
574     return flag;
575 }
576 
577 /**
578  * @description: Sets a parameter in key-value pair format.
579  * @param key Indicates the key matching the parameter.
580  */
SetParam(const std::string & key,IInterface * value)581 void WantParams::SetParam(const std::string &key, IInterface *value)
582 {
583     params_[key] = value;
584 }
585 
586 /**
587  * @description: Obtains the parameter value based on a given key.
588  * @param key Indicates the key matching the parameter.
589  * @return Returns the value matching the given key.
590  */
GetParam(const std::string & key) const591 sptr<IInterface> WantParams::GetParam(const std::string &key) const
592 {
593     auto it = params_.find(key);
594     if (it == params_.cend()) {
595         return nullptr;
596     }
597     return it->second;
598 }
599 
GetWantParams(const std::string & key) const600 WantParams WantParams::GetWantParams(const std::string& key) const
601 {
602     auto value = GetParam(key);
603     IWantParams *wp = IWantParams::Query(value);
604     if (wp != nullptr) {
605         return WantParamWrapper::Unbox(wp);
606     }
607     return WantParams();
608 }
609 
GetStringParam(const std::string & key) const610 std::string WantParams::GetStringParam(const std::string& key) const
611 {
612     auto value = GetParam(key);
613     IString *ao = IString::Query(value);
614     if (ao != nullptr) {
615         return String::Unbox(ao);
616     }
617     return std::string();
618 }
619 
GetIntParam(const std::string & key,const int defaultValue) const620 int WantParams::GetIntParam(const std::string& key, const int defaultValue) const
621 {
622     ABILITYBASE_LOGD("called");
623     auto value = GetParam(key);
624     IInteger *ao = IInteger::Query(value);
625     if (ao != nullptr) {
626         return Integer::Unbox(ao);
627     }
628     return defaultValue;
629 }
630 
631 /**
632  * @description: Obtains the parameter value based on a given key.
633  * @param key Indicates the key matching the parameter.
634  * @return Returns the value matching the given key.
635  */
636 
GetParams() const637 const std::map<std::string, sptr<IInterface>> &WantParams::GetParams() const
638 {
639     return params_;
640 }
641 
642 /**
643  * @description: Obtains a set of the keys of all parameters.
644  * @param
645  * @return Returns a set of keys.
646  */
KeySet() const647 const std::set<std::string> WantParams::KeySet() const
648 {
649     std::set<std::string> keySet;
650     keySet.clear();
651     for (auto it : params_) {
652         keySet.emplace(it.first);
653     }
654 
655     return keySet;
656 }
657 
658 /**
659  * @description: Removes the parameter matching the given key.
660  * @param key Indicates the key matching the parameter to be removed.
661  */
Remove(const std::string & key)662 void WantParams::Remove(const std::string &key)
663 {
664     params_.erase(key);
665 }
666 
667 /**
668  * @description: Checks whether the Want contains the given key.
669  * @param key Indicates the key to check.
670  * @return Returns true if the Want contains the key; returns false otherwise.
671  */
HasParam(const std::string & key) const672 bool WantParams::HasParam(const std::string &key) const
673 {
674     return (params_.count(key) > 0);
675 }
676 
677 /**
678  * @description: Obtains the number of parameters contained in this WantParams object.
679  * @return Returns the number of parameters.
680  */
Size() const681 int WantParams::Size() const
682 {
683     return params_.size();
684 }
685 
686 /**
687  * @description: Checks whether this WantParams object contains no parameters.
688  * @return Returns true if this object does not contain any parameters; returns false otherwise.
689  */
IsEmpty() const690 bool WantParams::IsEmpty() const
691 {
692     return (params_.size() == 0);
693 }
694 
WriteToParcelString(Parcel & parcel,sptr<IInterface> & o) const695 bool WantParams::WriteToParcelString(Parcel &parcel, sptr<IInterface> &o) const
696 {
697     std::string value = String::Unbox(IString::Query(o));
698     if (!parcel.WriteInt32(VALUE_TYPE_STRING)) {
699         return false;
700     }
701     return parcel.WriteString16(Str8ToStr16(value));
702 }
703 
WriteToParcelBool(Parcel & parcel,sptr<IInterface> & o) const704 bool WantParams::WriteToParcelBool(Parcel &parcel, sptr<IInterface> &o) const
705 {
706     bool value = Boolean::Unbox(IBoolean::Query(o));
707     if (!parcel.WriteInt32(VALUE_TYPE_BOOLEAN)) {
708         return false;
709     }
710     return parcel.WriteInt8(value);
711 }
712 
WriteToParcelWantParams(Parcel & parcel,sptr<IInterface> & o,int depth) const713 bool WantParams::WriteToParcelWantParams(Parcel &parcel, sptr<IInterface> &o, int depth) const
714 {
715     WantParams value = WantParamWrapper::Unbox(IWantParams::Query(o));
716 
717     auto type = value.GetParam(TYPE_PROPERTY);
718     AAFwk::IString *typeP = AAFwk::IString::Query(type);
719     if (typeP != nullptr) {
720         std::string typeValue = AAFwk::String::Unbox(typeP);
721         if (typeValue == FD) {
722             return WriteToParcelFD(parcel, value);
723         }
724         if (typeValue == REMOTE_OBJECT) {
725             return WriteToParcelRemoteObject(parcel, value);
726         }
727     }
728 
729     if (!parcel.WriteInt32(VALUE_TYPE_WANTPARAMS)) {
730         return false;
731     }
732     return value.DoMarshalling(parcel, depth + 1);
733 }
734 
WriteToParcelFD(Parcel & parcel,const WantParams & value) const735 bool WantParams::WriteToParcelFD(Parcel &parcel, const WantParams &value) const
736 {
737     ABILITYBASE_LOGI("called");
738     if (!parcel.WriteInt32(VALUE_TYPE_FD)) {
739         return false;
740     }
741 
742     auto fdWrap = value.GetParam(VALUE_PROPERTY);
743     AAFwk::IInteger *fdIWrap = AAFwk::IInteger::Query(fdWrap);
744     if (fdIWrap != nullptr) {
745         int fd = AAFwk::Integer::Unbox(fdIWrap);
746         auto messageParcel = static_cast<MessageParcel*>(&parcel);
747         if (messageParcel == nullptr) {
748             return false;
749         }
750         bool ret = messageParcel->WriteFileDescriptor(fd);
751         ABILITYBASE_LOGI("fd:%{public}d, ret:%{public}d", fd, ret);
752         return ret;
753     }
754 
755     return false;
756 }
757 
WriteToParcelRemoteObject(Parcel & parcel,const WantParams & value) const758 bool WantParams::WriteToParcelRemoteObject(Parcel &parcel, const WantParams &value) const
759 {
760     ABILITYBASE_LOGD("called");
761     if (!parcel.WriteInt32(VALUE_TYPE_REMOTE_OBJECT)) {
762         return false;
763     }
764 
765     auto remoteObjectWrap = value.GetParam(VALUE_PROPERTY);
766     AAFwk::IRemoteObjectWrap *remoteObjectIWrap = AAFwk::IRemoteObjectWrap::Query(remoteObjectWrap);
767     if (remoteObjectIWrap != nullptr) {
768         auto remoteObject = AAFwk::RemoteObjectWrap::UnBox(remoteObjectIWrap);
769         auto messageParcel = static_cast<MessageParcel*>(&parcel);
770         if (messageParcel == nullptr) {
771             return false;
772         }
773         bool ret = messageParcel->WriteRemoteObject(remoteObject);
774         ABILITYBASE_LOGD("ret:%{public}d", ret);
775         return ret;
776     }
777     return false;
778 }
779 
WriteToParcelByte(Parcel & parcel,sptr<IInterface> & o) const780 bool WantParams::WriteToParcelByte(Parcel &parcel, sptr<IInterface> &o) const
781 {
782     byte value = Byte::Unbox(IByte::Query(o));
783     if (!parcel.WriteInt32(VALUE_TYPE_BYTE)) {
784         return false;
785     }
786     return parcel.WriteInt8(value);
787 }
788 
WriteToParcelChar(Parcel & parcel,sptr<IInterface> & o) const789 bool WantParams::WriteToParcelChar(Parcel &parcel, sptr<IInterface> &o) const
790 {
791     zchar value = Char::Unbox(IChar::Query(o));
792     if (!parcel.WriteInt32(VALUE_TYPE_CHAR)) {
793         return false;
794     }
795     return parcel.WriteInt32(value);
796 }
797 
WriteToParcelShort(Parcel & parcel,sptr<IInterface> & o) const798 bool WantParams::WriteToParcelShort(Parcel &parcel, sptr<IInterface> &o) const
799 {
800     short value = Short::Unbox(IShort::Query(o));
801     if (!parcel.WriteInt32(VALUE_TYPE_SHORT)) {
802         return false;
803     }
804     return parcel.WriteInt16(value);
805 }
806 
WriteToParcelInt(Parcel & parcel,sptr<IInterface> & o) const807 bool WantParams::WriteToParcelInt(Parcel &parcel, sptr<IInterface> &o) const
808 {
809     int value = Integer::Unbox(IInteger::Query(o));
810     if (!parcel.WriteInt32(VALUE_TYPE_INT)) {
811         return false;
812     }
813     return parcel.WriteInt32(value);
814 }
815 
WriteToParcelLong(Parcel & parcel,sptr<IInterface> & o) const816 bool WantParams::WriteToParcelLong(Parcel &parcel, sptr<IInterface> &o) const
817 {
818     long value = Long::Unbox(ILong::Query(o));
819     if (!parcel.WriteInt32(VALUE_TYPE_LONG)) {
820         return false;
821     }
822     return parcel.WriteInt64(value);
823 }
824 
WriteToParcelFloat(Parcel & parcel,sptr<IInterface> & o) const825 bool WantParams::WriteToParcelFloat(Parcel &parcel, sptr<IInterface> &o) const
826 {
827     float value = Float::Unbox(IFloat::Query(o));
828     if (!parcel.WriteInt32(VALUE_TYPE_FLOAT)) {
829         return false;
830     }
831     return parcel.WriteFloat(value);
832 }
833 
WriteToParcelDouble(Parcel & parcel,sptr<IInterface> & o) const834 bool WantParams::WriteToParcelDouble(Parcel &parcel, sptr<IInterface> &o) const
835 {
836     double value = Double::Unbox(IDouble::Query(o));
837     if (!parcel.WriteInt32(VALUE_TYPE_DOUBLE)) {
838         return false;
839     }
840     return parcel.WriteDouble(value);
841 }
842 
WriteMarshalling(Parcel & parcel,sptr<IInterface> & o,int depth) const843 bool WantParams::WriteMarshalling(Parcel &parcel, sptr<IInterface> &o, int depth) const
844 {
845     if (IString::Query(o) != nullptr) {
846         return WriteToParcelString(parcel, o);
847     } else if (IBoolean::Query(o) != nullptr) {
848         return WriteToParcelBool(parcel, o);
849     } else if (IByte::Query(o) != nullptr) {
850         return WriteToParcelByte(parcel, o);
851     } else if (IChar::Query(o) != nullptr) {
852         return WriteToParcelChar(parcel, o);
853     } else if (IShort::Query(o) != nullptr) {
854         return WriteToParcelShort(parcel, o);
855     } else if (IInteger::Query(o) != nullptr) {
856         return WriteToParcelInt(parcel, o);
857     } else if (ILong::Query(o) != nullptr) {
858         return WriteToParcelLong(parcel, o);
859     } else if (IFloat::Query(o) != nullptr) {
860         return WriteToParcelFloat(parcel, o);
861     } else if (IDouble::Query(o) != nullptr) {
862         return WriteToParcelDouble(parcel, o);
863     } else if (IWantParams::Query(o) != nullptr) {
864         return WriteToParcelWantParams(parcel, o, depth);
865     } else {
866         IArray *ao = IArray::Query(o);
867         if (ao != nullptr) {
868             sptr<IArray> array(ao);
869             return WriteArrayToParcel(parcel, array, depth);
870         } else {
871             return true;
872         }
873     }
874 }
875 
DoMarshalling(Parcel & parcel,int depth) const876 bool WantParams::DoMarshalling(Parcel &parcel, int depth) const
877 {
878     if (depth >= MAX_RECURSION_DEPTH) {
879         return false;
880     }
881     size_t size = params_.size();
882     if (!cachedUnsupportedData_.empty()) {
883         size += cachedUnsupportedData_.size();
884     }
885 
886     if (!parcel.WriteInt32(size)) {
887         return false;
888     }
889 
890     auto iter = params_.cbegin();
891     while (iter != params_.cend()) {
892         std::string key = iter->first;
893         sptr<IInterface> o = iter->second;
894         if (!parcel.WriteString16(Str8ToStr16(key))) {
895             return false;
896         }
897         if (!WriteMarshalling(parcel, o, depth)) {
898             return false;
899         }
900         iter++;
901     }
902 
903     if (!cachedUnsupportedData_.empty()) {
904         for (const UnsupportedData &data : cachedUnsupportedData_) {
905             if (!parcel.WriteString16(data.key)) {
906                 return false;
907             }
908             if (!parcel.WriteInt32(data.type)) {
909                 return false;
910             }
911             if (!parcel.WriteInt32(data.size)) {
912                 return false;
913             }
914             // Corresponding to Parcel#writeByteArray() in Java.
915             if (!parcel.WriteInt32(data.size)) {
916                 return false;
917             }
918             if (!parcel.WriteBuffer(data.buffer, data.size)) {
919                 return false;
920             }
921         }
922     }
923     return true;
924 }
925 
926 /**
927  * @description: Marshals an WantParams object into a Parcel.
928  * @param Key-value pairs in the WantParams are marshalled separately.
929  * @return If any key-value pair fails to be marshalled, false is returned.
930  */
Marshalling(Parcel & parcel) const931 bool WantParams::Marshalling(Parcel &parcel) const
932 {
933     return DoMarshalling(parcel);
934 }
935 
936 template<typename dataType, typename className>
SetArray(const InterfaceID & id,const std::vector<dataType> & value,sptr<IArray> & ao)937 static bool SetArray(const InterfaceID &id, const std::vector<dataType> &value, sptr<IArray> &ao)
938 {
939     typename std::vector<dataType>::size_type size = value.size();
940     ao = new (std::nothrow) Array(size, id);
941     if (ao != nullptr) {
942         for (typename std::vector<dataType>::size_type i = 0; i < size; i++) {
943             ao->Set(i, className::Box(value[i]));
944         }
945         return true;
946     }
947     return false;
948 }
949 
950 template<typename T1, typename T2, typename T3>
FillArray(IArray * ao,std::vector<T1> & array)951 static void FillArray(IArray *ao, std::vector<T1> &array)
952 {
953     auto func = [&](IInterface *object) {
954         if (object != nullptr) {
955             T3 *value = T3::Query(object);
956             if (value != nullptr) {
957                 array.push_back(T2::Unbox(value));
958             }
959         }
960     };
961     Array::ForEach(ao, func);
962 }
963 // inner use template function
964 template<typename T1, typename T2, typename T3>
SetNewArray(const AAFwk::InterfaceID & id,AAFwk::IArray * orgIArray,sptr<AAFwk::IArray> & ao)965 static void SetNewArray(const AAFwk::InterfaceID &id, AAFwk::IArray *orgIArray, sptr<AAFwk::IArray> &ao)
966 {
967     if (orgIArray == nullptr) {
968         return;
969     }
970     std::vector<T1> array;
971     auto func = [&](IInterface *object) {
972         if (object != nullptr) {
973             T3 *value = T3::Query(object);
974             if (value != nullptr) {
975                 array.push_back(T2::Unbox(value));
976             }
977         }
978     };
979     Array::ForEach(orgIArray, func);
980 
981     typename std::vector<T1>::size_type size = array.size();
982     if (size > 0) {
983         ao = new (std::nothrow) AAFwk::Array(size, id);
984         if (ao != nullptr) {
985             for (typename std::vector<T1>::size_type i = 0; i < size; i++) {
986                 ao->Set(i, T2::Box(array[i]));
987             }
988         }
989     }
990 }
991 
WriteArrayToParcelString(Parcel & parcel,IArray * ao) const992 bool WantParams::WriteArrayToParcelString(Parcel &parcel, IArray *ao) const
993 {
994     if (ao == nullptr) {
995         return false;
996     }
997 
998     std::vector<std::u16string> array;
999     auto func = [&](IInterface *object) {
1000         std::string s = String::Unbox(IString::Query(object));
1001         array.push_back(Str8ToStr16(s));
1002     };
1003 
1004     Array::ForEach(ao, func);
1005 
1006     if (!parcel.WriteInt32(VALUE_TYPE_STRINGARRAY)) {
1007         return false;
1008     }
1009     return parcel.WriteString16Vector(array);
1010 }
1011 
WriteArrayToParcelBool(Parcel & parcel,IArray * ao) const1012 bool WantParams::WriteArrayToParcelBool(Parcel &parcel, IArray *ao) const
1013 {
1014     if (ao == nullptr) {
1015         return false;
1016     }
1017 
1018     std::vector<int8_t> array;
1019     std::vector<int32_t> intArray;
1020     FillArray<int8_t, Boolean, IBoolean>(ao, array);
1021     if (!parcel.WriteInt32(VALUE_TYPE_BOOLEANARRAY)) {
1022         return false;
1023     }
1024 
1025     for (std::vector<int8_t>::size_type i = 0; i < array.size(); i++) {
1026         intArray.push_back(array[i]);
1027     }
1028     return parcel.WriteInt32Vector(intArray);
1029 }
1030 
WriteArrayToParcelByte(Parcel & parcel,IArray * ao) const1031 bool WantParams::WriteArrayToParcelByte(Parcel &parcel, IArray *ao) const
1032 {
1033     if (ao == nullptr) {
1034         return false;
1035     }
1036 
1037     std::vector<int8_t> array;
1038     FillArray<int8_t, Byte, IByte>(ao, array);
1039     if (!parcel.WriteInt32(VALUE_TYPE_BYTEARRAY)) {
1040         return false;
1041     }
1042     return parcel.WriteInt8Vector(array);
1043 }
1044 
WriteArrayToParcelChar(Parcel & parcel,IArray * ao) const1045 bool WantParams::WriteArrayToParcelChar(Parcel &parcel, IArray *ao) const
1046 {
1047     if (ao == nullptr) {
1048         return false;
1049     }
1050 
1051     std::vector<int32_t> array;
1052     FillArray<int32_t, Char, IChar>(ao, array);
1053     if (!parcel.WriteInt32(VALUE_TYPE_CHARARRAY)) {
1054         return false;
1055     }
1056     return parcel.WriteInt32Vector(array);
1057 }
1058 
WriteArrayToParcelShort(Parcel & parcel,IArray * ao) const1059 bool WantParams::WriteArrayToParcelShort(Parcel &parcel, IArray *ao) const
1060 {
1061     if (ao == nullptr) {
1062         return false;
1063     }
1064 
1065     std::vector<short> array;
1066     FillArray<short, Short, IShort>(ao, array);
1067     if (!parcel.WriteInt32(VALUE_TYPE_SHORTARRAY)) {
1068         return false;
1069     }
1070     return parcel.WriteInt16Vector(array);
1071 }
1072 
WriteArrayToParcelInt(Parcel & parcel,IArray * ao) const1073 bool WantParams::WriteArrayToParcelInt(Parcel &parcel, IArray *ao) const
1074 {
1075     if (ao == nullptr) {
1076         return false;
1077     }
1078 
1079     std::vector<int> array;
1080     FillArray<int, Integer, IInteger>(ao, array);
1081     if (!parcel.WriteInt32(VALUE_TYPE_INTARRAY)) {
1082         return false;
1083     }
1084     return parcel.WriteInt32Vector(array);
1085 }
1086 
WriteArrayToParcelLong(Parcel & parcel,IArray * ao) const1087 bool WantParams::WriteArrayToParcelLong(Parcel &parcel, IArray *ao) const
1088 {
1089     if (ao == nullptr) {
1090         return false;
1091     }
1092 
1093     std::vector<int64_t> array;
1094     FillArray<int64_t, Long, ILong>(ao, array);
1095     if (!parcel.WriteInt32(VALUE_TYPE_LONGARRAY)) {
1096         return false;
1097     }
1098     return parcel.WriteInt64Vector(array);
1099 }
1100 
WriteArrayToParcelFloat(Parcel & parcel,IArray * ao) const1101 bool WantParams::WriteArrayToParcelFloat(Parcel &parcel, IArray *ao) const
1102 {
1103     if (ao == nullptr) {
1104         return false;
1105     }
1106 
1107     std::vector<float> array;
1108     FillArray<float, Float, IFloat>(ao, array);
1109     if (!parcel.WriteInt32(VALUE_TYPE_FLOATARRAY)) {
1110         return false;
1111     }
1112     return parcel.WriteFloatVector(array);
1113 }
1114 
WriteArrayToParcelDouble(Parcel & parcel,IArray * ao) const1115 bool WantParams::WriteArrayToParcelDouble(Parcel &parcel, IArray *ao) const
1116 {
1117     if (ao == nullptr) {
1118         return false;
1119     }
1120 
1121     std::vector<double> array;
1122     FillArray<double, Double, IDouble>(ao, array);
1123     if (!parcel.WriteInt32(VALUE_TYPE_DOUBLEARRAY)) {
1124         return false;
1125     }
1126     return parcel.WriteDoubleVector(array);
1127 }
1128 
WriteArrayToParcelWantParams(Parcel & parcel,IArray * ao,int depth) const1129 bool WantParams::WriteArrayToParcelWantParams(Parcel &parcel, IArray *ao, int depth) const
1130 {
1131     if (ao == nullptr) {
1132         return false;
1133     }
1134     if (!parcel.WriteInt32(VALUE_TYPE_WANTPARAMSARRAY)) {
1135         return false;
1136     }
1137     std::vector<WantParams> array;
1138     auto func = [&](AAFwk::IInterface *object) {
1139         if (object != nullptr) {
1140             IWantParams *value = AAFwk::IWantParams::Query(object);
1141             if (value != nullptr) {
1142                 array.push_back(AAFwk::WantParamWrapper::Unbox(value));
1143             }
1144         }
1145     };
1146     AAFwk::Array::ForEach(ao, func);
1147     if (!parcel.WriteInt32(array.size())) {
1148         return false;
1149     }
1150 
1151     for (const auto& wp : array) {
1152         if (!wp.DoMarshalling(parcel, depth + 1)) {
1153             return false;
1154         }
1155     }
1156     return true;
1157 }
1158 
WriteArrayToParcel(Parcel & parcel,IArray * ao,int depth) const1159 bool WantParams::WriteArrayToParcel(Parcel &parcel, IArray *ao, int depth) const
1160 {
1161     if (Array::IsStringArray(ao)) {
1162         return WriteArrayToParcelString(parcel, ao);
1163     } else if (Array::IsBooleanArray(ao)) {
1164         return WriteArrayToParcelBool(parcel, ao);
1165     } else if (Array::IsByteArray(ao)) {
1166         return WriteArrayToParcelByte(parcel, ao);
1167     } else if (Array::IsCharArray(ao)) {
1168         return WriteArrayToParcelChar(parcel, ao);
1169     } else if (Array::IsShortArray(ao)) {
1170         return WriteArrayToParcelShort(parcel, ao);
1171     } else if (Array::IsIntegerArray(ao)) {
1172         return WriteArrayToParcelInt(parcel, ao);
1173     } else if (Array::IsLongArray(ao)) {
1174         return WriteArrayToParcelLong(parcel, ao);
1175     } else if (Array::IsFloatArray(ao)) {
1176         return WriteArrayToParcelFloat(parcel, ao);
1177     } else if (Array::IsDoubleArray(ao)) {
1178         return WriteArrayToParcelDouble(parcel, ao);
1179     } else if (Array::IsWantParamsArray(ao)) {
1180         return WriteArrayToParcelWantParams(parcel, ao, depth);
1181     } else {
1182         return true;
1183     }
1184 }
1185 
ReadFromParcelArrayString(Parcel & parcel,sptr<IArray> & ao)1186 bool WantParams::ReadFromParcelArrayString(Parcel &parcel, sptr<IArray> &ao)
1187 {
1188     std::vector<std::u16string> value;
1189     if (!parcel.ReadString16Vector(&value)) {
1190         ABILITYBASE_LOGE("read string of array fail");
1191         return false;
1192     }
1193 
1194     std::vector<std::u16string>::size_type size = value.size();
1195     ao = new (std::nothrow) Array(size, g_IID_IString);
1196     if (ao != nullptr) {
1197         for (std::vector<std::u16string>::size_type i = 0; i < size; i++) {
1198             ao->Set(i, String::Box(Str16ToStr8(value[i])));
1199         }
1200         return true;
1201     } else {
1202         ABILITYBASE_LOGE("null ao");
1203     }
1204     return false;
1205 }
1206 
ReadFromParcelArrayBool(Parcel & parcel,sptr<IArray> & ao)1207 bool WantParams::ReadFromParcelArrayBool(Parcel &parcel, sptr<IArray> &ao)
1208 {
1209     std::vector<int32_t> value;
1210     std::vector<int8_t> boolValue;
1211     if (!parcel.ReadInt32Vector(&value)) {
1212         ABILITYBASE_LOGE("read bool of array fail");
1213         return false;
1214     }
1215 
1216     std::vector<int32_t>::size_type size = value.size();
1217     for (std::vector<int32_t>::size_type i = 0; i < size; i++) {
1218         boolValue.push_back(value[i]);
1219     }
1220     return SetArray<int8_t, Boolean>(g_IID_IBoolean, boolValue, ao);
1221 }
1222 
ReadFromParcelArrayByte(Parcel & parcel,sptr<IArray> & ao)1223 bool WantParams::ReadFromParcelArrayByte(Parcel &parcel, sptr<IArray> &ao)
1224 {
1225     std::vector<int8_t> value;
1226     if (!parcel.ReadInt8Vector(&value)) {
1227         ABILITYBASE_LOGE("read value failed");
1228         return false;
1229     }
1230     return SetArray<int8_t, Byte>(g_IID_IByte, value, ao);
1231 }
1232 
ReadFromParcelArrayChar(Parcel & parcel,sptr<IArray> & ao)1233 bool WantParams::ReadFromParcelArrayChar(Parcel &parcel, sptr<IArray> &ao)
1234 {
1235     std::vector<int32_t> value;
1236     if (!parcel.ReadInt32Vector(&value)) {
1237         ABILITYBASE_LOGE("read value failed");
1238         return false;
1239     }
1240     return SetArray<int32_t, Char>(g_IID_IChar, value, ao);
1241 }
1242 
ReadFromParcelArrayShort(Parcel & parcel,sptr<IArray> & ao)1243 bool WantParams::ReadFromParcelArrayShort(Parcel &parcel, sptr<IArray> &ao)
1244 {
1245     std::vector<short> value;
1246     if (!parcel.ReadInt16Vector(&value)) {
1247         ABILITYBASE_LOGE("read value failed");
1248         return false;
1249     }
1250     return SetArray<short, Short>(g_IID_IShort, value, ao);
1251 }
1252 
ReadFromParcelArrayInt(Parcel & parcel,sptr<IArray> & ao)1253 bool WantParams::ReadFromParcelArrayInt(Parcel &parcel, sptr<IArray> &ao)
1254 {
1255     std::vector<int> value;
1256     if (!parcel.ReadInt32Vector(&value)) {
1257         ABILITYBASE_LOGE("read value failed");
1258         return false;
1259     }
1260     return SetArray<int, Integer>(g_IID_IInteger, value, ao);
1261 }
1262 
ReadFromParcelArrayLong(Parcel & parcel,sptr<IArray> & ao)1263 bool WantParams::ReadFromParcelArrayLong(Parcel &parcel, sptr<IArray> &ao)
1264 {
1265     std::vector<int64_t> value;
1266     if (!parcel.ReadInt64Vector(&value)) {
1267         ABILITYBASE_LOGE("read value failed");
1268         return false;
1269     }
1270 
1271 #ifdef WANT_PARAM_USE_LONG
1272     return SetArray<int64_t, Long>(g_IID_ILong, value, ao);
1273 #else
1274     std::vector<std::string> strList;
1275     for (size_t i = 0; i < value.size(); i++) {
1276         strList.push_back(std::to_string(value[i]));
1277     }
1278     return SetArray<std::string, String>(g_IID_IString, strList, ao);
1279 #endif
1280 }
1281 
ReadFromParcelArrayFloat(Parcel & parcel,sptr<IArray> & ao)1282 bool WantParams::ReadFromParcelArrayFloat(Parcel &parcel, sptr<IArray> &ao)
1283 {
1284     std::vector<float> value;
1285     if (!parcel.ReadFloatVector(&value)) {
1286         ABILITYBASE_LOGE("read value failed");
1287         return false;
1288     }
1289     return SetArray<float, Float>(g_IID_IFloat, value, ao);
1290 }
1291 
ReadFromParcelArrayDouble(Parcel & parcel,sptr<IArray> & ao)1292 bool WantParams::ReadFromParcelArrayDouble(Parcel &parcel, sptr<IArray> &ao)
1293 {
1294     std::vector<double> value;
1295     if (!parcel.ReadDoubleVector(&value)) {
1296         ABILITYBASE_LOGE("read value failed");
1297         return false;
1298     }
1299     return SetArray<double, Double>(g_IID_IDouble, value, ao);
1300 }
1301 
ReadFromParcelArrayWantParams(Parcel & parcel,sptr<IArray> & ao,int depth)1302 bool WantParams::ReadFromParcelArrayWantParams(Parcel &parcel, sptr<IArray> &ao, int depth)
1303 {
1304     int32_t size = parcel.ReadInt32();
1305     static constexpr int32_t maxAllowedSize = 1024;
1306     if (size < 0 || size > maxAllowedSize) {
1307         ABILITYBASE_LOGE("invalid size: %{public}d", size);
1308         return false;
1309     }
1310     std::vector<sptr<IInterface>> arrayWantParams;
1311     for (int32_t i = 0; i < size; ++i) {
1312         sptr<WantParams> value(Unmarshalling(parcel, depth + 1));
1313         if (value != nullptr) {
1314             sptr<IInterface> interface = WantParamWrapper::Box(*value);
1315             if (interface != nullptr) {
1316                 arrayWantParams.push_back(interface);
1317             }
1318         }
1319     }
1320 
1321     ao = new (std::nothrow) AAFwk::Array(arrayWantParams.size(), AAFwk::g_IID_IWantParams);
1322     if (ao != nullptr) {
1323         for (size_t i = 0; i < arrayWantParams.size(); i++) {
1324             ao->Set(i, arrayWantParams[i]);
1325         }
1326         return true;
1327     }
1328     return false;
1329 }
1330 
ReadArrayToParcel(Parcel & parcel,int type,sptr<IArray> & ao,int depth)1331 bool WantParams::ReadArrayToParcel(Parcel &parcel, int type, sptr<IArray> &ao, int depth)
1332 {
1333     switch (type) {
1334         case VALUE_TYPE_STRINGARRAY:
1335         case VALUE_TYPE_CHARSEQUENCEARRAY:
1336             return ReadFromParcelArrayString(parcel, ao);
1337         case VALUE_TYPE_BOOLEANARRAY:
1338             return ReadFromParcelArrayBool(parcel, ao);
1339         case VALUE_TYPE_BYTEARRAY:
1340             return ReadFromParcelArrayByte(parcel, ao);
1341         case VALUE_TYPE_CHARARRAY:
1342             return ReadFromParcelArrayChar(parcel, ao);
1343         case VALUE_TYPE_SHORTARRAY:
1344             return ReadFromParcelArrayShort(parcel, ao);
1345         case VALUE_TYPE_INTARRAY:
1346             return ReadFromParcelArrayInt(parcel, ao);
1347         case VALUE_TYPE_LONGARRAY:
1348             return ReadFromParcelArrayLong(parcel, ao);
1349         case VALUE_TYPE_FLOATARRAY:
1350             return ReadFromParcelArrayFloat(parcel, ao);
1351         case VALUE_TYPE_DOUBLEARRAY:
1352             return ReadFromParcelArrayDouble(parcel, ao);
1353         case VALUE_TYPE_WANTPARAMSARRAY:
1354             return ReadFromParcelArrayWantParams(parcel, ao, depth);
1355         default:
1356             break;
1357     }
1358 
1359     return true;
1360 }
1361 
ReadFromParcelString(Parcel & parcel,const std::string & key)1362 bool WantParams::ReadFromParcelString(Parcel &parcel, const std::string &key)
1363 {
1364     std::u16string value = parcel.ReadString16();
1365     std::string strValue(Str16ToStr8(value));
1366     sptr<IInterface> intf = String::Box(Str16ToStr8(value));
1367     if (intf) {
1368         SetParam(key, intf);
1369     } else {
1370         ABILITYBASE_LOGE("read data fail: key=%{public}s", key.c_str());
1371     }
1372     return true;
1373 }
1374 
ReadFromParcelBool(Parcel & parcel,const std::string & key)1375 bool WantParams::ReadFromParcelBool(Parcel &parcel, const std::string &key)
1376 {
1377     int8_t value;
1378     if (parcel.ReadInt8(value)) {
1379         sptr<IInterface> intf = Boolean::Box(value);
1380         if (intf) {
1381             SetParam(key, intf);
1382         } else {
1383             ABILITYBASE_LOGE("insert param fail: key=%{public}s", key.c_str());
1384         }
1385         return true;
1386     } else {
1387         ABILITYBASE_LOGE("read data fail: key=%{public}s", key.c_str());
1388         return false;
1389     }
1390 }
1391 
ReadFromParcelInt8(Parcel & parcel,const std::string & key)1392 bool WantParams::ReadFromParcelInt8(Parcel &parcel, const std::string &key)
1393 {
1394     int8_t value;
1395     if (parcel.ReadInt8(value)) {
1396         sptr<IInterface> intf = Byte::Box(value);
1397         if (intf) {
1398             SetParam(key, intf);
1399         } else {
1400             ABILITYBASE_LOGE("insert arguments fail: key=%{public}s", key.c_str());
1401         }
1402         return true;
1403     } else {
1404         ABILITYBASE_LOGE("read data error: key=%{public}s", key.c_str());
1405         return false;
1406     }
1407 }
1408 
ReadFromParcelChar(Parcel & parcel,const std::string & key)1409 bool WantParams::ReadFromParcelChar(Parcel &parcel, const std::string &key)
1410 {
1411     int32_t value;
1412     if (parcel.ReadInt32(value)) {
1413         sptr<IInterface> intf = Char::Box(value);
1414         if (intf) {
1415             SetParam(key, intf);
1416         } else {
1417             ABILITYBASE_LOGE("insert param error: key=%{public}s", key.c_str());
1418         }
1419         return true;
1420     } else {
1421         ABILITYBASE_LOGE("read data error: key=%{public}s", key.c_str());
1422         return false;
1423     }
1424 }
1425 
ReadFromParcelShort(Parcel & parcel,const std::string & key)1426 bool WantParams::ReadFromParcelShort(Parcel &parcel, const std::string &key)
1427 {
1428     short value;
1429     if (parcel.ReadInt16(value)) {
1430         sptr<IInterface> intf = Short::Box(value);
1431         if (intf) {
1432             SetParam(key, intf);
1433         } else {
1434             ABILITYBASE_LOGE("insert arguments error: key=%{public}s", key.c_str());
1435         }
1436         return true;
1437     } else {
1438         ABILITYBASE_LOGE("read data fail: key=%{public}s", key.c_str());
1439         return false;
1440     }
1441 }
1442 
ReadFromParcelInt(Parcel & parcel,const std::string & key)1443 bool WantParams::ReadFromParcelInt(Parcel &parcel, const std::string &key)
1444 {
1445     int value;
1446     if (parcel.ReadInt32(value)) {
1447         sptr<IInterface> intf = Integer::Box(value);
1448         if (intf) {
1449             SetParam(key, intf);
1450         } else {
1451             ABILITYBASE_LOGE("insert param fail: key:%{public}s", key.c_str());
1452         }
1453         return true;
1454     } else {
1455         ABILITYBASE_LOGE("read data fail: key:%{public}s", key.c_str());
1456         return false;
1457     }
1458 }
1459 
ReadFromParcelWantParamWrapper(Parcel & parcel,const std::string & key,int type,int depth)1460 bool WantParams::ReadFromParcelWantParamWrapper(Parcel &parcel, const std::string &key, int type, int depth)
1461 {
1462     if (type == VALUE_TYPE_FD) {
1463         return ReadFromParcelFD(parcel, key);
1464     }
1465 
1466     if (type == VALUE_TYPE_INVALID_FD) {
1467         ABILITYBASE_LOGE("fd invalid");
1468         return true;
1469     }
1470 
1471     if (type == VALUE_TYPE_REMOTE_OBJECT) {
1472         return ReadFromParcelRemoteObject(parcel, key);
1473     }
1474 
1475     sptr<WantParams> value(Unmarshalling(parcel, depth + 1));
1476     if (value != nullptr) {
1477         sptr<IInterface> intf = WantParamWrapper::Box(*value);
1478         if (intf) {
1479             SetParam(key, intf);
1480         }
1481     }
1482 
1483     return true;
1484 }
1485 
ReadFromParcelFD(Parcel & parcel,const std::string & key)1486 bool WantParams::ReadFromParcelFD(Parcel &parcel, const std::string &key)
1487 {
1488     auto messageParcel = static_cast<MessageParcel*>(&parcel);
1489     if (messageParcel == nullptr) {
1490         return false;
1491     }
1492     auto fd = messageParcel->ReadFileDescriptor();
1493     ABILITYBASE_LOGI("fd:%{public}d", fd);
1494     WantParams wp;
1495     wp.SetParam(TYPE_PROPERTY, String::Box(FD));
1496     wp.SetParam(VALUE_PROPERTY, Integer::Box(fd));
1497     sptr<AAFwk::IWantParams> pWantParams = AAFwk::WantParamWrapper::Box(wp);
1498     SetParam(key, pWantParams);
1499     fds_[key] = fd;
1500     return true;
1501 }
1502 
ReadFromParcelRemoteObject(Parcel & parcel,const std::string & key)1503 bool WantParams::ReadFromParcelRemoteObject(Parcel &parcel, const std::string &key)
1504 {
1505     ABILITYBASE_LOGD("called");
1506     auto messageParcel = static_cast<MessageParcel*>(&parcel);
1507     if (messageParcel == nullptr) {
1508         return false;
1509     }
1510     auto remoteObject = messageParcel->ReadRemoteObject();
1511     WantParams wp;
1512     wp.SetParam(TYPE_PROPERTY, String::Box(REMOTE_OBJECT));
1513     wp.SetParam(VALUE_PROPERTY, RemoteObjectWrap::Box(remoteObject));
1514     sptr<AAFwk::IWantParams> pWantParams = AAFwk::WantParamWrapper::Box(wp);
1515     SetParam(key, pWantParams);
1516     return true;
1517 }
1518 
ReadFromParcelLong(Parcel & parcel,const std::string & key)1519 bool WantParams::ReadFromParcelLong(Parcel &parcel, const std::string &key)
1520 {
1521     int64_t value;
1522     if (parcel.ReadInt64(value)) {
1523         std::string strValue(std::to_string(value));
1524 #ifdef WANT_PARAM_USE_LONG
1525         sptr<IInterface> intf = Long::Box(value);
1526 #else
1527         sptr<IInterface> intf = String::Box(std::to_string(value));
1528 #endif
1529         if (intf) {
1530             SetParam(key, intf);
1531         } else {
1532             ABILITYBASE_LOGE("insert param fail: key=%{public}s", key.c_str());
1533         }
1534         return true;
1535     } else {
1536         ABILITYBASE_LOGE("read data error: key:%{public}s", key.c_str());
1537         return false;
1538     }
1539 }
1540 
ReadFromParcelFloat(Parcel & parcel,const std::string & key)1541 bool WantParams::ReadFromParcelFloat(Parcel &parcel, const std::string &key)
1542 {
1543     float value;
1544     if (parcel.ReadFloat(value)) {
1545         sptr<IInterface> intf = Float::Box(value);
1546         if (intf) {
1547             SetParam(key, intf);
1548         } else {
1549             ABILITYBASE_LOGE("insert parameter fail: key=%{public}s", key.c_str());
1550         }
1551         return true;
1552     } else {
1553         ABILITYBASE_LOGE("read data fail: key=%{public}s", key.c_str());
1554         return false;
1555     }
1556 }
1557 
ReadFromParcelDouble(Parcel & parcel,const std::string & key)1558 bool WantParams::ReadFromParcelDouble(Parcel &parcel, const std::string &key)
1559 {
1560     double value;
1561     if (parcel.ReadDouble(value)) {
1562         sptr<IInterface> intf = Double::Box(value);
1563         if (intf) {
1564             SetParam(key, intf);
1565         } else {
1566             ABILITYBASE_LOGE("insert parameter fail: key:%{public}s", key.c_str());
1567         }
1568         return true;
1569     } else {
1570         ABILITYBASE_LOGE("read data fail: key=%{public}s", key.c_str());
1571         return false;
1572     }
1573 }
1574 
ReadUnsupportedData(Parcel & parcel,const std::string & key,int type)1575 bool WantParams::ReadUnsupportedData(Parcel &parcel, const std::string &key, int type)
1576 {
1577     int32_t bufferSize = 0;
1578     if (!parcel.ReadInt32(bufferSize)) {
1579         return false;
1580     }
1581     static constexpr int32_t maxAllowedSize = 100 * 1024 * 1024;
1582     if (bufferSize < 0 || bufferSize > maxAllowedSize) {
1583         ABILITYBASE_LOGE("invalid size: %{public}d", bufferSize);
1584         return false;
1585     }
1586 
1587     // Corresponding to Parcel#writeByteArray() in Java.
1588     int32_t length = 0;
1589     if (!parcel.ReadInt32(length)) {
1590         return false;
1591     }
1592     const uint8_t *bufferP = parcel.ReadUnpadBuffer(bufferSize);
1593     if (bufferP == nullptr) {
1594         return false;
1595     }
1596 
1597     UnsupportedData data;
1598     data.key = Str8ToStr16(key);
1599     data.type = type;
1600     data.size = bufferSize;
1601     data.buffer = new (std::nothrow) uint8_t[bufferSize];
1602     if (data.buffer == nullptr) {
1603         return false;
1604     }
1605 
1606     if (memcpy_s(data.buffer, bufferSize, bufferP, bufferSize) != EOK) {
1607         return false;
1608     }
1609     cachedUnsupportedData_.emplace_back(std::move(data));
1610     return true;
1611 }
1612 
ReadFromParcelParam(Parcel & parcel,const std::string & key,int type,int depth)1613 bool WantParams::ReadFromParcelParam(Parcel &parcel, const std::string &key, int type, int depth)
1614 {
1615     if (depth >= MAX_RECURSION_DEPTH) {
1616         return false;
1617     }
1618     switch (type) {
1619         case VALUE_TYPE_CHARSEQUENCE:
1620         case VALUE_TYPE_STRING:
1621             return ReadFromParcelString(parcel, key);
1622         case VALUE_TYPE_BOOLEAN:
1623             return ReadFromParcelBool(parcel, key);
1624         case VALUE_TYPE_BYTE:
1625             return ReadFromParcelInt8(parcel, key);
1626         case VALUE_TYPE_CHAR:
1627             return ReadFromParcelChar(parcel, key);
1628         case VALUE_TYPE_SHORT:
1629             return ReadFromParcelShort(parcel, key);
1630         case VALUE_TYPE_INT:
1631             return ReadFromParcelInt(parcel, key);
1632         case VALUE_TYPE_LONG:
1633             return ReadFromParcelLong(parcel, key);
1634         case VALUE_TYPE_FLOAT:
1635             return ReadFromParcelFloat(parcel, key);
1636         case VALUE_TYPE_DOUBLE:
1637             return ReadFromParcelDouble(parcel, key);
1638         case VALUE_TYPE_WANTPARAMS:
1639         case VALUE_TYPE_FD:
1640         case VALUE_TYPE_REMOTE_OBJECT:
1641             return ReadFromParcelWantParamWrapper(parcel, key, type, depth);
1642         case VALUE_TYPE_NULL:
1643             break;
1644         case VALUE_TYPE_PARCELABLE:
1645         case VALUE_TYPE_PARCELABLEARRAY:
1646         case VALUE_TYPE_SERIALIZABLE:
1647         case VALUE_TYPE_LIST:
1648             if (!ReadUnsupportedData(parcel, key, type)) {
1649                 return false;
1650             }
1651             break;
1652         default: {
1653             // handle array
1654             sptr<IArray> ao = nullptr;
1655             if (!ReadArrayToParcel(parcel, type, ao, depth)) {
1656                 return false;
1657             }
1658             sptr<IInterface> intf = ao;
1659             if (intf) {
1660                 SetParam(key, intf);
1661             }
1662             break;
1663         }
1664     }
1665     return true;
1666 }
1667 
ReadFromParcel(Parcel & parcel,int depth)1668 bool WantParams::ReadFromParcel(Parcel &parcel, int depth)
1669 {
1670     int32_t size;
1671     if (!parcel.ReadInt32(size)) {
1672         ABILITYBASE_LOGE("read size fail");
1673         return false;
1674     }
1675     for (int32_t i = 0; i < size; i++) {
1676         std::u16string key = parcel.ReadString16();
1677         int type;
1678         if (!parcel.ReadInt32(type)) {
1679             ABILITYBASE_LOGE("read type fail");
1680             return false;
1681         }
1682         if (!ReadFromParcelParam(parcel, Str16ToStr8(key), type, depth)) {
1683             ABILITYBASE_LOGE("get i=%{public}d fail", i);
1684             return false;
1685         }
1686     }
1687     return true;
1688 }
1689 
1690 /**
1691  * @description: Unmarshals an WantParams object from a Parcel.
1692  * @param Key-value pairs in the WantParams are unmarshalled separately.
1693  * @return If any key-value pair fails to be unmarshalled, false is returned.
1694  */
Unmarshalling(Parcel & parcel,int depth)1695 WantParams *WantParams::Unmarshalling(Parcel &parcel, int depth)
1696 {
1697     WantParams *wantParams = new (std::nothrow) WantParams();
1698     if (wantParams == nullptr) {
1699         return nullptr;
1700     }
1701     if (!wantParams->ReadFromParcel(parcel, depth)) {
1702         delete wantParams;
1703         wantParams = nullptr;
1704     }
1705     return wantParams;
1706 }
1707 
DumpInfo(int level) const1708 void WantParams::DumpInfo(int level) const
1709 {
1710     for (auto it : params_) {
1711         int typeId = WantParams::GetDataType(it.second);
1712         if (typeId != VALUE_TYPE_NULL) {
1713             std::string value = WantParams::GetStringByType(it.second, typeId);
1714             ABILITYBASE_LOGI("=WantParams[%{public}s]:%{private}s =======", it.first.c_str(), value.c_str());
1715         } else {
1716             ABILITYBASE_LOGE("=WantParams[%{public}s]:type error =======", it.first.c_str());
1717         }
1718     }
1719 }
1720 
CloseAllFd()1721 void WantParams::CloseAllFd()
1722 {
1723     for (auto it : fds_) {
1724         if (it.second > 0) {
1725             ABILITYBASE_LOGI("fd:%{public}d", it.second);
1726             close(it.second);
1727         }
1728         params_.erase(it.first);
1729     }
1730     fds_.clear();
1731 }
1732 
RemoveAllFd()1733 void WantParams::RemoveAllFd()
1734 {
1735     for (auto it : fds_) {
1736         params_.erase(it.first);
1737     }
1738     fds_.clear();
1739 }
1740 
DupAllFd()1741 void WantParams::DupAllFd()
1742 {
1743     for (auto it : fds_) {
1744         if (it.second > 0) {
1745             int dupFd = dup(it.second);
1746             if (dupFd > 0) {
1747                 params_.erase(it.first);
1748                 WantParams wp;
1749                 wp.SetParam(TYPE_PROPERTY, String::Box(FD));
1750                 wp.SetParam(VALUE_PROPERTY, Integer::Box(dupFd));
1751                 sptr<AAFwk::IWantParams> pWantParams = AAFwk::WantParamWrapper::Box(wp);
1752                 SetParam(it.first, pWantParams);
1753                 fds_[it.first] = dupFd;
1754             }
1755         }
1756     }
1757 }
1758 
GetCachedUnsupportedData(std::vector<UnsupportedData> & cachedUnsupportedData) const1759 void WantParams::GetCachedUnsupportedData(std::vector<UnsupportedData> &cachedUnsupportedData) const
1760 {
1761     for (UnsupportedData item : cachedUnsupportedData_) {
1762         cachedUnsupportedData.emplace_back(std::move(item));
1763     }
1764 }
1765 
SetCachedUnsupportedData(const std::vector<UnsupportedData> & cachedUnsupportedData)1766 void WantParams::SetCachedUnsupportedData(const std::vector<UnsupportedData> &cachedUnsupportedData)
1767 {
1768     cachedUnsupportedData_ = cachedUnsupportedData;
1769 }
1770 
UnwrapWantParamsNumber(const nlohmann::json & jsonObject,const std::string & key)1771 void WantParams::UnwrapWantParamsNumber(const nlohmann::json &jsonObject, const std::string &key)
1772 {
1773     int32_t natValue32 = 0;
1774     int64_t natValue64 = 0;
1775     double natValueDouble = 0.0;
1776 
1777     if (jsonObject.is_number_float()) {
1778         natValueDouble = jsonObject.get<double>();
1779         SetParam(key, Double::Box(natValueDouble));
1780     }
1781 
1782     if (!jsonObject.is_number_integer()) {
1783         return;
1784     }
1785     natValue32 = jsonObject.get<int32_t>();
1786     natValue64 = jsonObject.get<int64_t>();
1787     if (natValue32 == natValue64) {
1788         SetParam(key, Integer::Box(natValue32));
1789         return;
1790     }
1791     natValueDouble = natValue64 * 1.0;
1792     SetParam(key, Double::Box(natValueDouble));
1793 }
1794 
FromJson(const nlohmann::json & jsonObject)1795 void WantParams::FromJson(const nlohmann::json &jsonObject)
1796 {
1797     if (!jsonObject.is_object() && !jsonObject.is_array()) {
1798         ABILITYBASE_LOGE("not object or array, type name:%{public}s", jsonObject.type_name());
1799         return;
1800     }
1801     for (const auto &it : jsonObject.items()) {
1802         /* skip reserved param */
1803         if (BlackListFilter(it.key())) {
1804             ABILITYBASE_LOGD("%{public}s is filtered.", it.key().c_str());
1805             continue;
1806         }
1807         if (it.value().is_string()) {
1808             std::string natValue = it.value().get<std::string>();
1809             SetParam(it.key(), String::Box(natValue));
1810             continue;
1811         }
1812         if (it.value().is_boolean()) {
1813             bool natValue = it.value().get<bool>();
1814             SetParam(it.key(), Boolean::Box(natValue));
1815             continue;
1816         }
1817         if (it.value().is_number()) {
1818             UnwrapWantParamsNumber(it.value(), it.key());
1819             continue;
1820         }
1821         if (it.value().is_array()) {
1822             sptr<IArray> ao = HandleArrayFromJson(it.value());
1823             SetParam(it.key(), ao);
1824             continue;
1825         }
1826         if (it.value().is_object()) {
1827             auto wp = it.value().get<WantParams>();
1828             sptr<IWantParams> pWantParams = WantParamWrapper::Box(wp);
1829             if (pWantParams != nullptr) {
1830                 SetParam(it.key(), pWantParams);
1831             }
1832         }
1833     }
1834     if (jsonObject.is_array()) {
1835         // Consistent with napi behavior
1836         SetParam("length", Integer::Box(jsonObject.size()));
1837     }
1838 }
1839 
InnerWrapWantParamsByte(nlohmann::json & jsObject,const std::string & key) const1840 void WantParams::InnerWrapWantParamsByte(nlohmann::json &jsObject, const std::string &key) const
1841 {
1842     auto value = GetParam(key);
1843     IByte *bo = IByte::Query(value);
1844     if (bo == nullptr) {
1845         return;
1846     }
1847 
1848     int intValue = (int)Byte::Unbox(bo);
1849     jsObject[key] = intValue;
1850 }
1851 
InnerWrapWantParamsChar(nlohmann::json & jsObject,const std::string & key) const1852 void WantParams::InnerWrapWantParamsChar(nlohmann::json &jsObject, const std::string &key) const
1853 {
1854     auto value = GetParam(key);
1855     IChar *ao = IChar::Query(value);
1856     if (ao == nullptr) {
1857         return;
1858     }
1859 
1860     std::string natValue(static_cast<Char *>(ao)->ToString());
1861     jsObject[key] = natValue;
1862 }
1863 
InnerWrapWantParamsShort(nlohmann::json & jsObject,const std::string & key) const1864 void WantParams::InnerWrapWantParamsShort(nlohmann::json &jsObject, const std::string &key) const
1865 {
1866     auto value = GetParam(key);
1867     IShort *ao = IShort::Query(value);
1868     if (ao == nullptr) {
1869         return;
1870     }
1871 
1872     short natValue = Short::Unbox(ao);
1873     jsObject[key] = natValue;
1874 }
1875 
InnerWrapWantParamsBool(nlohmann::json & jsObject,const std::string & key) const1876 void WantParams::InnerWrapWantParamsBool(nlohmann::json &jsObject, const std::string &key) const
1877 {
1878     auto value = GetParam(key);
1879     IBoolean *bo = IBoolean::Query(value);
1880     if (bo == nullptr) {
1881         return;
1882     }
1883 
1884     bool natValue = Boolean::Unbox(bo);
1885     jsObject[key] = natValue;
1886 }
1887 
InnerWrapWantParamsString(nlohmann::json & jsObject,const std::string & key) const1888 void WantParams::InnerWrapWantParamsString(nlohmann::json &jsObject, const std::string &key) const
1889 {
1890     auto value = GetParam(key);
1891     IString *ao = IString::Query(value);
1892     if (ao == nullptr) {
1893         return;
1894     }
1895 
1896     std::string natValue = String::Unbox(ao);
1897     jsObject[key] = natValue;
1898 }
1899 
InnerWrapWantParamsInt32(nlohmann::json & jsObject,const std::string & key) const1900 void WantParams::InnerWrapWantParamsInt32(nlohmann::json &jsObject, const std::string &key) const
1901 {
1902     auto value = GetParam(key);
1903     IInteger *ao = IInteger::Query(value);
1904     if (ao == nullptr) {
1905         return;
1906     }
1907 
1908     int natValue = Integer::Unbox(ao);
1909     jsObject[key] = natValue;
1910 }
1911 
InnerWrapWantParamsInt64(nlohmann::json & jsObject,const std::string & key) const1912 void WantParams::InnerWrapWantParamsInt64(nlohmann::json &jsObject, const std::string &key) const
1913 {
1914     auto value = GetParam(key);
1915     ILong *ao = ILong::Query(value);
1916     if (ao == nullptr) {
1917         return;
1918     }
1919 
1920     int64_t natValue = Long::Unbox(ao);
1921     jsObject[key] = natValue;
1922 }
1923 
InnerWrapWantParamsFloat(nlohmann::json & jsObject,const std::string & key) const1924 void WantParams::InnerWrapWantParamsFloat(nlohmann::json &jsObject, const std::string &key) const
1925 {
1926     auto value = GetParam(key);
1927     IFloat *ao = IFloat::Query(value);
1928     if (ao == nullptr) {
1929         return;
1930     }
1931 
1932     float natValue = Float::Unbox(ao);
1933     jsObject[key] = natValue;
1934 }
1935 
InnerWrapWantParamsDouble(nlohmann::json & jsObject,const std::string & key) const1936 void WantParams::InnerWrapWantParamsDouble(nlohmann::json &jsObject, const std::string &key) const
1937 {
1938     auto value = GetParam(key);
1939     IDouble *ao = IDouble::Query(value);
1940     if (ao == nullptr) {
1941         return;
1942     }
1943 
1944     double natValue = Double::Unbox(ao);
1945     jsObject[key] = natValue;
1946 }
1947 
InnerWrapWantParamsWantParams(nlohmann::json & jsObject,const std::string & key) const1948 void WantParams::InnerWrapWantParamsWantParams(nlohmann::json &jsObject, const std::string &key) const
1949 {
1950     auto value = GetParam(key);
1951     IWantParams *o = IWantParams::Query(value);
1952     if (o == nullptr) {
1953         return;
1954     }
1955 
1956     WantParams wp = WantParamWrapper::Unbox(o);
1957     jsObject[key] = wp;
1958 }
1959 
InnerWrapWantParamsArrayString(nlohmann::json & jsObject,const std::string & key,sptr<IArray> & ao) const1960 void WantParams::InnerWrapWantParamsArrayString(
1961     nlohmann::json &jsObject, const std::string &key, sptr<IArray> &ao) const
1962 {
1963     long size = 0;
1964     if (ao->GetLength(size) != ERR_OK) {
1965         return;
1966     }
1967 
1968     std::vector<std::string> natArray;
1969     for (long i = 0; i < size; i++) {
1970         sptr<IInterface> iface = nullptr;
1971         if (ao->Get(i, iface) == ERR_OK) {
1972             IString *iValue = IString::Query(iface);
1973             if (iValue != nullptr) {
1974                 natArray.push_back(String::Unbox(iValue));
1975             }
1976         }
1977     }
1978     jsObject[key] = natArray;
1979 }
1980 
InnerWrapWantParamsArrayBool(nlohmann::json & jsObject,const std::string & key,sptr<IArray> & ao) const1981 void WantParams::InnerWrapWantParamsArrayBool(nlohmann::json &jsObject, const std::string &key, sptr<IArray> &ao) const
1982 {
1983     long size = 0;
1984     if (ao->GetLength(size) != ERR_OK) {
1985         return;
1986     }
1987 
1988     std::vector<bool> natArray;
1989     for (long i = 0; i < size; i++) {
1990         sptr<IInterface> iface = nullptr;
1991         if (ao->Get(i, iface) == ERR_OK) {
1992             IBoolean *iValue = IBoolean::Query(iface);
1993             if (iValue != nullptr) {
1994                 natArray.push_back(Boolean::Unbox(iValue));
1995             }
1996         }
1997     }
1998     jsObject[key] = natArray;
1999 }
2000 
InnerWrapWantParamsArrayShort(nlohmann::json & jsObject,const std::string & key,sptr<IArray> & ao) const2001 void WantParams::InnerWrapWantParamsArrayShort(nlohmann::json &jsObject, const std::string &key, sptr<IArray> &ao) const
2002 {
2003     long size = 0;
2004     if (ao->GetLength(size) != ERR_OK) {
2005         return;
2006     }
2007 
2008     std::vector<int> natArray;
2009     for (long i = 0; i < size; i++) {
2010         sptr<IInterface> iface = nullptr;
2011         if (ao->Get(i, iface) == ERR_OK) {
2012             IShort *iValue = IShort::Query(iface);
2013             if (iValue != nullptr) {
2014                 natArray.push_back(Short::Unbox(iValue));
2015             }
2016         }
2017     }
2018     jsObject[key] = natArray;
2019 }
2020 
InnerWrapWantParamsArrayByte(nlohmann::json & jsObject,const std::string & key,sptr<IArray> & ao) const2021 void WantParams::InnerWrapWantParamsArrayByte(nlohmann::json &jsObject, const std::string &key, sptr<IArray> &ao) const
2022 {
2023     long size = 0;
2024     if (ao->GetLength(size) != ERR_OK) {
2025         return;
2026     }
2027 
2028     std::vector<int> natArray;
2029     for (long i = 0; i < size; i++) {
2030         sptr<IInterface> iface = nullptr;
2031         if (ao->Get(i, iface) == ERR_OK) {
2032             IByte *iValue = IByte::Query(iface);
2033             if (iValue != nullptr) {
2034                 int intValue = (int)Byte::Unbox(iValue);
2035                 natArray.push_back(intValue);
2036             }
2037         }
2038     }
2039     jsObject[key] = natArray;
2040 }
2041 
InnerWrapWantParamsArrayInt32(nlohmann::json & jsObject,const std::string & key,sptr<IArray> & ao) const2042 void WantParams::InnerWrapWantParamsArrayInt32(nlohmann::json &jsObject, const std::string &key, sptr<IArray> &ao) const
2043 {
2044     long size = 0;
2045     if (ao->GetLength(size) != ERR_OK) {
2046         return;
2047     }
2048 
2049     std::vector<int> natArray;
2050     for (long i = 0; i < size; i++) {
2051         sptr<IInterface> iface = nullptr;
2052         if (ao->Get(i, iface) == ERR_OK) {
2053             IInteger *iValue = IInteger::Query(iface);
2054             if (iValue != nullptr) {
2055                 natArray.push_back(Integer::Unbox(iValue));
2056             }
2057         }
2058     }
2059     jsObject[key] = natArray;
2060 }
2061 
InnerWrapWantParamsArrayInt64(nlohmann::json & jsObject,const std::string & key,sptr<IArray> & ao) const2062 void WantParams::InnerWrapWantParamsArrayInt64(nlohmann::json &jsObject, const std::string &key, sptr<IArray> &ao) const
2063 {
2064     long size = 0;
2065     if (ao->GetLength(size) != ERR_OK) {
2066         return;
2067     }
2068 
2069     std::vector<int64_t> natArray;
2070     for (long i = 0; i < size; i++) {
2071         sptr<IInterface> iface = nullptr;
2072         if (ao->Get(i, iface) == ERR_OK) {
2073             ILong *iValue = ILong::Query(iface);
2074             if (iValue != nullptr) {
2075                 natArray.push_back(Long::Unbox(iValue));
2076             }
2077         }
2078     }
2079     jsObject[key] = natArray;
2080 }
2081 
InnerWrapWantParamsArrayFloat(nlohmann::json & jsObject,const std::string & key,sptr<IArray> & ao) const2082 void WantParams::InnerWrapWantParamsArrayFloat(nlohmann::json &jsObject, const std::string &key, sptr<IArray> &ao) const
2083 {
2084     long size = 0;
2085     if (ao->GetLength(size) != ERR_OK) {
2086         return;
2087     }
2088 
2089     std::vector<double> natArray;
2090     for (long i = 0; i < size; i++) {
2091         sptr<IInterface> iface = nullptr;
2092         if (ao->Get(i, iface) == ERR_OK) {
2093             IFloat *iValue = IFloat::Query(iface);
2094             if (iValue != nullptr) {
2095                 natArray.push_back(Float::Unbox(iValue));
2096             }
2097         }
2098     }
2099     jsObject[key] = natArray;
2100 }
2101 
InnerWrapWantParamsArrayWantParams(nlohmann::json & jsObject,const std::string & key,sptr<IArray> & ao) const2102 void WantParams::InnerWrapWantParamsArrayWantParams(
2103     nlohmann::json &jsObject, const std::string &key, sptr<IArray> &ao) const
2104 {
2105     long size = 0;
2106     if (ao->GetLength(size) != ERR_OK) {
2107         return;
2108     }
2109 
2110     std::vector<WantParams> natArray;
2111     for (long i = 0; i < size; i++) {
2112         sptr<IInterface> iface = nullptr;
2113         if (ao->Get(i, iface) == ERR_OK) {
2114             IWantParams *iValue = IWantParams::Query(iface);
2115             if (iValue != nullptr) {
2116                 natArray.push_back(WantParamWrapper::Unbox(iValue));
2117             }
2118         }
2119     }
2120     jsObject[key] = natArray;
2121 }
2122 
InnerWrapWantParamsArrayChar(nlohmann::json & jsObject,const std::string & key,sptr<AAFwk::IArray> & ao) const2123 void WantParams::InnerWrapWantParamsArrayChar(
2124     nlohmann::json &jsObject, const std::string &key, sptr<AAFwk::IArray> &ao) const
2125 {
2126     long size = 0;
2127     if (ao->GetLength(size) != ERR_OK) {
2128         return;
2129     }
2130 
2131     std::vector<std::string> natArray;
2132     for (long i = 0; i < size; i++) {
2133         sptr<AAFwk::IInterface> iface = nullptr;
2134         if (ao->Get(i, iface) == ERR_OK) {
2135             AAFwk::IChar *iValue = AAFwk::IChar::Query(iface);
2136             if (iValue != nullptr) {
2137                 std::string str(static_cast<Char *>(iValue)->ToString());
2138                 natArray.push_back(str);
2139             }
2140         }
2141     }
2142     jsObject[key] = natArray;
2143 }
2144 
InnerWrapWantParamsArrayDouble(nlohmann::json & jsObject,const std::string & key,sptr<AAFwk::IArray> & ao) const2145 void WantParams::InnerWrapWantParamsArrayDouble(
2146     nlohmann::json &jsObject, const std::string &key, sptr<AAFwk::IArray> &ao) const
2147 {
2148     long size = 0;
2149     if (ao->GetLength(size) != ERR_OK) {
2150         return;
2151     }
2152 
2153     std::vector<double> natArray;
2154     for (long i = 0; i < size; i++) {
2155         sptr<AAFwk::IInterface> iface = nullptr;
2156         if (ao->Get(i, iface) == ERR_OK) {
2157             AAFwk::IDouble *iValue = AAFwk::IDouble::Query(iface);
2158             if (iValue != nullptr) {
2159                 natArray.push_back(AAFwk::Double::Unbox(iValue));
2160             }
2161         }
2162     }
2163     jsObject[key] = natArray;
2164 }
2165 
InnerWrapWantParamsArray(nlohmann::json & jsObject,const std::string & key,sptr<AAFwk::IArray> & ao) const2166 void WantParams::InnerWrapWantParamsArray(
2167     nlohmann::json &jsObject, const std::string &key, sptr<AAFwk::IArray> &ao) const
2168 {
2169     if (Array::IsStringArray(ao)) {
2170         return InnerWrapWantParamsArrayString(jsObject, key, ao);
2171     } else if (Array::IsBooleanArray(ao)) {
2172         return InnerWrapWantParamsArrayBool(jsObject, key, ao);
2173     } else if (Array::IsShortArray(ao)) {
2174         return InnerWrapWantParamsArrayShort(jsObject, key, ao);
2175     } else if (Array::IsIntegerArray(ao)) {
2176         return InnerWrapWantParamsArrayInt32(jsObject, key, ao);
2177     } else if (Array::IsLongArray(ao)) {
2178         return InnerWrapWantParamsArrayInt64(jsObject, key, ao);
2179     } else if (Array::IsFloatArray(ao)) {
2180         return InnerWrapWantParamsArrayFloat(jsObject, key, ao);
2181     } else if (Array::IsByteArray(ao)) {
2182         return InnerWrapWantParamsArrayByte(jsObject, key, ao);
2183     } else if (Array::IsCharArray(ao)) {
2184         return InnerWrapWantParamsArrayChar(jsObject, key, ao);
2185     } else if (Array::IsDoubleArray(ao)) {
2186         return InnerWrapWantParamsArrayDouble(jsObject, key, ao);
2187     } else if (Array::IsWantParamsArray(ao)) {
2188         return InnerWrapWantParamsArrayWantParams(jsObject, key, ao);
2189     }
2190 }
2191 
ToJson(nlohmann::json & jsObject) const2192 void WantParams::ToJson(nlohmann::json &jsObject) const
2193 {
2194     const std::map<std::string, sptr<IInterface>> paramList = GetParams();
2195     for (auto iter = paramList.begin(); iter != paramList.end(); iter++) {
2196         if (IString::Query(iter->second) != nullptr) {
2197             InnerWrapWantParamsString(jsObject, iter->first);
2198         } else if (IBoolean::Query(iter->second) != nullptr) {
2199             InnerWrapWantParamsBool(jsObject, iter->first);
2200         } else if (IShort::Query(iter->second) != nullptr) {
2201             InnerWrapWantParamsShort(jsObject, iter->first);
2202         } else if (IInteger::Query(iter->second) != nullptr) {
2203             InnerWrapWantParamsInt32(jsObject, iter->first);
2204         } else if (ILong::Query(iter->second) != nullptr) {
2205             InnerWrapWantParamsInt64(jsObject, iter->first);
2206         } else if (IFloat::Query(iter->second) != nullptr) {
2207             InnerWrapWantParamsFloat(jsObject, iter->first);
2208         } else if (IDouble::Query(iter->second) != nullptr) {
2209             InnerWrapWantParamsDouble(jsObject, iter->first);
2210         } else if (IChar::Query(iter->second) != nullptr) {
2211             InnerWrapWantParamsChar(jsObject, iter->first);
2212         } else if (IByte::Query(iter->second) != nullptr) {
2213             InnerWrapWantParamsByte(jsObject, iter->first);
2214         } else if (IArray::Query(iter->second) != nullptr) {
2215             IArray *ao = IArray::Query(iter->second);
2216             if (ao != nullptr) {
2217                 sptr<IArray> array(ao);
2218                 InnerWrapWantParamsArray(jsObject, iter->first, array);
2219             }
2220         } else if (IWantParams::Query(iter->second) != nullptr) {
2221             InnerWrapWantParamsWantParams(jsObject, iter->first);
2222         }
2223     }
2224 }
2225 
from_json(const nlohmann::json & jsonObject,WantParams & wantParams)2226 void from_json(const nlohmann::json &jsonObject, WantParams &wantParams)
2227 {
2228     wantParams.FromJson(jsonObject);
2229 }
2230 
to_json(nlohmann::json & jsonObject,const WantParams & wantParams)2231 void to_json(nlohmann::json &jsonObject, const WantParams &wantParams)
2232 {
2233     wantParams.ToJson(jsonObject);
2234 }
2235 }  // namespace AAFwk
2236 }  // namespace OHOS
2237