1 /*
2 * Copyright (c) 2024 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 <securec.h>
17 #include "vendor_helper.h"
18 #include "print_service_converter.h"
19 #include "print_log.h"
20 #include <json/json.h>
21 #include "print_json_util.h"
22
23 namespace {
24 const std::string VENDOR_MANAGER_PREFIX = "fwk.";
25 const std::string GLOBAL_ID_DELIMITER = ":";
26 const uint32_t ORIENTATION_OFFSET = 3;
27 const int NUMBER_BASE = 10;
28 const size_t MAX_STRING_COUNT = 1000;
29 const uint32_t MAX_MEDIA_TYPE_SIZE = 200;
30 }
31
32 namespace OHOS::Print {
33
CopyString(const std::string & source)34 char *CopyString(const std::string &source)
35 {
36 auto len = source.length();
37 char *dest = new (std::nothrow) char[len + 1];
38 if (dest == nullptr) {
39 PRINT_HILOGW("allocate failed");
40 return nullptr;
41 }
42 if (strcpy_s(dest, len + 1, source.c_str()) != 0) {
43 PRINT_HILOGW("CopyString strcpy_s failed");
44 }
45 dest[len] = '\0';
46 return dest;
47 }
48
49 template <typename T1, typename T2>
ConvertArrayToList(const T1 * array,uint32_t count,std::vector<T2> & list,bool (* convertType)(const T1 &,T2 &))50 bool ConvertArrayToList(const T1 *array, uint32_t count, std::vector<T2> &list, bool (*convertType)(const T1 &, T2 &))
51 {
52 if (convertType == nullptr) {
53 PRINT_HILOGW("convertType is null");
54 return false;
55 }
56 if (count == 0) {
57 return true;
58 }
59 if (array == nullptr) {
60 PRINT_HILOGW("array is null");
61 return false;
62 }
63 for (uint32_t i = 0; i < count; ++i) {
64 T2 data;
65 if (convertType(array[i], data)) {
66 if (std::find(list.begin(), list.end(), data) != list.end()) {
67 PRINT_HILOGW("ignore the same item");
68 continue;
69 }
70 list.push_back(data);
71 }
72 }
73 return true;
74 }
75
76 template <typename T>
ConvertArrayToJson(const T * array,uint32_t count,bool (* convertToJson)(const T &,Json::Value &))77 std::string ConvertArrayToJson(const T *array, uint32_t count, bool (*convertToJson)(const T &, Json::Value &))
78 {
79 if (array == nullptr || convertToJson == nullptr) {
80 PRINT_HILOGW("invalid params");
81 return "";
82 }
83 std::vector<T> list;
84 for (uint32_t i = 0; i < count; ++i) {
85 AddToUniqueList<T>(list, array[i]);
86 }
87 return ConvertListToJson<T>(list, convertToJson);
88 }
89
ConvertJsonToStringList(const std::string & jsonString,std::vector<std::string> & list)90 bool ConvertJsonToStringList(const std::string &jsonString, std::vector<std::string> &list)
91 {
92 Json::Value jsonObject;
93 if (!PrintJsonUtil::Parse(jsonString, jsonObject)) {
94 PRINT_HILOGW("invalid jsonString");
95 return false;
96 }
97 if (!jsonObject.isArray()) {
98 PRINT_HILOGW("jsonObject is not array");
99 return false;
100 }
101 uint32_t jsonSize = jsonObject.size();
102 if (jsonSize > MAX_MEDIA_TYPE_SIZE) {
103 PRINT_HILOGE("jsonObject size is illegal.");
104 return false;
105 }
106 for (uint32_t i = 0; i < jsonSize; i++) {
107 if (jsonObject[i].isString()) {
108 list.push_back(jsonObject[i].asString());
109 }
110 }
111 return true;
112 }
113
GetStringValueFromJson(const Json::Value & jsonObject,const std::string & key)114 std::string GetStringValueFromJson(const Json::Value &jsonObject, const std::string &key)
115 {
116 if (!PrintJsonUtil::IsMember(jsonObject, key) || !jsonObject[key].isString()) {
117 PRINT_HILOGW("can not find %{public}s", key.c_str());
118 return "";
119 }
120 return jsonObject[key].asString();
121 }
122
ConvertStringToLong(const char * src,long & dst)123 bool ConvertStringToLong(const char *src, long &dst)
124 {
125 if (src == nullptr) {
126 return false;
127 }
128 errno = 0;
129 char *endPtr = nullptr;
130 dst = strtol(src, &endPtr, NUMBER_BASE);
131 if (errno == ERANGE || endPtr == src) {
132 PRINT_HILOGW("ConvertStringToLong fail: %{public}s", src);
133 return false;
134 }
135 return true;
136 }
137
ConvertColorMode(const Print_ColorMode & code,uint32_t & dst)138 bool ConvertColorMode(const Print_ColorMode &code, uint32_t &dst)
139 {
140 dst = static_cast<uint32_t>(code);
141 if (dst > static_cast<uint32_t>(COLOR_MODE_AUTO)) {
142 return false;
143 }
144 return true;
145 }
ConvertColorModeToJson(const Print_ColorMode & code,Json::Value & jsonObject)146 bool ConvertColorModeToJson(const Print_ColorMode &code, Json::Value &jsonObject)
147 {
148 jsonObject["color"] = std::to_string(static_cast<int>(code));
149 return true;
150 }
151
ConvertDuplexMode(const Print_DuplexMode & code,uint32_t & dst)152 bool ConvertDuplexMode(const Print_DuplexMode &code, uint32_t &dst)
153 {
154 dst = static_cast<uint32_t>(code);
155 if (dst > static_cast<uint32_t>(DUPLEX_MODE_TWO_SIDED_SHORT_EDGE)) {
156 return false;
157 }
158 return true;
159 }
ConvertDuplexModeToJson(const Print_DuplexMode & code,Json::Value & jsonObject)160 bool ConvertDuplexModeToJson(const Print_DuplexMode &code, Json::Value &jsonObject)
161 {
162 jsonObject["duplex"] = std::to_string(static_cast<int>(code));
163 return true;
164 }
165
ConvertQuality(const Print_Quality & code,uint32_t & dst)166 bool ConvertQuality(const Print_Quality &code, uint32_t &dst)
167 {
168 dst = static_cast<uint32_t>(code);
169 if (dst < static_cast<uint32_t>(PRINT_QUALITY_DRAFT) || dst > static_cast<uint32_t>(PRINT_QUALITY_HIGH)) {
170 return false;
171 }
172 return true;
173 }
ConvertQualityToJson(const Print_Quality & code,Json::Value & jsonObject)174 bool ConvertQualityToJson(const Print_Quality &code, Json::Value &jsonObject)
175 {
176 jsonObject["quality"] = std::to_string(static_cast<int>(code));
177 return true;
178 }
179
ConvertStringToPrinterState(const std::string & stateData,Print_PrinterState & state)180 bool ConvertStringToPrinterState(const std::string &stateData, Print_PrinterState &state)
181 {
182 long result = 0;
183 Json::Value jsonObject;
184 if (!PrintJsonUtil::Parse(stateData, jsonObject)) {
185 PRINT_HILOGW("invalid stateData");
186 return false;
187 }
188 // 参数处理
189 std::string stateValue = GetStringValueFromJson(jsonObject, "state");
190 if (!ConvertStringToLong(stateValue.c_str(), result)) {
191 return false;
192 }
193 std::string reasonValue = GetStringValueFromJson(jsonObject, "reason");
194 if (reasonValue == "shutdown") {
195 PRINT_HILOGD("printer shutdown");
196 state = PRINTER_UNAVAILABLE;
197 return true;
198 }
199 if (result < 0 || result > PRINTER_UNAVAILABLE + 1) {
200 PRINT_HILOGW("invalid state");
201 return false;
202 }
203 if (result == PRINTER_UNAVAILABLE + 1) {
204 state = PRINTER_UNAVAILABLE;
205 } else if (result == 1) {
206 state = PRINTER_BUSY;
207 } else {
208 state = PRINTER_IDLE;
209 }
210 return true;
211 }
212
LogDiscoveryItem(const Print_DiscoveryItem * discoveryItem)213 void LogDiscoveryItem(const Print_DiscoveryItem *discoveryItem)
214 {
215 if (discoveryItem == nullptr) {
216 PRINT_HILOGW("discoveryItem is null");
217 return;
218 }
219 if (discoveryItem->printerId != nullptr) {
220 PRINT_HILOGD("printerId: %{public}s", discoveryItem->printerId);
221 } else {
222 PRINT_HILOGW("printerId is null");
223 }
224 if (discoveryItem->printerName != nullptr) {
225 PRINT_HILOGD("printerName: %{public}s", discoveryItem->printerName);
226 } else {
227 PRINT_HILOGW("printerName is null");
228 }
229 if (discoveryItem->description != nullptr) {
230 PRINT_HILOGD("description: %{public}s", discoveryItem->description);
231 }
232 if (discoveryItem->location != nullptr) {
233 PRINT_HILOGD("location: %{public}s", discoveryItem->location);
234 }
235 if (discoveryItem->makeAndModel != nullptr) {
236 PRINT_HILOGD("makeAndModel: %{public}s", discoveryItem->makeAndModel);
237 } else {
238 PRINT_HILOGW("makeAndModel is null");
239 }
240 if (discoveryItem->printerUri != nullptr) {
241 PRINT_HILOGD("printerUri: %{public}s", discoveryItem->printerUri);
242 } else {
243 PRINT_HILOGW("printerUri is null");
244 }
245 if (discoveryItem->printerUuid != nullptr) {
246 PRINT_HILOGD("printerUuid: %{public}s", discoveryItem->printerUuid);
247 }
248 }
249
LogPageCapability(const Print_PrinterCapability * capability)250 void LogPageCapability(const Print_PrinterCapability *capability)
251 {
252 if (capability == nullptr) {
253 PRINT_HILOGW("capability is null");
254 return;
255 }
256 if (capability->supportedPageSizes != nullptr && capability->supportedPageSizesCount > 0) {
257 for (uint32_t i = 0; i < capability->supportedPageSizesCount; ++i) {
258 if (capability->supportedPageSizes[i].id != nullptr) {
259 PRINT_HILOGD("page id = %{public}s", capability->supportedPageSizes[i].id);
260 }
261 if (capability->supportedPageSizes[i].name != nullptr) {
262 PRINT_HILOGD("page name = %{public}s", capability->supportedPageSizes[i].name);
263 }
264 PRINT_HILOGD("page size = %{public}u x %{public}u", capability->supportedPageSizes[i].width,
265 capability->supportedPageSizes[i].height);
266 }
267 }
268 if (capability->supportedMediaTypes != nullptr) {
269 PRINT_HILOGD("media types = %{public}s", capability->supportedMediaTypes);
270 }
271 if (capability->supportedPaperSources != nullptr) {
272 PRINT_HILOGD("Paper Sources = %{public}s", capability->supportedPaperSources);
273 }
274 }
275
LogOtherCapability(const Print_PrinterCapability * capability)276 void LogOtherCapability(const Print_PrinterCapability *capability)
277 {
278 if (capability == nullptr) {
279 PRINT_HILOGW("capability is null");
280 return;
281 }
282 if (capability->supportedColorModes != nullptr && capability->supportedColorModesCount > 0) {
283 for (uint32_t i = 0; i < capability->supportedColorModesCount; ++i) {
284 PRINT_HILOGD("color mode = %{public}u", static_cast<uint32_t>(capability->supportedColorModes[i]));
285 }
286 }
287 if (capability->supportedDuplexModes != nullptr && capability->supportedDuplexModesCount > 0) {
288 for (uint32_t i = 0; i < capability->supportedDuplexModesCount; ++i) {
289 PRINT_HILOGD("duplex mode = %{public}u", static_cast<uint32_t>(capability->supportedDuplexModes[i]));
290 }
291 }
292 if (capability->supportedQualities != nullptr && capability->supportedQualitiesCount > 0) {
293 for (uint32_t i = 0; i < capability->supportedQualitiesCount; ++i) {
294 PRINT_HILOGD("quality mode = %{public}u", static_cast<uint32_t>(capability->supportedQualities[i]));
295 }
296 }
297 PRINT_HILOGD("copy count = %{public}u", capability->supportedCopies);
298 if (capability->supportedResolutions != nullptr && capability->supportedResolutionsCount > 0) {
299 for (uint32_t i = 0; i < capability->supportedResolutionsCount; ++i) {
300 PRINT_HILOGD("dpi = %{public}u x %{public}u", capability->supportedResolutions[i].horizontalDpi,
301 capability->supportedResolutions[i].verticalDpi);
302 }
303 }
304 if (capability->supportedOrientations != nullptr && capability->supportedOrientationsCount > 0) {
305 for (uint32_t i = 0; i < capability->supportedOrientationsCount; ++i) {
306 PRINT_HILOGD("Orientation = %{public}u", static_cast<uint32_t>(capability->supportedOrientations[i]));
307 }
308 }
309 if (capability->advancedCapability != nullptr) {
310 PRINT_HILOGD("advancedCapability = %{public}s", capability->advancedCapability);
311 }
312 }
313
LogDefaultValue(const Print_DefaultValue * defaultValue)314 void LogDefaultValue(const Print_DefaultValue *defaultValue)
315 {
316 if (defaultValue == nullptr) {
317 PRINT_HILOGW("defaultValue is null");
318 return;
319 }
320 PRINT_HILOGD("default color mode = %{public}u", static_cast<uint32_t>(defaultValue->defaultColorMode));
321 PRINT_HILOGD("default duplex mode = %{public}u", static_cast<uint32_t>(defaultValue->defaultDuplexMode));
322 if (defaultValue->defaultMediaType != nullptr) {
323 PRINT_HILOGD("defaultMediaType = %{public}s", defaultValue->defaultMediaType);
324 }
325 if (defaultValue->defaultPageSizeId != nullptr) {
326 PRINT_HILOGD("defaultPageSizeId = %{public}s", defaultValue->defaultPageSizeId);
327 }
328 PRINT_HILOGD("defaultMargin = [%{public}u, %{public}u, %{public}u, %{public}u]",
329 defaultValue->defaultMargin.leftMargin, defaultValue->defaultMargin.topMargin,
330 defaultValue->defaultMargin.rightMargin, defaultValue->defaultMargin.bottomMargin);
331 if (defaultValue->defaultPaperSource != nullptr) {
332 PRINT_HILOGD("defaultPaperSource = %{public}s", defaultValue->defaultPaperSource);
333 }
334 PRINT_HILOGD("defaultPrintQuality = %{public}u", static_cast<uint32_t>(defaultValue->defaultPrintQuality));
335 PRINT_HILOGD("defaultCopies = %{public}u", defaultValue->defaultCopies);
336 PRINT_HILOGD("defaultResolution = %{public}u x %{public}u", defaultValue->defaultResolution.horizontalDpi,
337 defaultValue->defaultResolution.verticalDpi);
338 PRINT_HILOGD("defaultOrientation = %{public}u", static_cast<uint32_t>(defaultValue->defaultOrientation));
339 if (defaultValue->otherDefaultValues != nullptr) {
340 PRINT_HILOGD("otherDefaultValues = %{public}s", defaultValue->otherDefaultValues);
341 }
342 }
343
LogProperties(const Print_PropertyList * propertyList)344 void LogProperties(const Print_PropertyList *propertyList)
345 {
346 if (propertyList == nullptr) {
347 PRINT_HILOGW("propertyList is null");
348 return;
349 }
350 if (propertyList->count == 0 || propertyList->list == nullptr) {
351 PRINT_HILOGW("propertyList empty");
352 return;
353 }
354 for (uint32_t i = 0; i < propertyList->count; ++i) {
355 if (propertyList->list[i].key == nullptr) {
356 PRINT_HILOGW("propertyList item empty: %{public}u", i);
357 continue;
358 }
359 PRINT_HILOGD("LogProperties key: %{public}s", propertyList->list[i].key);
360 if (propertyList->list[i].value == nullptr) {
361 PRINT_HILOGW("propertyList value empty: %{public}u", i);
362 continue;
363 }
364 PRINT_HILOGD("LogProperties value: %{public}s", propertyList->list[i].value);
365 }
366 }
367
FindPropertyFromPropertyList(const Print_PropertyList * propertyList,const std::string & keyName)368 std::shared_ptr<std::string> FindPropertyFromPropertyList(const Print_PropertyList *propertyList,
369 const std::string &keyName)
370 {
371 if (propertyList == nullptr) {
372 PRINT_HILOGW("propertyList is null");
373 return nullptr;
374 }
375 if (propertyList->count == 0 || propertyList->list == nullptr) {
376 PRINT_HILOGW("propertyList empty");
377 return nullptr;
378 }
379 for (uint32_t i = 0; i < propertyList->count; ++i) {
380 if (propertyList->list[i].key == nullptr) {
381 PRINT_HILOGW("propertyList key empty: %{public}u", i);
382 continue;
383 }
384 PRINT_HILOGD("FindPropertyFromPropertyList key: %{public}s", propertyList->list[i].key);
385 if (strcmp(keyName.c_str(), propertyList->list[i].key) != 0) {
386 continue;
387 }
388 if (propertyList->list[i].value == nullptr) {
389 PRINT_HILOGW("propertyList value empty, key: %{public}s", keyName.c_str());
390 break;
391 }
392 PRINT_HILOGD("FindPropertyFromPropertyList value: %{public}s", propertyList->list[i].value);
393 return std::make_shared<std::string>(propertyList->list[i].value);
394 }
395 return nullptr;
396 }
UpdatePrinterInfoWithDiscovery(PrinterInfo & info,const Print_DiscoveryItem * discoveryItem)397 bool UpdatePrinterInfoWithDiscovery(PrinterInfo &info, const Print_DiscoveryItem *discoveryItem)
398 {
399 if (discoveryItem == nullptr) {
400 PRINT_HILOGW("discoveryItem is null");
401 return false;
402 }
403 if (discoveryItem->printerId == nullptr || discoveryItem->printerName == nullptr) {
404 PRINT_HILOGW("invalid discoveryItem");
405 return false;
406 }
407 info.SetPrinterId(std::string(discoveryItem->printerId));
408 std::string name(discoveryItem->printerName);
409 info.SetPrinterName(name);
410 if (discoveryItem->description != nullptr) {
411 info.SetDescription(std::string(discoveryItem->description));
412 }
413 if (discoveryItem->printerUri != nullptr) {
414 info.SetUri(std::string(discoveryItem->printerUri));
415 }
416 if (discoveryItem->makeAndModel != nullptr) {
417 info.SetPrinterMake(std::string(discoveryItem->makeAndModel));
418 }
419 if (discoveryItem->printerUuid != nullptr) {
420 info.SetPrinterUuid(std::string(discoveryItem->printerUuid));
421 }
422 if (discoveryItem->printerUri != nullptr && discoveryItem->makeAndModel != nullptr) {
423 PRINT_HILOGD("printerUri: %{public}s", discoveryItem->printerUri);
424 Json::Value option;
425 option["printerName"] = name;
426 option["printerUri"] = std::string(discoveryItem->printerUri);
427 option["make"] = std::string(discoveryItem->makeAndModel);
428 if (discoveryItem->printerUuid != nullptr) {
429 option["printer-uuid"] = std::string(discoveryItem->printerUuid);
430 }
431 if (discoveryItem->detailInfo != nullptr) {
432 Json::Value detailInfo;
433 std::istringstream iss(std::string(discoveryItem->detailInfo));
434 if (PrintJsonUtil::ParseFromStream(iss, detailInfo) && !detailInfo.isNull()
435 && PrintJsonUtil::IsMember(detailInfo, "bsunidriver_support") &&
436 detailInfo["bsunidriver_support"].isString()) {
437 option["bsunidriverSupport"] = detailInfo["bsunidriver_support"].asString();
438 }
439 } else {
440 PRINT_HILOGW("DetailInfo is null");
441 }
442 info.SetOption(PrintJsonUtil::WriteString(option));
443 }
444 return true;
445 }
446
AddUniquePageSize(std::vector<PrintPageSize> & pageSizeList,const PrintPageSize & printPageSize)447 void AddUniquePageSize(std::vector<PrintPageSize> &pageSizeList, const PrintPageSize &printPageSize)
448 {
449 for (auto const &item : pageSizeList) {
450 if (item.GetId() == printPageSize.GetId()) {
451 return;
452 }
453 }
454 pageSizeList.push_back(printPageSize);
455 }
456
UpdateDefaultPageSizeId(PrinterCapability & printerCap,const std::string & defaultPageId,const std::string & pageId,const Print_PageSize & page)457 bool UpdateDefaultPageSizeId(PrinterCapability &printerCap, const std::string &defaultPageId, const std::string &pageId,
458 const Print_PageSize &page)
459 {
460 if (page.id != nullptr && defaultPageId == std::string(page.id)) {
461 printerCap.SetPrinterAttrNameAndValue("defaultPageSizeId", pageId.c_str());
462 return true;
463 }
464 return false;
465 }
466
UpdatePageSizeCapability(PrinterCapability & printerCap,const Print_PrinterCapability * capability,const Print_DefaultValue * defaultValue)467 bool UpdatePageSizeCapability(PrinterCapability &printerCap, const Print_PrinterCapability *capability,
468 const Print_DefaultValue *defaultValue)
469 {
470 if (capability == nullptr || capability->supportedPageSizes == nullptr) {
471 PRINT_HILOGW("supportedPageSizes is null");
472 return false;
473 }
474 std::string defaultPageId;
475 if (defaultValue != nullptr && defaultValue->defaultPageSizeId != nullptr) {
476 defaultPageId = defaultValue->defaultPageSizeId;
477 }
478 std::vector<PrintPageSize> pageSizeList;
479 for (uint32_t i = 0; i < capability->supportedPageSizesCount; ++i) {
480 PrintPageSize printPageSize;
481 if (capability->supportedPageSizes[i].name != nullptr) {
482 std::string pageSizeName(capability->supportedPageSizes[i].name);
483 PAGE_SIZE_ID id = PrintPageSize::MatchPageSize(pageSizeName);
484 if (!id.empty() && PrintPageSize::FindPageSizeById(id, printPageSize)) {
485 AddUniquePageSize(pageSizeList, printPageSize);
486 UpdateDefaultPageSizeId(printerCap, defaultPageId, id, capability->supportedPageSizes[i]);
487 PRINT_HILOGD("page size matched = %{public}s", id.c_str());
488 continue;
489 }
490 }
491 if (capability->supportedPageSizes[i].id != nullptr) {
492 PAGE_SIZE_ID id = std::string(capability->supportedPageSizes[i].id);
493 if (!id.empty() && PrintPageSize::FindPageSizeById(id, printPageSize)) {
494 AddUniquePageSize(pageSizeList, printPageSize);
495 UpdateDefaultPageSizeId(printerCap, defaultPageId, id, capability->supportedPageSizes[i]);
496 PRINT_HILOGD("page size matched = %{public}s", id.c_str());
497 continue;
498 }
499 }
500 if (capability->supportedPageSizes[i].name != nullptr && capability->supportedPageSizes[i].id != nullptr) {
501 if (strstr(capability->supportedPageSizes[i].id, "CUSTOM_MIN") ||
502 strstr(capability->supportedPageSizes[i].id, "CUSTOM_MAX")) {
503 PRINT_HILOGW("skip pageSize: %{public}s", capability->supportedPageSizes[i].name);
504 continue;
505 }
506 printPageSize.SetWidth(capability->supportedPageSizes[i].width);
507 printPageSize.SetHeight(capability->supportedPageSizes[i].height);
508 if (printPageSize.ConvertToPwgStyle()) {
509 AddUniquePageSize(pageSizeList, printPageSize);
510 PRINT_HILOGD("custom page size matched = %{public}s", printPageSize.GetId().c_str());
511 continue;
512 }
513 }
514 }
515 printerCap.SetSupportedPageSize(pageSizeList);
516 return true;
517 }
518
UpdateQualityCapability(PrinterCapability & printerCap,const Print_PrinterCapability * capability)519 bool UpdateQualityCapability(PrinterCapability &printerCap, const Print_PrinterCapability *capability)
520 {
521 if (capability == nullptr || capability->supportedQualities == nullptr) {
522 PRINT_HILOGW("supportedQualities is null");
523 return false;
524 }
525 std::vector<uint32_t> supportedQualityList;
526 if (ConvertArrayToList<Print_Quality, uint32_t>(capability->supportedQualities,
527 capability->supportedQualitiesCount, supportedQualityList, ConvertQuality)) {
528 printerCap.SetSupportedQuality(supportedQualityList);
529 }
530 std::string supportedQualities = ConvertArrayToJson<Print_Quality>(
531 capability->supportedQualities, capability->supportedQualitiesCount, ConvertQualityToJson);
532 PRINT_HILOGD("quality: %{public}s", supportedQualities.c_str());
533 if (!supportedQualities.empty()) {
534 printerCap.SetPrinterAttrNameAndValue("print-quality-supported", supportedQualities.c_str());
535 }
536 return true;
537 }
538
UpdateColorCapability(PrinterCapability & printerCap,const Print_PrinterCapability * capability)539 bool UpdateColorCapability(PrinterCapability &printerCap, const Print_PrinterCapability *capability)
540 {
541 if (capability == nullptr || capability->supportedColorModes == nullptr) {
542 PRINT_HILOGW("supportedColorModes is null");
543 return false;
544 }
545 std::vector<uint32_t> supportedColorModes;
546 if (ConvertArrayToList<Print_ColorMode, uint32_t>(capability->supportedColorModes,
547 capability->supportedColorModesCount, supportedColorModes, ConvertColorMode)) {
548 printerCap.SetSupportedColorMode(supportedColorModes);
549 }
550 std::string colorModeJson = ConvertArrayToJson<Print_ColorMode>(
551 capability->supportedColorModes, capability->supportedColorModesCount, ConvertColorModeToJson);
552 if (!colorModeJson.empty()) {
553 printerCap.SetPrinterAttrNameAndValue("print-color-mode-supported", colorModeJson.c_str());
554 }
555 for (uint32_t i = 0; i < capability->supportedColorModesCount; ++i) {
556 if (capability->supportedColorModes[i] == Print_ColorMode::COLOR_MODE_COLOR) {
557 printerCap.SetColorMode(ColorModeCode::COLOR_MODE_COLOR);
558 break;
559 }
560 }
561 return true;
562 }
563
UpdateDuplexCapability(PrinterCapability & printerCap,const Print_PrinterCapability * capability)564 bool UpdateDuplexCapability(PrinterCapability &printerCap, const Print_PrinterCapability *capability)
565 {
566 if (capability == nullptr || capability->supportedDuplexModes == nullptr) {
567 PRINT_HILOGW("supportedDuplexModes is null");
568 return false;
569 }
570 std::vector<uint32_t> supportedDuplexModes;
571 if (ConvertArrayToList<Print_DuplexMode, uint32_t>(capability->supportedDuplexModes,
572 capability->supportedDuplexModesCount, supportedDuplexModes, ConvertDuplexMode)) {
573 printerCap.SetSupportedDuplexMode(supportedDuplexModes);
574 }
575 std::string duplexModeJson = ConvertArrayToJson<Print_DuplexMode>(
576 capability->supportedDuplexModes, capability->supportedDuplexModesCount, ConvertDuplexModeToJson);
577 if (!duplexModeJson.empty()) {
578 printerCap.SetPrinterAttrNameAndValue("sides-supported", duplexModeJson.c_str());
579 }
580 if (capability->supportedDuplexModesCount > 1) {
581 printerCap.SetDuplexMode(static_cast<uint32_t>(Print_DuplexMode::DUPLEX_MODE_TWO_SIDED_LONG_EDGE));
582 }
583 return true;
584 }
UpdateResolutionCapability(PrinterCapability & printerCap,const Print_PrinterCapability * capability)585 bool UpdateResolutionCapability(PrinterCapability &printerCap, const Print_PrinterCapability *capability)
586 {
587 if (capability == nullptr || capability->supportedResolutions == nullptr) {
588 PRINT_HILOGW("supportedResolutions is null");
589 return false;
590 }
591 std::vector<PrintResolution> resolutionList;
592 Json::Value resolutionArray;
593 for (uint32_t i = 0; i < capability->supportedResolutionsCount; ++i) {
594 PrintResolution printResolution;
595 uint32_t xRes = capability->supportedResolutions[i].horizontalDpi;
596 uint32_t yRes = capability->supportedResolutions[i].verticalDpi;
597 printResolution.SetHorizontalDpi(xRes);
598 printResolution.SetVerticalDpi(yRes);
599 PRINT_HILOGD("resolution = %{public}u x %{public}u", xRes, yRes);
600 resolutionList.push_back(printResolution);
601 Json::Value object;
602 object["horizontalDpi"] = xRes;
603 object["verticalDpi"] = yRes;
604 resolutionArray.append(object);
605 }
606 printerCap.SetResolution(resolutionList);
607 printerCap.SetPrinterAttrNameAndValue("printer-resolution-supported",
608 (PrintJsonUtil::WriteString(resolutionArray)).c_str());
609 return true;
610 }
611
UpdateResolutionDefaultValue(PrinterCapability & printerCap,const Print_DefaultValue * defaultValue)612 bool UpdateResolutionDefaultValue(PrinterCapability &printerCap, const Print_DefaultValue *defaultValue)
613 {
614 if (defaultValue == nullptr) {
615 PRINT_HILOGW("defaultValue is null");
616 return false;
617 }
618 Json::Value object;
619 object["horizontalDpi"] = defaultValue->defaultResolution.horizontalDpi;
620 object["verticalDpi"] = defaultValue->defaultResolution.verticalDpi;
621 printerCap.SetPrinterAttrNameAndValue("printer-resolution-default", (PrintJsonUtil::WriteString(object)).c_str());
622 return true;
623 }
624
UpdateCopiesCapability(PrinterCapability & printerCap,const Print_PrinterCapability * capability,const Print_DefaultValue * defaultValue)625 bool UpdateCopiesCapability(PrinterCapability &printerCap, const Print_PrinterCapability *capability,
626 const Print_DefaultValue *defaultValue)
627 {
628 if (capability == nullptr || defaultValue == nullptr) {
629 PRINT_HILOGW("capability or defaultValue is null");
630 return false;
631 }
632 printerCap.SetPrinterAttrNameAndValue("copies-supported", std::to_string(capability->supportedCopies).c_str());
633 printerCap.SetPrinterAttrNameAndValue("copies-default", std::to_string(defaultValue->defaultCopies).c_str());
634 return true;
635 }
636
UpdateOrientationCapability(PrinterCapability & printerCap,const Print_PrinterCapability * capability,const Print_DefaultValue * defaultValue)637 bool UpdateOrientationCapability(PrinterCapability &printerCap, const Print_PrinterCapability *capability,
638 const Print_DefaultValue *defaultValue)
639 {
640 if (capability == nullptr || defaultValue == nullptr) {
641 PRINT_HILOGW("capability or defaultValue is null");
642 return false;
643 }
644 printerCap.SetPrinterAttrNameAndValue("orientation-requested-default",
645 std::to_string(defaultValue->defaultOrientation).c_str());
646 if (capability->supportedOrientations != nullptr) {
647 Json::Value supportedOrientationArray;
648 std::vector<uint32_t> supportedOrientations;
649 for (uint32_t i = 0; i < capability->supportedOrientationsCount; ++i) {
650 int orientationEnum = static_cast<int>(capability->supportedOrientations[i]) + ORIENTATION_OFFSET;
651 supportedOrientationArray.append(orientationEnum);
652 supportedOrientations.push_back(static_cast<uint32_t>(orientationEnum));
653 }
654 printerCap.SetSupportedOrientation(supportedOrientations);
655 printerCap.SetPrinterAttrNameAndValue("orientation-requested-supported",
656 (PrintJsonUtil::WriteString(supportedOrientationArray)).c_str());
657 }
658 return true;
659 }
660
UpdateMediaCapability(PrinterCapability & printerCap,const Print_PrinterCapability * capability,const Print_DefaultValue * defaultValue)661 bool UpdateMediaCapability(PrinterCapability &printerCap, const Print_PrinterCapability *capability,
662 const Print_DefaultValue *defaultValue)
663 {
664 if (capability == nullptr || defaultValue == nullptr) {
665 PRINT_HILOGW("capability or defaultValue is null");
666 return false;
667 }
668 if (capability->supportedMediaTypes != nullptr) {
669 printerCap.SetPrinterAttrNameAndValue("media-type-supported", capability->supportedMediaTypes);
670 std::string mediaTypeJson(capability->supportedMediaTypes);
671 std::vector<std::string> mediaTypeList;
672 if (ConvertJsonToStringList(mediaTypeJson, mediaTypeList)) {
673 printerCap.SetSupportedMediaType(mediaTypeList);
674 } else {
675 PRINT_HILOGW("invalid media types");
676 }
677 }
678 if (defaultValue->defaultMediaType != nullptr) {
679 printerCap.SetPrinterAttrNameAndValue("media-type-default", defaultValue->defaultMediaType);
680 }
681 if (capability->supportedPaperSources != nullptr) {
682 printerCap.SetPrinterAttrNameAndValue("media-source-supported", capability->supportedPaperSources);
683 }
684 if (defaultValue->defaultPaperSource != nullptr) {
685 printerCap.SetPrinterAttrNameAndValue("media-source-default", defaultValue->defaultPaperSource);
686 }
687 return true;
688 }
UpdateMarginCapability(PrinterCapability & printerCap,const Print_DefaultValue * defaultValue)689 bool UpdateMarginCapability(PrinterCapability &printerCap, const Print_DefaultValue *defaultValue)
690 {
691 if (defaultValue == nullptr) {
692 PRINT_HILOGW("defaultValue is null");
693 return false;
694 }
695 PrintMargin printMargin;
696 printMargin.SetLeft(defaultValue->defaultMargin.leftMargin);
697 printMargin.SetTop(defaultValue->defaultMargin.topMargin);
698 printMargin.SetRight(defaultValue->defaultMargin.rightMargin);
699 printMargin.SetBottom(defaultValue->defaultMargin.bottomMargin);
700 PRINT_HILOGD("margin left = %{public}u, top = %{public}u, right = %{public}u, bottom = %{public}u",
701 defaultValue->defaultMargin.leftMargin, defaultValue->defaultMargin.topMargin,
702 defaultValue->defaultMargin.rightMargin, defaultValue->defaultMargin.bottomMargin);
703 printerCap.SetMinMargin(printMargin);
704 return true;
705 }
UpdatePrinterCapability(PrinterCapability & printerCap,const Print_PrinterCapability * capability,const Print_DefaultValue * defaultValue)706 bool UpdatePrinterCapability(PrinterCapability &printerCap, const Print_PrinterCapability *capability,
707 const Print_DefaultValue *defaultValue)
708 {
709 if (capability == nullptr || defaultValue == nullptr) {
710 PRINT_HILOGW("capability or defaultValue is null");
711 return false;
712 }
713 if (!UpdatePageSizeCapability(printerCap, capability, defaultValue)) {
714 return false;
715 }
716 UpdateColorCapability(printerCap, capability);
717 uint32_t defaultColorMode = static_cast<uint32_t>(defaultValue->defaultColorMode);
718 printerCap.SetPrinterAttrNameAndValue("defaultColorMode", std::to_string(defaultColorMode).c_str());
719 UpdateDuplexCapability(printerCap, capability);
720 uint32_t defaultDuplexMode = static_cast<uint32_t>(defaultValue->defaultDuplexMode);
721 printerCap.SetPrinterAttrNameAndValue("sides-default", std::to_string(defaultDuplexMode).c_str());
722 UpdateQualityCapability(printerCap, capability);
723 UpdateResolutionCapability(printerCap, capability);
724 UpdateResolutionDefaultValue(printerCap, defaultValue);
725 UpdateCopiesCapability(printerCap, capability, defaultValue);
726 UpdateOrientationCapability(printerCap, capability, defaultValue);
727 UpdateMediaCapability(printerCap, capability, defaultValue);
728 UpdateMarginCapability(printerCap, defaultValue);
729 return true;
730 }
731
UpdatePrinterInfoWithCapability(PrinterInfo & info,const Print_DiscoveryItem * discoveryItem,const Print_PrinterCapability * capability,const Print_DefaultValue * defaultValue)732 bool UpdatePrinterInfoWithCapability(PrinterInfo &info, const Print_DiscoveryItem *discoveryItem,
733 const Print_PrinterCapability *capability, const Print_DefaultValue *defaultValue)
734 {
735 PrinterCapability printerCap;
736 if (!UpdatePrinterCapability(printerCap, capability, defaultValue)) {
737 PRINT_HILOGW("update capability fail");
738 return false;
739 }
740 Json::Value options;
741 if (discoveryItem != nullptr) {
742 if (discoveryItem->makeAndModel != nullptr) {
743 options["make"] = std::string(discoveryItem->makeAndModel);
744 }
745 if (discoveryItem->printerName != nullptr) {
746 options["printerName"] = info.GetPrinterName();
747 }
748 if (discoveryItem->printerUuid != nullptr) {
749 options["printer-uuid"] = std::string(discoveryItem->printerUuid);
750 }
751 }
752 Json::Value cupsOptionsJson = printerCap.GetPrinterAttrGroupJson();
753 options["cupsOptions"] = cupsOptionsJson;
754 std::string optionStr = PrintJsonUtil::WriteString(options);
755 PRINT_HILOGD("SetOption: %{public}s", optionStr.c_str());
756 printerCap.SetOption(optionStr);
757 info.SetCapability(printerCap);
758 info.Dump();
759 return true;
760 }
761
ConvertVendorCapabilityToPrinterInfo(const Print_DiscoveryItem * printer,const Print_PrinterCapability * capability,const Print_DefaultValue * defaultValue)762 std::shared_ptr<PrinterInfo> ConvertVendorCapabilityToPrinterInfo(const Print_DiscoveryItem *printer,
763 const Print_PrinterCapability *capability,
764 const Print_DefaultValue *defaultValue)
765 {
766 if (printer == nullptr || printer->printerId == nullptr) {
767 PRINT_HILOGW("printer null");
768 return nullptr;
769 }
770 std::shared_ptr<PrinterInfo> info = std::make_shared<PrinterInfo>();
771 if (info == nullptr) {
772 return nullptr;
773 }
774 if (!UpdatePrinterInfoWithDiscovery(*info, printer)) {
775 PRINT_HILOGW("update printer info fail");
776 return nullptr;
777 }
778 UpdatePrinterInfoWithCapability(*info, printer, capability, defaultValue);
779 return info;
780 }
781
ConvertStringVectorToStringList(const std::vector<std::string> & stringVector,Print_StringList & stringList)782 bool ConvertStringVectorToStringList(const std::vector<std::string> &stringVector, Print_StringList &stringList)
783 {
784 size_t count = stringVector.size();
785 if (count == 0 || count > MAX_STRING_COUNT) {
786 return false;
787 }
788 stringList.count = 0;
789 stringList.list = new (std::nothrow) char *[count];
790 if (stringList.list == nullptr) {
791 PRINT_HILOGW("stringList list allocate fail");
792 return false;
793 }
794 if (memset_s(stringList.list, count * sizeof(char *), 0, count * sizeof(char *)) != 0) {
795 PRINT_HILOGW("memset_s fail");
796 delete[] stringList.list;
797 stringList.list = nullptr;
798 return false;
799 }
800 for (auto const &key : stringVector) {
801 stringList.list[stringList.count] = CopyString(key);
802 stringList.count++;
803 }
804 return true;
805 }
806
ReleaseStringList(Print_StringList & stringList)807 void ReleaseStringList(Print_StringList &stringList)
808 {
809 if (stringList.list != nullptr) {
810 for (uint32_t i = 0; i < stringList.count; i++) {
811 if (stringList.list[i] != nullptr) {
812 delete[] stringList.list[i];
813 stringList.list[i] = nullptr;
814 }
815 }
816 delete[] stringList.list;
817 stringList.list = nullptr;
818 }
819 stringList.count = 0;
820 }
821 }
822