一、问题描述
连接两个u盘;一个为NTFS,一个为FAT32;从NTFS可以向FAT32拷贝,反之报错“只读文件系统”。
二、问题原因
mount
/dev/block/vold/8:1 /mnt/usb/843E1E3A3E1E2628 ntfs ro,dirsync,nosuid,nodev,noexec,relatime,uid=1023,gid=1023,umask=02,nls=utf8,errors=continu
e,mft_zone_multiplier=1 0 0
ll /mnt/usb/
dr-xr-xr-x media_rw media_rw 2015-04-03 14:23 843E1E3A3E1E2628
问题有两个:
1.NTFS格式U盘挂载为READONLY;
2.挂载点目录权限问题
三、问题解决
1.修复问题1
移植fstype_support/android_external_ntfs-3g,使用ntfs-3g挂载。
system/vold/Ntfs.cpp
#define NTFS_3G_PATH "/system/bin/ntfs-3g" //add by tank
int Ntfs::doMount(const char *fsPath, const char *mountPoint,
bool ro, bool remount, int ownerUid, int ownerGid,
int permMask) {
int rc;
unsigned long flags;
char mountData[255];
flags = MS_NODEV | MS_NOEXEC | MS_NOSUID | MS_DIRSYNC;
flags |= (ro ? MS_RDONLY : 0);
flags |= (remount ? MS_REMOUNT : 0);
#if 0
char value[PROPERTY_VALUE_MAX];
property_get("persist.sampling_profiler", value, "");
if (value[0] == '1') {
SLOGW("The SD card is world-writable because the"
" 'persist.sampling_profiler' system property is set to '1'.");
permMask = 0;
}
sprintf(mountData,
"uid=%d,gid=%d,fmask=%o,dmask=%o,nls=utf8",
ownerUid, ownerGid, permMask, permMask);
rc = mount(fsPath, mountPoint, "ntfs3g", flags, mountData);
#else
SLOGI("mount ntfs block device by tcl ntfs ntfs-3g");
sprintf(mountData,"locale=utf8,uid=%d,gid=%d,fmask=%o,dmask=%o,inherit, atime",\
ownerUid, ownerGid, permMask, permMask);
const char *args[16];
args[0] = NTFS_3G_PATH;
args[1] = fsPath;
args[2] = mountPoint;
args[3] = "-o";
args[4] = mountData;
args[5] = NULL;
rc = logwrap(5, args, 1);
#endif
if (rc) {
SLOGE("%s appears to be a read only filesystem - retrying mount RO", fsPath);
flags |= MS_RDONLY;
rc = mount(fsPath, mountPoint, "ntfs", flags, mountData);
}
return rc;
}
2.修复问题2
system/vold/Volume.cpp
int Volume::mountVol() {
if (isFatFs) {
if (Fat::doMount(devicePath, getMountpoint(), false, false, false,
/*AID_MEDIA_RW*/AID_SYSTEM, /*AID_MEDIA_RW*/AID_SDCARD_RW, /*permMask*/0002, true)) { //modify by tank
SLOGE("%s failed to mount via VFAT (%s)\n", devicePath, strerror(errno));
isFatFs = false;
} else {
isExtFs = false;
isExfatFs = false;
}
}
}