frameworks/native/services/fileinotify/FileInotify_M.cpp

191 lines
4.1 KiB
C++
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/*******************************
程序功能:解析/debug_ramdisk/mount.cfg配置文件把文件挂载到tmpfs内存中。避免频繁写入内部存储提高EMMC使用寿命。
mount.cfg格式如下
/data/user/0/com.ss.android.ugc.aweme.lite/databases/ss_app_log.db
/data/user/0/com.ss.android.ugc.aweme.lite/databases/ss_app_log.db-journal
********************************/
#define LOG_TAG "FileInotify"
#include <iostream>
#include <fstream>
#include <string>
#include <filesystem>
#include <utils/RefBase.h>
#include <utils/Log.h>
#include <cutils/properties.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <sys/inotify.h>
#include <pthread.h>
#include <sys/mount.h>
#include <sys/prctl.h>
#include <cstring>
#include <errno.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#define MOUNT_INFO_DEV "/dev/minfo"
#define CMD_BASE 0xCBAABC10
#define FK_IS_GET_POWER2 (CMD_BASE + 12)
#define M_IOCTL_MAGIC 0xB3
#define MOUNT_INFO _IOW(M_IOCTL_MAGIC, 0x41, unsigned long)
#define MOUNT_CFG "/debug_ramdisk/mount.cfg" //配置文件路径
#define MOUNT_MAX_LINE 64 //最大的挂载数
#define READ_LINE 128 //文件路径缓存大小
struct fileinotify_info{
int containerid; //容器ID
char src[MOUNT_MAX_LINE][READ_LINE]; //挂载原路径
char dst[MOUNT_MAX_LINE][READ_LINE]; //挂载目标路径
int flag[MOUNT_MAX_LINE]; //挂载标记0x00:未挂载0xAA:已挂载
int line; //挂载文件数量
}__attribute__ ((packed));
#if 0
void createFile(const std::string& path)
{
namespace fs = std::filesystem;
//确保目录存在,如果不存在则创建
fs::create_directories(fs::path(path).parent_path());
//创建文件
std::ofstream file(path);
if (file.is_open()) {
file.close();
}
}
#else
bool createDirectory(const std::string &path)
{
size_t pos = 0;
std::string currentPath;
while ((pos = path.find('/', pos)) != std::string::npos)
{
currentPath = path.substr(0, pos++);
if (currentPath.empty()) continue;
// 检查当前目录是否存在
if (mkdir(currentPath.c_str(), 0777) != 0) {
if (errno != EEXIST) { // 如果目录不存在且无法创建
return false;
}
}
}
// 创建完整路径
if (mkdir(path.c_str(), 0777) != 0 && errno != EEXIST)
{
return false;
}
return true;
}
bool createFile(const std::string &filePath) {
// 提取目录路径
size_t lastSlash = filePath.find_last_of('/');
if (lastSlash != std::string::npos)
{
std::string directory = filePath.substr(0, lastSlash);
// 创建目录
if (!createDirectory(directory)) {
return false;
}
}
// 创建文件
std::ofstream ofs(filePath);
if (!ofs) {
return false;
}
ofs.close();
return true;
}
#endif
int mount_info_init(struct fileinotify_info *info)
{
const std::string str = "/data_mirror";
int i = 0;
std::ifstream file(MOUNT_CFG);
if (!file.is_open()) {
return 0;
}
std::string line;
while (std::getline(file, line)) {
//std::cout << line << std::endl;
if(line.size() > 0)
{
//create file
createFile(str + line);
//save mount info
sprintf(info->dst[i], "%s", line.c_str());
sprintf(info->src[i], "/data_mirror%s", line.c_str());
info->line = i + 1;
i++;
}
}
file.close();
return info->line;
}
int file_exists(const char *filename)
{
return access(filename, F_OK) == 0;
}
int main(void)
{
struct fileinotify_info info;
char buf[READ_LINE];
int fd, ret;
int line;
//selinux
prctl(FK_IS_GET_POWER2, 0, 0, 0);
//file_exists
if(!file_exists(MOUNT_CFG))
goto OUT;
//mount info init
umask(0000);
mount_info_init(&info);
//for(int i = 0; i < info.line; i++)
//{
// ALOGD("line=%d, src=%s, dst=%s\n", i, info.src[i], info.dst[i]);
//}
fd = open(MOUNT_INFO_DEV, O_RDWR | O_NONBLOCK | O_NOCTTY);
if(fd < 0)
{
ALOGD("open minfo fail.\n");
return -1;
}
ret = ioctl(fd, MOUNT_INFO, &info);
if(ret != 0)
{
close(fd);
ALOGD("ioctl minfo fail.\n");
return -2;
}
close(fd);
OUT:
return 0;
}