LCOV - code coverage report
Current view: top level - adump/common - file.cpp (source / functions) Coverage Total Hit
Test: coverage.info Lines: 89.7 % 126 113
Test Date: 2026-08-31 10:09:28 Functions: 90.9 % 11 10

            Line data    Source code
       1              : /**
       2              :  * Copyright (c) 2025 Huawei Technologies Co., Ltd.
       3              :  * This program is free software, you can redistribute it and/or modify it under the terms and conditions of
       4              :  * CANN Open Software License Agreement Version 2.0 (the "License").
       5              :  * Please refer to the License for details. You may not use this file except in compliance with the License.
       6              :  * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED,
       7              :  * INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY, OR FITNESS FOR A PARTICULAR PURPOSE.
       8              :  * See LICENSE in the root of the software repository for the full text of the License.
       9              :  */
      10              : 
      11              : #include "file.h"
      12              : #include "path.h"
      13              : #include "adump_pub.h"
      14              : #include "log/adx_log.h"
      15              : #include "extra_config.h"
      16              : 
      17              : namespace Adx {
      18              : namespace {
      19              : constexpr int32_t INVALID_FILE_FD = -1;
      20              : constexpr mmMode_t READ_WRITE_MODE = M_IRUSR | M_IWUSR;
      21              : constexpr int64_t MAX_BUFFER_LENGTH = 512;
      22              : static const std::string MAPPING_FILE_NAME = "mapping.csv";
      23              : } // namespace
      24              : 
      25          217 : File::File(const std::string& path, int32_t flag, mmMode_t mode, bool lazyOpen)
      26          217 :     : filePath_(path), fd_(INVALID_FILE_FD), flag_(flag), mode_(mode)
      27              : {
      28          217 :     if (lazyOpen) {
      29           88 :         return;
      30              :     }
      31          129 :     if (Open(flag, mode) != ADUMP_SUCCESS) {
      32           19 :         fd_ = INVALID_FILE_FD;
      33              :     }
      34            0 : }
      35              : 
      36           22 : int32_t File::EnsureOpen()
      37              : {
      38           22 :     if (fd_ != INVALID_FILE_FD) {
      39            0 :         return ADUMP_SUCCESS;
      40              :     }
      41           22 :     if (Open(flag_, mode_) != ADUMP_SUCCESS) {
      42            0 :         fd_ = INVALID_FILE_FD;
      43            0 :         return ADUMP_FAILED;
      44              :     }
      45           22 :     return ADUMP_SUCCESS;
      46              : }
      47              : 
      48          217 : File::~File() { (void)Close(); }
      49              : 
      50          151 : int32_t File::Open(int32_t flag, mmMode_t mode)
      51              : {
      52          151 :     Path filePath(filePath_);
      53          151 :     std::string fileName = filePath.GetFileName();
      54          151 :     Path parentPath = filePath.ParentPath();
      55          151 :     if (!parentPath.Empty() && !parentPath.RealPath()) {
      56            7 :         IDE_LOGE("Real file path failed, file: %s", filePath_.c_str());
      57            7 :         return ADUMP_FAILED;
      58              :     }
      59              : 
      60          144 :     std::string realFilePath = parentPath.Concat(fileName).GetString();
      61          144 :     fd_ = mmOpen2(realFilePath.c_str(), flag, mode);
      62          144 :     if (fd_ >= 0) {
      63          129 :         return ADUMP_SUCCESS;
      64              :     }
      65           15 :     if (mmGetErrorCode() != ENAMETOOLONG) {
      66            9 :         IDE_LOGE("Open file failed. file: %s, fd: %d, message: %s", realFilePath.c_str(), fd_, strerror(errno));
      67            9 :         return ADUMP_FAILED;
      68              :     }
      69            6 :     parentPath = filePath.ParentPath();
      70            6 :     if (!parentPath.Empty() && !parentPath.RealPath()) {
      71            0 :         IDE_LOGE("Real long name file path failed, file: %s", filePath_.c_str());
      72            0 :         return ADUMP_FAILED;
      73              :     }
      74            6 :     std::string hashName = std::to_string(std::hash<std::string>{}(fileName));
      75            6 :     if (AddMapping(parentPath.GetString(), fileName, hashName) != ADUMP_SUCCESS) {
      76            3 :         IDE_LOGE("Add mapping item [ %s ] failed", hashName.c_str());
      77              :     }
      78            6 :     realFilePath = parentPath.Concat(hashName).GetString();
      79            6 :     IDE_LOGW(
      80              :         "File name [ %s ] too long rename as [ %s ] and the mapping record in %s", fileName.c_str(),
      81              :         realFilePath.c_str(), MAPPING_FILE_NAME.c_str());
      82            6 :     fd_ = mmOpen2(realFilePath.c_str(), O_APPEND | M_RDWR | M_CREAT, M_IREAD | M_IWRITE);
      83            6 :     IDE_CTRL_VALUE_FAILED(fd_ >= 0, return ADUMP_FAILED, "Open hash file failed, fd: %d", fd_);
      84            3 :     return ADUMP_SUCCESS;
      85          151 : }
      86              : 
      87            0 : int32_t File::GetFileDiscriptor() const { return fd_; }
      88              : 
      89          120 : int32_t File::IsFileOpen() const
      90              : {
      91          120 :     if (fd_ == INVALID_FILE_FD) {
      92           19 :         return ADUMP_FAILED;
      93              :     }
      94          101 :     return ADUMP_SUCCESS;
      95              : }
      96              : 
      97          232 : int32_t File::Close()
      98              : {
      99          232 :     if (fd_ == INVALID_FILE_FD) {
     100           91 :         return ADUMP_SUCCESS;
     101              :     }
     102              : 
     103          141 :     const int32_t ret = mmClose(fd_);
     104          141 :     if (ret != EN_OK) {
     105            6 :         IDE_LOGW("Can not close file handle, file: %s, ret: %d.", filePath_.c_str(), ret);
     106            6 :         return ADUMP_FAILED;
     107              :     }
     108          135 :     fd_ = INVALID_FILE_FD;
     109          135 :     return ADUMP_SUCCESS;
     110              : }
     111              : 
     112          241 : int64_t File::Write(const char* const buffer, int64_t length) const
     113              : {
     114          241 :     mmSsize_t ret = 0;
     115          241 :     UINT32 reserve = static_cast<UINT32>(length);
     116              :     do {
     117          244 :         ret = mmWrite(fd_, const_cast<char*>(buffer) + (static_cast<UINT32>(length) - reserve), reserve);
     118          244 :         if ((ret == EN_ERROR) && (mmGetErrorCode() == EINTR)) {
     119            0 :             continue;
     120              :         }
     121          244 :         if (ret < 0 || static_cast<UINT32>(ret) > reserve) {
     122            9 :             IDE_LOGE("Write data failed, buff: %p, length: %ld, ret: %zd", buffer, length, ret);
     123            9 :             break;
     124              :         }
     125          235 :         reserve -= ret;
     126          235 :         if (reserve == 0) {
     127          232 :             break;
     128              :         }
     129              :     } while (true);
     130              : 
     131          241 :     return static_cast<int64_t>(ret);
     132              : }
     133              : 
     134           57 : int64_t File::Read(char* buffer, int64_t length) const
     135              : {
     136              :     mmSsize_t ret;
     137              :     do {
     138           57 :         ret = mmRead(fd_, buffer, static_cast<UINT32>(length));
     139           57 :     } while (ret == EN_ERROR && mmGetErrorCode() == EINTR);
     140              : 
     141           57 :     if (ret == EN_ERROR) {
     142            3 :         IDE_LOGE("Read data failed, buff: %p, length: %ld bytes, ret: %zd", buffer, length, ret);
     143              :     }
     144           57 :     return static_cast<int64_t>(ret);
     145              : }
     146              : 
     147           29 : int32_t File::Copy(const std::string& srcPath, const std::string& dstPath)
     148              : {
     149           29 :     IDE_LOGI("copy file from %s to %s", srcPath.c_str(), dstPath.c_str());
     150           29 :     File srcFile(srcPath, M_RDONLY);
     151           29 :     int32_t ret = srcFile.IsFileOpen();
     152           29 :     if (ret != ADUMP_SUCCESS) {
     153            6 :         IDE_LOGE("Open src file failed, file: %s", srcPath.c_str());
     154            6 :         return ret;
     155              :     }
     156              : 
     157           23 :     File dstFile(dstPath, M_CREAT | M_WRONLY | M_TRUNC, READ_WRITE_MODE);
     158           23 :     ret = dstFile.IsFileOpen();
     159           23 :     if (ret != ADUMP_SUCCESS) {
     160            4 :         IDE_LOGE("Open dst file failed, file: %s", dstPath.c_str());
     161            4 :         return ret;
     162              :     }
     163              : 
     164           19 :     char buffer[MAX_BUFFER_LENGTH] = {0};
     165           19 :     int64_t size = 0;
     166              :     do {
     167           54 :         size = srcFile.Read(buffer, MAX_BUFFER_LENGTH);
     168           54 :         if (size < 0) {
     169            0 :             IDE_LOGE("Read file failed, file: %s", srcPath.c_str());
     170            0 :             return ADUMP_FAILED;
     171              :         }
     172           54 :         IDE_LOGD("Read file size: %ld bytes", size);
     173           54 :         if (size > 0) {
     174           41 :             const auto writeSize = dstFile.Write(buffer, size);
     175           41 :             if (writeSize < 0) {
     176            6 :                 IDE_LOGE("Write file failed, file: %s", dstPath.c_str());
     177            6 :                 return ADUMP_FAILED;
     178              :             }
     179              :         }
     180           48 :     } while (size > 0);
     181           13 :     return ADUMP_SUCCESS;
     182           29 : }
     183              : 
     184              : /**
     185              :  * @brief       : add map item into mapping.csv
     186              :  * @param [in]  : filePath    file path
     187              :  * @param [in]  : hashName    hash value of file name
     188              :  * @return      : ADUMP_SUCCESS: success; ADUMP_FAILED: failed
     189              :  */
     190            9 : int32_t File::AddMapping(const std::string& filePath, const std::string& fileName, const std::string& hashName)
     191              : {
     192            9 :     IDE_CTRL_VALUE_FAILED(!filePath.empty(), return ADUMP_FAILED, "FilePath is empty");
     193            9 :     IDE_CTRL_VALUE_FAILED(!hashName.empty(), return ADUMP_FAILED, "HashName is empty");
     194              : 
     195            9 :     Path parentPath(filePath);
     196            9 :     std::string mappingFile = parentPath.Concat('/' + MAPPING_FILE_NAME).GetString();
     197            9 :     fd_ = mmOpen2(mappingFile.c_str(), O_APPEND | M_RDWR | M_CREAT, M_IRUSR | M_IWRITE);
     198            9 :     IDE_CTRL_VALUE_FAILED(fd_ >= 0, return ADUMP_FAILED, "Open mapping file failed, fd: %d", fd_);
     199              : 
     200            6 :     std::string mapping = hashName + ',' + fileName + '\n';
     201            6 :     uint32_t mappingLen = mapping.length();
     202            6 :     uint32_t residLen = mappingLen;
     203              : 
     204              :     do {
     205              :         mmSsize_t writeLen =
     206            6 :             mmWrite(fd_, const_cast<AdxStringBuffer>(mapping.c_str()) + (mappingLen - residLen), residLen);
     207            6 :         if (writeLen < 0) {
     208            0 :             IDE_LOGE("Write failed, info: %s, write length: %ld bytes", strerror(errno), writeLen);
     209            0 :             (void)Close();
     210            0 :             return ADUMP_FAILED;
     211              :         }
     212            6 :         if (residLen >= static_cast<uint32_t>(writeLen)) {
     213            3 :             residLen -= static_cast<uint32_t>(writeLen);
     214              :         } else {
     215            3 :             IDE_LOGE("Write failed, info: %s, write length larger than remaining length", strerror(errno));
     216            3 :             (void)Close();
     217            3 :             return ADUMP_FAILED;
     218              :         }
     219            3 :     } while (residLen != 0);
     220              : 
     221            3 :     (void)Close();
     222            3 :     return ADUMP_SUCCESS;
     223            9 : }
     224              : } // namespace Adx
        

Generated by: LCOV version 2.0-1