1/* 2 * Copyright (c) 2024-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 <algorithm> 17 18#include "elf_sign_block.h" 19#include "fs_verity_descriptor.h" 20#include "fs_verity_descriptor_with_sign.h" 21#include "verify_code_signature.h" 22#include "code_signing.h" 23#include "signer_factory.h" 24#include "localization_adapter.h" 25 26namespace OHOS { 27namespace SignatureTools { 28const int BUFFER_SIZE = 16 * 1024; 29const int FILE_NAME_SIZE = 512; 30const std::vector<std::string> CodeSigning::SUPPORT_FILE_FORM = { "hap", "hsp", "hqf" }; 31const std::string CodeSigning::HAP_SIGNATURE_ENTRY_NAME = "Hap"; 32const std::string CodeSigning::ENABLE_SIGN_CODE_VALUE = "1"; 33const std::string CodeSigning::LIBS_PATH_PREFIX = "libs/"; 34 35const FsVerityHashAlgorithm FS_SHA256(1, "SHA-256", 256 / 8); 36const FsVerityHashAlgorithm FS_SHA512(2, "SHA-512", 512 / 8); 37const int8_t LOG_2_OF_FSVERITY_HASH_PAGE_SIZE = 12; 38 39CodeSigning::CodeSigning(SignerConfig* signConfig) : mPools(new Uscript::ThreadPool(POOL_SIZE)) 40{ 41 m_signConfig = signConfig; 42} 43 44CodeSigning::CodeSigning() : mPools(new Uscript::ThreadPool(POOL_SIZE)) 45{ 46} 47 48bool CodeSigning::GetCodeSignBlock(const std::string &input, int64_t offset, 49 const std::string &inForm, const std::string &profileContent, 50 ZipSigner& zip, std::vector<int8_t>& ret) 51{ 52 SIGNATURE_TOOLS_LOGI("Start to sign code."); 53 bool formatFlag = std::find(SUPPORT_FILE_FORM.begin(), SUPPORT_FILE_FORM.end(), inForm) 54 == SUPPORT_FILE_FORM.end(); 55 if (formatFlag) { 56 SIGNATURE_TOOLS_LOGE("only support format is [hap, hqf, hsp, app]"); 57 return false; 58 } 59 uint32_t dataSize = ComputeDataSize(zip); 60 if (dataSize < 0) { 61 return false; 62 } 63 m_timestamp = GetTimestamp(); 64 int64_t fsvTreeOffset = m_codeSignBlock.ComputeMerkleTreeOffset(offset); 65 std::unique_ptr<FsVerityInfoSegment> fsVerityInfoSegment = 66 std::make_unique<FsVerityInfoSegment>((int8_t)FsVerityDescriptor::VERSION, 67 (int8_t)FsVerityGenerator::GetFsVerityHashAlgorithm(), 68 (int8_t)FsVerityGenerator::GetLog2BlockSize()); 69 m_codeSignBlock.SetFsVerityInfoSegment(*(fsVerityInfoSegment.get())); 70 SIGNATURE_TOOLS_LOGI("Sign hap."); 71 std::string ownerID = HapUtils::GetAppIdentifier(profileContent); 72 std::ifstream inputStream; 73 inputStream.open(input, std::ios::binary); 74 if (!inputStream.is_open()) { 75 PrintErrorNumberMsg("IO_ERROR", IO_ERROR, "open file: " + input + "failed"); 76 inputStream.close(); 77 return false; 78 } 79 std::pair<SignInfo, std::vector<int8_t>> hapSignInfoAndMerkleTreeBytesPair; 80 bool signFileFlag = SignFile(inputStream, dataSize, true, fsvTreeOffset, ownerID, 81 hapSignInfoAndMerkleTreeBytesPair); 82 if (!signFileFlag) { 83 SIGNATURE_TOOLS_LOGE("SignFile Failed"); 84 inputStream.close(); 85 return false; 86 } 87 inputStream.close(); 88 m_codeSignBlock.GetHapInfoSegment().SetSignInfo(hapSignInfoAndMerkleTreeBytesPair.first); 89 m_codeSignBlock.AddOneMerkleTree(HAP_SIGNATURE_ENTRY_NAME, 90 hapSignInfoAndMerkleTreeBytesPair.second); 91 if (!SignNativeLibs(input, ownerID)) { 92 PrintErrorNumberMsg("SIGN_ERROR", SIGN_ERROR, "Failed to sign the contents in the compressed file."); 93 return false; 94 } 95 UpdateCodeSignBlock(); 96 m_codeSignBlock.GenerateCodeSignBlockByte(fsvTreeOffset, ret); 97 SIGNATURE_TOOLS_LOGI("Sign successfully."); 98 return true; 99} 100 101uint32_t CodeSigning::ComputeDataSize(ZipSigner& zip) 102{ 103 uint32_t dataSize = 0L; 104 for (const auto& entry : zip.GetZipEntries()) { 105 ZipEntryHeader* zipEntryHeader = entry->GetZipEntryData()->GetZipEntryHeader(); 106 bool runnableFileFlag = FileUtils::IsRunnableFile(zipEntryHeader->GetFileName()) 107 && zipEntryHeader->GetMethod() == ZipSigner::FILE_UNCOMPRESS_METHOD_FLAG; 108 if (runnableFileFlag) { 109 continue; 110 } 111 // if the first file is not uncompressed abc or so, set dataSize to zero 112 if (entry->GetCentralDirectory()->GetOffset() == 0) { 113 break; 114 } 115 // the first entry which is not abc/so/an is found, return its data offset 116 dataSize = entry->GetCentralDirectory()->GetOffset() + ZipEntryHeader::HEADER_LENGTH 117 + zipEntryHeader->GetFileNameLength() + zipEntryHeader->GetExtraLength(); 118 break; 119 } 120 if ((dataSize % CodeSignBlock::PAGE_SIZE_4K) != 0) { 121 PrintErrorNumberMsg("SIGN_ERROR", SIGN_ERROR, 122 "Invalid dataSize, the dataSize must be an integer multiple of 4096"); 123 return -1; 124 } 125 return dataSize; 126} 127 128int64_t CodeSigning::GetTimestamp() 129{ 130 auto now = std::chrono::system_clock::now(); 131 auto nowSeconds = std::chrono::time_point_cast<std::chrono::seconds>(now); 132 return nowSeconds.time_since_epoch().count(); 133} 134 135bool CodeSigning::SignFile(std::istream& inputStream, int64_t fileSize, bool storeTree, 136 int64_t fsvTreeOffset, const std::string &ownerID, 137 std::pair<SignInfo, std::vector<int8_t>>& ret) 138{ 139 std::unique_ptr<FsVerityGenerator> fsVerityGenerator = 140 std::make_unique<FsVerityGenerator>(); 141 if (!fsVerityGenerator->GenerateFsVerityDigest(inputStream, fileSize, fsvTreeOffset)) { 142 SIGNATURE_TOOLS_LOGE("SignFile GenerateFsVerityDigest Fail"); 143 return false; 144 } 145 std::vector<int8_t> fsVerityDigest = fsVerityGenerator->GetFsVerityDigest(); 146 std::vector<int8_t> signature; 147 bool generateSignatureFlag = GenerateSignature(fsVerityDigest, ownerID, signature); 148 if (!generateSignatureFlag) { 149 SIGNATURE_TOOLS_LOGE("SignFile GenerateSignature Fail"); 150 return false; 151 } 152 int flags = 0; 153 if (storeTree) { 154 flags = SignInfo::FLAG_MERKLE_TREE_INCLUDED; 155 } 156 int saltSize = fsVerityGenerator->GetSaltSize(); 157 std::vector<int8_t> salt = fsVerityGenerator->GetSalt(); 158 SignInfo signInfo(saltSize, flags, fileSize, salt, signature); 159 // if store merkle tree in sign info 160 if (storeTree) { 161 int merkleTreeSize = fsVerityGenerator->GetTreeBytes().empty() ? 0 162 : fsVerityGenerator->GetTreeBytes().size(); 163 MerkleTreeExtension* merkleTreeExtension = new MerkleTreeExtension(merkleTreeSize, 164 fsvTreeOffset, 165 fsVerityGenerator->GetRootHash()); 166 if (merkleTreeExtension == nullptr) { 167 PrintErrorNumberMsg("SIGN_ERROR", SIGN_ERROR, "system failed to allocate memory for MerkleTreeExtension"); 168 return false; 169 } 170 signInfo.AddExtension(merkleTreeExtension); 171 } 172 ret = std::make_pair(signInfo, fsVerityGenerator->GetTreeBytes()); 173 return true; 174} 175 176bool CodeSigning::GetElfCodeSignBlock(const std::string &input, int64_t offset, 177 const std::string &inForm, const std::string &profileContent, 178 std::vector<int8_t>& codesignData) 179{ 180 SIGNATURE_TOOLS_LOGI("Start to sign elf code."); 181 int paddingSize = ElfSignBlock::ComputeMerkleTreePaddingLength(offset); 182 int64_t fsvTreeOffset = offset + FsVerityDescriptorWithSign::INTEGER_BYTES * 2 + paddingSize; 183 std::ifstream inputstream(input, std::ios::binary | std::ios::ate); 184 if (!inputstream.is_open()) { 185 PrintErrorNumberMsg("IO_ERROR", IO_ERROR, "open file: " + input + "failed"); 186 return false; 187 } 188 std::streamsize fileSize = inputstream.tellg(); 189 inputstream.seekg(0, std::ios::beg); 190 std::unique_ptr<FsVerityGenerator> fsVerityGenerator = std::make_unique<FsVerityGenerator>(); 191 fsVerityGenerator->GenerateFsVerityDigest(inputstream, fileSize, fsvTreeOffset); 192 std::vector<int8_t> fsVerityDigest = fsVerityGenerator->GetFsVerityDigest(); 193 std::string ownerID = profileContent.empty() ? "DEBUF_LIB_ID" : HapUtils::GetAppIdentifier(profileContent); 194 std::vector<int8_t> signature; 195 bool generateSignatureFlag = GenerateSignature(fsVerityDigest, ownerID, signature); 196 if (!generateSignatureFlag) { 197 SIGNATURE_TOOLS_LOGE("[SignElf] generate elf signature failed"); 198 return false; 199 } 200 201 FsVerityDescriptor::Builder fsdbuilder; 202 fsdbuilder.SetFileSize(fileSize) 203 .SetHashAlgorithm(FS_SHA256.GetId()) 204 .SetLog2BlockSize(LOG_2_OF_FSVERITY_HASH_PAGE_SIZE) 205 .SetSaltSize(fsVerityGenerator->GetSaltSize()) 206 .SetSignSize(signature.size()) 207 .SetFileSize(fileSize) 208 .SetSalt(fsVerityGenerator->Getsalt()) 209 .SetRawRootHash(fsVerityGenerator->GetRootHash()) 210 .SetFlags(FsVerityDescriptor::FLAG_STORE_MERKLE_TREE_OFFSET) 211 .SetMerkleTreeOffset(fsvTreeOffset) 212 .SetCsVersion(FsVerityDescriptor::CODE_SIGN_VERSION); 213 214 FsVerityDescriptorWithSign fsVerityDescriptorWithSign = 215 FsVerityDescriptorWithSign(FsVerityDescriptor(fsdbuilder), signature); 216 std::vector<int8_t> treeBytes = fsVerityGenerator->GetTreeBytes(); 217 ElfSignBlock signBlock = ElfSignBlock(paddingSize, treeBytes, fsVerityDescriptorWithSign); 218 signBlock.ToByteArray(codesignData); 219 return true; 220} 221 222bool CodeSigning::SignNativeLibs(const std::string &input, std::string &ownerID) 223{ 224 // sign native files 225 std::vector<std::pair<std::string, SignInfo>> ret; 226 UnzipHandleParam param(ret, ownerID, true); 227 bool nativeLibflag = GetNativeEntriesFromHap(input, param); 228 if (!nativeLibflag) { 229 SIGNATURE_TOOLS_LOGE("%s native libs handle failed", input.c_str()); 230 return false; 231 } 232 std::vector<std::pair<std::string, SignInfo>>& nativeLibInfoList = param.GetRet(); 233 if (nativeLibInfoList.empty()) { 234 SIGNATURE_TOOLS_LOGI("No native libs."); 235 return true; 236 } 237 m_codeSignBlock.GetSoInfoSegment().SetSoInfoList(nativeLibInfoList); 238 return true; 239} 240 241void CodeSigning::UpdateCodeSignBlock() 242{ 243 // construct segment header list 244 m_codeSignBlock.SetSegmentHeaders(); 245 // Compute and set segment number 246 m_codeSignBlock.SetSegmentNum(); 247 // update code sign block header flag 248 m_codeSignBlock.SetCodeSignBlockFlag(); 249 // compute segment offset 250 m_codeSignBlock.ComputeSegmentOffset(); 251} 252 253bool CodeSigning::GetNativeEntriesFromHap(const std::string& packageName, UnzipHandleParam& param) 254{ 255 unzFile zFile = unzOpen(packageName.c_str()); 256 if (zFile == NULL) { 257 PrintErrorNumberMsg("IO_ERROR", IO_ERROR, "zlib open file: " + packageName + " failed."); 258 return false; 259 } 260 // get zipFile all paramets 261 unz_global_info zGlobalInfo; 262 int getRet = unzGetGlobalInfo(zFile, &zGlobalInfo); 263 if (getRet != UNZ_OK) { 264 PrintErrorNumberMsg("SIGN_ERROR", SIGN_ERROR, "zlib get global info failed."); 265 unzClose(zFile); 266 return false; 267 } 268 // search each file 269 bool handleFlag = HandleZipGlobalInfo(packageName, zFile, zGlobalInfo, param); 270 if (!handleFlag) { 271 unzClose(zFile); 272 return false; 273 } 274 275 unzClose(zFile); 276 return true; 277} 278 279bool CodeSigning::GetSingleFileStreamFromZip(unzFile &zFile, char fileName[], 280 unz_file_info &zFileInfo, 281 int &readFileSize, std::stringbuf &sb) 282{ 283 char szReadBuffer[BUFFER_SIZE] = { 0 }; 284 285 long fileLength = zFileInfo.uncompressed_size; 286 int nReadFileSize; 287 do { 288 nReadFileSize = 0; 289 if (memset_s(szReadBuffer, BUFFER_SIZE, 0, BUFFER_SIZE) != EOK) { 290 SIGNATURE_TOOLS_LOGE("memset_s failed"); 291 unzClose(zFile); 292 return false; 293 } 294 nReadFileSize = unzReadCurrentFile(zFile, szReadBuffer, BUFFER_SIZE); 295 if (nReadFileSize > 0) { 296 sb.sputn(szReadBuffer, nReadFileSize); 297 } 298 fileLength -= nReadFileSize; 299 readFileSize += nReadFileSize; 300 } while (fileLength > 0 && nReadFileSize > 0); 301 if (fileLength) { 302 PrintErrorNumberMsg("SIGN_ERROR", SIGN_ERROR, "zlib read stream from " 303 + std::string(fileName) + " failed."); 304 unzClose(zFile); 305 return false; 306 } 307 308 unzCloseCurrentFile(zFile); 309 unzClose(zFile); 310 return true; 311} 312 313bool CodeSigning::RunParseZipInfo(const std::string& packageName, UnzipHandleParam& param, uLong index) 314{ 315 unzFile zFile = unzOpen(packageName.c_str()); 316 if (zFile == NULL) { 317 PrintErrorNumberMsg("IO_ERROR", IO_ERROR, "zlib open file: " + packageName + " failed."); 318 return false; 319 } 320 // get zipFile all paramets 321 unz_global_info zGlobalInfo; 322 int getRet = unzGetGlobalInfo(zFile, &zGlobalInfo); 323 if (getRet != UNZ_OK) { 324 PrintErrorNumberMsg("SIGN_ERROR", SIGN_ERROR, "zlib get global info failed."); 325 unzClose(zFile); 326 return false; 327 } 328 for (uLong i = 0; i < index; ++i) { 329 int ret = unzGoToNextFile(zFile); 330 if (ret != UNZ_OK) { 331 unzClose(zFile); 332 return false; 333 } 334 } 335 unz_file_info zFileInfo; 336 char fileName[FILE_NAME_SIZE]; 337 int readFileSize = 0; 338 std::stringbuf sb; 339 if (memset_s(fileName, FILE_NAME_SIZE, 0, FILE_NAME_SIZE) != 0) { 340 unzClose(zFile); 341 return false; 342 } 343 size_t nameLen = 0; 344 if (!CheckUnzParam(zFile, zFileInfo, fileName, &nameLen)) { 345 unzClose(zFile); 346 return false; 347 } 348 if (!CheckFileName(zFile, fileName, &nameLen)) { 349 unzClose(zFile); 350 return true; 351 } 352 bool flag = GetSingleFileStreamFromZip(zFile, fileName, zFileInfo, readFileSize, sb); 353 if (!flag) { 354 return false; 355 } 356 bool handleFlag = DoNativeLibSignOrVerify(std::string(fileName), sb, param, readFileSize); 357 if (!handleFlag) { 358 SIGNATURE_TOOLS_LOGE("%s native libs handle failed", fileName); 359 return false; 360 } 361 return true; 362} 363 364bool CodeSigning::HandleZipGlobalInfo(const std::string& packageName, unzFile& zFile, 365 unz_global_info& zGlobalInfo, UnzipHandleParam& param) 366{ 367 std::vector<std::future<bool>> thread_results; 368 SIGNATURE_TOOLS_LOGI("zGlobalInfo.number_entry = %lu", zGlobalInfo.number_entry); 369 for (uLong i = 0; i < zGlobalInfo.number_entry; ++i) { 370 thread_results.push_back(mPools->Enqueue(&CodeSigning::RunParseZipInfo, this, 371 std::ref(packageName), std::ref(param), i)); 372 } 373 374 bool result = true; 375 for (auto& thread_result : thread_results) { 376 if (!thread_result.get()) 377 result = false; 378 } 379 if (!result) { 380 return false; 381 } 382 return true; 383} 384 385bool CodeSigning::DoNativeLibVerify(std::string fileName, std::stringbuf& sb, 386 UnzipHandleParam& param, int readFileSize) 387{ 388 std::istream input(&sb); 389 CodeSignBlock csb = param.GetCodeSignBlock(); 390 std::vector<std::string>& fileNames = csb.GetSoInfoSegment().GetFileNameList(); 391 bool isContainFileName = std::find(fileNames.begin(), fileNames.end(), fileName) != fileNames.end(); 392 if (!isContainFileName) { 393 PrintErrorNumberMsg("VERIFY_ERROR", VERIFY_ERROR, 394 "verify signed file position failed, file: " + fileName); 395 return false; 396 } 397 for (int j = 0; j < csb.GetSoInfoSegment().GetSectionNum(); j++) { 398 SignInfo signInfo = csb.GetSoInfoSegment().GetSignInfoList()[j]; 399 std::string entryName = csb.GetSoInfoSegment().GetFileNameList()[j]; 400 std::vector<int8_t> entrySig = signInfo.GetSignature(); 401 std::string entrySigStr(entrySig.begin(), entrySig.end()); 402 if (fileName != entryName) { 403 continue; 404 } 405 if (readFileSize != signInfo.GetDataSize()) { 406 PrintErrorNumberMsg("VERIFY_ERROR", VERIFY_ERROR, "Invalid dataSize of native lib"); 407 return false; 408 } 409 bool verifyFlag = VerifyCodeSignature::VerifySingleFile(input, readFileSize, entrySig, 0, 410 std::vector<int8_t>()); 411 if (!verifyFlag) { 412 return false; 413 } 414 std::ifstream* inputFile = (std::ifstream*)(&input); 415 inputFile->close(); 416 std::pair<std::string, std::string> pairResult = param.GetPairResult(); 417 bool checkOwnerIDFlag = CmsUtils::CheckOwnerID(entrySigStr, pairResult.first, pairResult.second); 418 if (!checkOwnerIDFlag) { 419 return false; 420 } 421 } 422 return true; 423} 424 425bool CodeSigning::DoNativeLibSignOrVerify(std::string fileName, std::stringbuf& sb, 426 UnzipHandleParam& param, int readFileSize) 427{ 428 bool isSign = param.IsSign(); 429 if (isSign) { 430 std::istream input(&sb); 431 std::string ownerID = param.GetOwnerID(); 432 std::pair<SignInfo, std::vector<int8_t>> pairSignInfoAndMerkleTreeBytes; 433 bool signFileFlag = SignFile(input, readFileSize, false, 0, ownerID, pairSignInfoAndMerkleTreeBytes); 434 if (!signFileFlag) { 435 return false; 436 } 437 m_mutex.lock(); 438 std::vector<std::pair<std::string, SignInfo>> &ret = param.GetRet(); 439 ret.push_back(std::make_pair(fileName, pairSignInfoAndMerkleTreeBytes.first)); 440 m_mutex.unlock(); 441 } else { 442 bool flag = DoNativeLibVerify(fileName, sb, param, readFileSize); 443 if (!flag) { 444 return false; 445 } 446 } 447 return true; 448} 449 450bool CodeSigning::CheckUnzParam(unzFile& zFile, unz_file_info& zFileInfo, 451 char fileName[], size_t* nameLen) 452{ 453 if (UNZ_OK != unzGetCurrentFileInfo(zFile, &zFileInfo, fileName, 454 FILE_NAME_SIZE, NULL, 0, NULL, 0)) { 455 PrintErrorNumberMsg("SIGN_ERROR", SIGN_ERROR, 456 "unzip get file: " + std::string(fileName) + "info failed!"); 457 return false; 458 } 459 SIGNATURE_TOOLS_LOGI("Open zipFile filename is : %s", fileName); 460 if ((*nameLen = strlen(fileName)) == 0U) { 461 PrintErrorNumberMsg("SIGN_ERROR", SIGN_ERROR, "Open zipFile fileName is null"); 462 return false; 463 } 464 if (UNZ_OK != unzOpenCurrentFile(zFile)) { 465 PrintErrorNumberMsg("SIGN_ERROR", SIGN_ERROR, 466 "unzOpenCurrentFile zipFile error"); 467 return false; 468 } 469 return true; 470} 471 472bool CodeSigning::CheckFileName(unzFile& zFile, char fileName[], size_t* nameLen) 473{ 474 if (fileName[*nameLen - 1] == '/') { 475 SIGNATURE_TOOLS_LOGI("It is dictionary."); 476 unzCloseCurrentFile(zFile); 477 unzGoToNextFile(zFile); 478 return false; 479 } 480 std::string str(fileName); 481 bool nativeFileFlag = IsNativeFile(str); 482 if (!nativeFileFlag) { 483 SIGNATURE_TOOLS_LOGI("Suffix mismatched."); 484 unzCloseCurrentFile(zFile); 485 unzGoToNextFile(zFile); 486 return false; 487 } 488 return true; 489} 490 491bool CodeSigning::IsNativeFile(const std::string& input) 492{ 493 size_t dotPos = input.rfind('.'); 494 if (dotPos == std::string::npos) { 495 return false; 496 } 497 std::string suffix = input.substr(dotPos + 1); 498 if (suffix == "an") { 499 return true; 500 } 501 std::string libDir = input.substr(0, LIBS_PATH_PREFIX.size()); 502 int ret = LIBS_PATH_PREFIX.compare(libDir); 503 if (ret == 0) { 504 return true; 505 } 506 return false; 507} 508 509bool CodeSigning::GenerateSignature(const std::vector<int8_t>& signedData, const std::string& ownerID, 510 std::vector<int8_t>& ret) 511{ 512 Options* options = m_signConfig->GetOptions(); 513 SignerFactory factory; 514 LocalizationAdapter adapter(options); 515 std::shared_ptr<Signer> signer(factory.GetSigner(adapter)); 516 if (signer != nullptr) { 517 STACK_OF(X509)* certs = NULL; 518 certs = signer->GetCertificates(); 519 if (certs == nullptr) { 520 PrintErrorNumberMsg("SIGN_ERROR", SIGN_ERROR, 521 "No certificates configured for sign."); 522 return false; 523 } 524 sk_X509_pop_free(certs, X509_free); 525 } else { 526 return false; 527 } 528 std::unique_ptr<BCSignedDataGenerator> bcSignedDataGenerator = 529 std::make_unique<BCSignedDataGenerator>(); 530 if (!ownerID.empty()) { 531 SIGNATURE_TOOLS_LOGW("generate signature get owner id not null."); 532 bcSignedDataGenerator->SetOwnerId(ownerID); 533 } 534 std::string signed_data(signedData.begin(), signedData.end()); 535 std::string ret_str; 536 if (signedData.empty()) { 537 PrintErrorNumberMsg("SIGN_ERROR", SIGN_ERROR, "Generate verity digest is null"); 538 return false; 539 } 540 bool generateSignedDataFlag = bcSignedDataGenerator->GenerateSignedData(signed_data, m_signConfig, ret_str); 541 if (generateSignedDataFlag) { 542 SIGNATURE_TOOLS_LOGE("Generate signedData failed"); 543 return false; 544 } 545 ret = std::vector<int8_t>(ret_str.begin(), ret_str.end()); 546 return true; 547} 548} // namespace SignatureTools 549} // namespace OHOS 550