mirror of
https://github.com/Tencent/MMKV.git
synced 2026-10-17 04:30:56 +08:00
add copyFile() & copyFileContent() for POSIX env
This commit is contained in:
+2
-2
@@ -332,7 +332,7 @@ string MMKV::cryptKey() const {
|
||||
if (m_crypter) {
|
||||
char key[AES_KEY_LEN];
|
||||
m_crypter->getKey(key);
|
||||
return string(key, strnlen(key, AES_KEY_LEN));
|
||||
return {key, strnlen(key, AES_KEY_LEN)};
|
||||
}
|
||||
return "";
|
||||
}
|
||||
@@ -1220,7 +1220,7 @@ static string md5(const basic_string<T> &value) {
|
||||
snprintf(tmp, sizeof(tmp), "%2.2x", ch);
|
||||
strcat(buf, tmp);
|
||||
}
|
||||
return string(buf);
|
||||
return {buf};
|
||||
}
|
||||
|
||||
static MMKVPath_t encodeFilePath(const string &mmapID) {
|
||||
|
||||
+93
-3
@@ -303,16 +303,106 @@ size_t getPageSize() {
|
||||
|
||||
#ifndef MMKV_APPLE
|
||||
|
||||
static pair<MMKVPath_t, int> createUniqueTempFile(const char *prefix) {
|
||||
char path[PATH_MAX];
|
||||
snprintf(path, PATH_MAX, "%s%s.XXXXX", P_tmpdir, prefix);
|
||||
|
||||
auto fd = mkstemp(path);
|
||||
if (fd < 0) {
|
||||
MMKVError("fail to create unique temp file %s, %d(%s)", path, errno, strerror(errno));
|
||||
return {"", fd};
|
||||
}
|
||||
return {MMKVPath_t(path), fd};
|
||||
}
|
||||
|
||||
bool copyFile(const MMKVPath_t &srcPath, const MMKVPath_t &dstPath) {
|
||||
return false;
|
||||
auto pair = createUniqueTempFile("MMKV");
|
||||
auto tmpFD = pair.second;
|
||||
auto &tmpPath = pair.first;
|
||||
if (tmpFD < 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
bool ret = false;
|
||||
if (copyFileContent(srcPath, tmpFD)) {
|
||||
MMKVInfo("copyfile [%s] to [%s]", srcPath.c_str(), tmpPath.c_str());
|
||||
ret = (::rename(tmpPath.c_str(), dstPath.c_str()) == 0);
|
||||
if (ret) {
|
||||
MMKVInfo("copyfile [%s] to [%s] finish.", srcPath.c_str(), dstPath.c_str());
|
||||
} else {
|
||||
MMKVError("fail to rename [%s] to [%s]", tmpPath.c_str(), dstPath.c_str());
|
||||
}
|
||||
}
|
||||
|
||||
::close(tmpFD);
|
||||
::unlink(tmpPath.c_str());
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
bool copyFileContent(const MMKVPath_t &srcPath, const MMKVPath_t &dstPath) {
|
||||
return false;
|
||||
auto dstFd = open(dstPath.c_str(), O_WRONLY | O_CREAT | O_TRUNC, S_IRWXU);
|
||||
if (dstFd < 0) {
|
||||
MMKVError("fail to open [%s], %d(%s)", dstPath.c_str(), errno, strerror(errno));
|
||||
return false;
|
||||
}
|
||||
auto ret = copyFileContent(srcPath, dstFd);
|
||||
if (!ret) {
|
||||
MMKVError("fail to copyfile(): target file %s", dstPath.c_str());
|
||||
} else {
|
||||
MMKVInfo("copy content from %s to [%s] finish", srcPath.c_str(), dstPath.c_str());
|
||||
}
|
||||
::close(dstFd);
|
||||
return ret;
|
||||
}
|
||||
|
||||
bool copyFileContent(const MMKVPath_t &srcPath, MMKVFileHandle_t dstFD) {
|
||||
return false;
|
||||
if (dstFD < 0) {
|
||||
return false;
|
||||
}
|
||||
bool ret = false;
|
||||
char *buffer = nullptr;
|
||||
auto bufferSize = getPageSize();
|
||||
auto srcFd = open(srcPath.c_str(), O_RDONLY, S_IRWXU);
|
||||
if (srcFd < 0) {
|
||||
MMKVError("fail to open [%s], %d(%s)", srcPath.c_str(), errno, strerror(errno));
|
||||
return false;
|
||||
}
|
||||
buffer = (char *)malloc(bufferSize);
|
||||
if (!buffer) {
|
||||
MMKVError("fail to malloc size %zu, %d(%s)", bufferSize, errno, strerror(errno));
|
||||
goto errorOut;
|
||||
}
|
||||
|
||||
// the POSIX standard don't have sendfile()/fcopyfile() equivalent, have to do it the hard way
|
||||
while (true) {
|
||||
auto sizeRead = read(srcFd, buffer, bufferSize);
|
||||
if (sizeRead < 0) {
|
||||
MMKVError("fail to read file [%s], %d(%s)", srcPath.c_str(), errno, strerror(errno));
|
||||
goto errorOut;
|
||||
}
|
||||
|
||||
size_t totalWrite = 0;
|
||||
do {
|
||||
auto sizeWrite = write(dstFD, buffer + totalWrite, sizeRead - totalWrite);
|
||||
if (sizeWrite < 0) {
|
||||
MMKVError("fail to write fd [%d], %d(%s)", dstFD, errno, strerror(errno));
|
||||
goto errorOut;
|
||||
}
|
||||
totalWrite += sizeWrite;
|
||||
} while (totalWrite < sizeRead);
|
||||
|
||||
if (sizeRead < bufferSize) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
ret = true;
|
||||
MMKVInfo("copy content from %s to fd[%d] finish", srcPath.c_str(), dstFD);
|
||||
|
||||
errorOut:
|
||||
free(buffer);
|
||||
::close(srcFd);
|
||||
return ret;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
@@ -180,7 +180,7 @@ string ASharedMemory_getName(int fd) {
|
||||
MMKVError("fail to get ashmem name:%d, %s", fd, strerror(errno));
|
||||
return "";
|
||||
}
|
||||
return string(name);
|
||||
return {name};
|
||||
}
|
||||
|
||||
} // namespace mmkv
|
||||
|
||||
@@ -110,9 +110,10 @@ bool copyFileContent(const MMKVPath_t &srcPath, const MMKVPath_t &dstPath) {
|
||||
auto ret = copyFileContent(srcPath, dstFD);
|
||||
if (!ret) {
|
||||
MMKVError("fail to copyfile(): target file %s", dstPath.c_str());
|
||||
} else {
|
||||
MMKVInfo("copy content from %s to fd[%s] finish", srcPath.c_str(), dstPath.c_str());
|
||||
}
|
||||
::close(dstFD);
|
||||
MMKVInfo("copy content from %s to fd[%s] finish", srcPath.c_str(), dstPath.c_str());
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user