fs: sdfat: Update to version 2.1.8

Taken from SM-G965F_PP_Opensource kernel (G965FXXU2CRLI)
This commit is contained in:
derfelot 2019-01-06 00:33:53 +01:00 committed by Andreas Schneider
parent daca7c28f2
commit 46b831137b
12 changed files with 277 additions and 145 deletions

7
api.c
View File

@ -478,6 +478,13 @@ void fsapi_invalidate_extent(struct inode *inode)
} }
EXPORT_SYMBOL(fsapi_invalidate_extent); EXPORT_SYMBOL(fsapi_invalidate_extent);
/* check device is ejected */
s32 fsapi_check_bdi_valid(struct super_block *sb)
{
return fscore_check_bdi_valid(sb);
}
EXPORT_SYMBOL(fsapi_check_bdi_valid);
#ifdef CONFIG_SDFAT_DFR #ifdef CONFIG_SDFAT_DFR

3
api.h
View File

@ -355,6 +355,9 @@ u32 fsapi_get_au_stat(struct super_block *sb, s32 mode);
/* extent cache functions */ /* extent cache functions */
void fsapi_invalidate_extent(struct inode *inode); void fsapi_invalidate_extent(struct inode *inode);
/* bdev management */
s32 fsapi_check_bdi_valid(struct super_block *sb);
#ifdef CONFIG_SDFAT_DFR #ifdef CONFIG_SDFAT_DFR
/*----------------------------------------------------------------------*/ /*----------------------------------------------------------------------*/
/* Defragmentation related */ /* Defragmentation related */

15
core.c
View File

@ -1621,6 +1621,12 @@ s32 fscore_shutdown(void)
return 0; return 0;
} }
/* check device is ejected */
s32 fscore_check_bdi_valid(struct super_block *sb)
{
return bdev_check_bdi_valid(sb);
}
static bool is_exfat(pbr_t *pbr) static bool is_exfat(pbr_t *pbr)
{ {
int i = 53; int i = 53;
@ -1703,6 +1709,7 @@ s32 fscore_mount(struct super_block *sb)
pbr_t *p_pbr; pbr_t *p_pbr;
struct buffer_head *tmp_bh = NULL; struct buffer_head *tmp_bh = NULL;
struct gendisk *disk = sb->s_bdev->bd_disk; struct gendisk *disk = sb->s_bdev->bd_disk;
struct hd_struct *part = sb->s_bdev->bd_part;
struct sdfat_mount_options *opts = &(SDFAT_SB(sb)->options); struct sdfat_mount_options *opts = &(SDFAT_SB(sb)->options);
FS_INFO_T *fsi = &(SDFAT_SB(sb)->fsi); FS_INFO_T *fsi = &(SDFAT_SB(sb)->fsi);
@ -1802,9 +1809,11 @@ free_bh:
"misaligned" : "aligned"); "misaligned" : "aligned");
sdfat_log_msg(sb, KERN_INFO, sdfat_log_msg(sb, KERN_INFO,
"detected volume size : %llu MB (disk_size : %llu MB)", "detected volume size : %llu KB (disk : %llu KB, "
fsi->num_sectors >> 11, "part : %llu KB)",
disk ? (u64)((disk->part0.nr_sects) >> 11) : 0); (fsi->num_sectors * (sb->s_blocksize >> SECTOR_SIZE_BITS)) >> 1,
disk ? (u64)((disk->part0.nr_sects) >> 1) : 0,
part ? (u64)((part->nr_sects) >> 1) : 0);
ret = load_upcase_table(sb); ret = load_upcase_table(sb);
if (ret) { if (ret) {

3
core.h
View File

@ -70,6 +70,9 @@ typedef struct {
s32 fscore_init(void); s32 fscore_init(void);
s32 fscore_shutdown(void); s32 fscore_shutdown(void);
/* bdev management */
s32 fscore_check_bdi_valid(struct super_block *sb);
/* chain management */ /* chain management */
s32 chain_cont_cluster(struct super_block *sb, u32 chain, u32 len); s32 chain_cont_cluster(struct super_block *sb, u32 chain, u32 len);

View File

@ -1323,8 +1323,9 @@ static sector_t __calc_hidden_sect(struct super_block *sb)
hidden = bdev->bd_part->start_sect; hidden = bdev->bd_part->start_sect;
/* a disk device, not a partition */ /* a disk device, not a partition */
if (!hidden) { if (!hidden) {
ASSERT(bdev == bdev->bd_contains); if (bdev != bdev->bd_contains)
ASSERT(!bdev->bd_part->partno); sdfat_log_msg(sb, KERN_WARNING,
"hidden(0), but disk has a partition table");
goto out; goto out;
} }
@ -1334,8 +1335,8 @@ static sector_t __calc_hidden_sect(struct super_block *sb)
} }
out: out:
sdfat_log_msg(sb, KERN_INFO, "start_sect of partition : %lld", sdfat_log_msg(sb, KERN_INFO, "start_sect of part(%d) : %lld",
(s64)hidden); bdev ? bdev->bd_part->partno : -1, (s64)hidden);
return hidden; return hidden;
} }

22
misc.c
View File

@ -43,11 +43,23 @@
#include "version.h" #include "version.h"
#ifdef CONFIG_SDFAT_SUPPORT_STLOG #ifdef CONFIG_SDFAT_SUPPORT_STLOG
#ifdef CONFIG_PROC_FSLOG
#include <linux/fslog.h>
#else
#include <linux/stlog.h> #include <linux/stlog.h>
#endif
#else #else
#define ST_LOG(fmt, ...) #define ST_LOG(fmt, ...)
#endif #endif
/*************************************************************************
* FUNCTIONS WHICH HAS KERNEL VERSION DEPENDENCY
*************************************************************************/
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 12, 0)
#define CURRENT_TIME_SEC timespec_trunc(current_kernel_time(), NSEC_PER_SEC)
#endif
/* /*
* sdfat_fs_error reports a file system problem that might indicate fa data * sdfat_fs_error reports a file system problem that might indicate fa data
* corruption/inconsistency. Depending on 'errors' mount option the * corruption/inconsistency. Depending on 'errors' mount option the
@ -84,6 +96,7 @@ void __sdfat_fs_error(struct super_block *sb, int report, const char *fmt, ...)
sb->s_id, MAJOR(bd_dev), MINOR(bd_dev)); sb->s_id, MAJOR(bd_dev), MINOR(bd_dev));
} else if (opts->errors == SDFAT_ERRORS_RO && !(sb->s_flags & MS_RDONLY)) { } else if (opts->errors == SDFAT_ERRORS_RO && !(sb->s_flags & MS_RDONLY)) {
sb->s_flags |= MS_RDONLY; sb->s_flags |= MS_RDONLY;
sdfat_statistics_set_mnt_ro();
pr_err("[SDFAT](%s[%d:%d]): Filesystem has been set " pr_err("[SDFAT](%s[%d:%d]): Filesystem has been set "
"read-only\n", sb->s_id, MAJOR(bd_dev), MINOR(bd_dev)); "read-only\n", sb->s_id, MAJOR(bd_dev), MINOR(bd_dev));
#ifdef CONFIG_SDFAT_SUPPORT_STLOG #ifdef CONFIG_SDFAT_SUPPORT_STLOG
@ -253,15 +266,9 @@ void sdfat_time_unix2fat(struct sdfat_sb_info *sbi, struct timespec *ts,
TIMESTAMP_T *tm_now(struct sdfat_sb_info *sbi, TIMESTAMP_T *tp) TIMESTAMP_T *tm_now(struct sdfat_sb_info *sbi, TIMESTAMP_T *tp)
{ {
struct timespec ts; struct timespec ts = CURRENT_TIME_SEC;
DATE_TIME_T dt; DATE_TIME_T dt;
#if LINUX_VERSION_CODE < KERNEL_VERSION(4,8,0)
ts = CURRENT_TIME_SEC;
#else
ktime_get_real_ts(&ts);
#endif
sdfat_time_unix2fat(sbi, &ts, &dt); sdfat_time_unix2fat(sbi, &ts, &dt);
tp->year = dt.Year; tp->year = dt.Year;
@ -384,3 +391,4 @@ void __sdfat_dmsg(int level, const char *fmt, ...)
#endif #endif
} }
#endif #endif

79
mpage.c
View File

@ -78,6 +78,27 @@ static void __mpage_write_end_io(struct bio *bio, int err);
/************************************************************************* /*************************************************************************
* FUNCTIONS WHICH HAS KERNEL VERSION DEPENDENCY * FUNCTIONS WHICH HAS KERNEL VERSION DEPENDENCY
*************************************************************************/ *************************************************************************/
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 14, 0)
/* EMPTY */
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 14, 0) */
static inline void bio_set_dev(struct bio *bio, struct block_device *bdev)
{
bio->bi_bdev = bdev;
}
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 10, 0)
static inline void __sdfat_clean_bdev_aliases(struct block_device *bdev, sector_t block)
{
clean_bdev_aliases(bdev, block, 1);
}
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4,10,0) */
static inline void __sdfat_clean_bdev_aliases(struct block_device *bdev, sector_t block)
{
unmap_underlying_metadata(bdev, block);
}
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 8, 0) #if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 8, 0)
static inline void __sdfat_submit_bio_write2(int flags, struct bio *bio) static inline void __sdfat_submit_bio_write2(int flags, struct bio *bio)
{ {
@ -91,24 +112,6 @@ static inline void __sdfat_submit_bio_write2(int flags, struct bio *bio)
} }
#endif #endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 3, 0)
static void mpage_write_end_io(struct bio *bio)
{
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 13, 0)
__mpage_write_end_io(bio, bio->bi_status);
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 13, 0) */
__mpage_write_end_io(bio, bio->bi_error);
#endif
}
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4,3,0) */
static void mpage_write_end_io(struct bio *bio, int err)
{
if (test_bit(BIO_UPTODATE, &bio->bi_flags))
err = 0;
__mpage_write_end_io(bio, err);
}
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 1, 0) #if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 1, 0)
static inline int bio_get_nr_vecs(struct block_device *bdev) static inline int bio_get_nr_vecs(struct block_device *bdev)
{ {
@ -160,6 +163,28 @@ static inline void __sdfat_set_bio_size(struct bio *bio, unsigned int size)
} }
#endif #endif
/*************************************************************************
* MORE FUNCTIONS WHICH HAS KERNEL VERSION DEPENDENCY
*************************************************************************/
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 13, 0)
static void mpage_write_end_io(struct bio *bio)
{
__mpage_write_end_io(bio, blk_status_to_errno(bio->bi_status));
}
#elif LINUX_VERSION_CODE >= KERNEL_VERSION(4, 3, 0)
static void mpage_write_end_io(struct bio *bio)
{
__mpage_write_end_io(bio, bio->bi_error);
}
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4,3,0) */
static void mpage_write_end_io(struct bio *bio, int err)
{
if (test_bit(BIO_UPTODATE, &bio->bi_flags))
err = 0;
__mpage_write_end_io(bio, err);
}
#endif
/* __check_dfr_on() and __dfr_writepage_end_io() functions /* __check_dfr_on() and __dfr_writepage_end_io() functions
* are copied from sdfat.c * are copied from sdfat.c
* Each function should be same perfectly * Each function should be same perfectly
@ -281,11 +306,7 @@ mpage_alloc(struct block_device *bdev,
} }
if (bio) { if (bio) {
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4,14,0)
bio_set_dev(bio, bdev); bio_set_dev(bio, bdev);
#else
bio->bi_bdev = bdev;
#endif
__sdfat_set_bio_sector(bio, first_sector); __sdfat_set_bio_sector(bio, first_sector);
} }
return bio; return bio;
@ -369,11 +390,7 @@ static int sdfat_mpage_writepage(struct page *page,
if (buffer_new(bh)) { if (buffer_new(bh)) {
clear_buffer_new(bh); clear_buffer_new(bh);
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 10, 0) __sdfat_clean_bdev_aliases(bh->b_bdev, bh->b_blocknr);
clean_bdev_bh_alias(bh);
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 10, 0) */
unmap_underlying_metadata(bh->b_bdev, bh->b_blocknr);
#endif
} }
} }
@ -423,12 +440,7 @@ static int sdfat_mpage_writepage(struct page *page,
goto confused; goto confused;
if (buffer_new(&map_bh)) if (buffer_new(&map_bh))
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 10, 0) __sdfat_clean_bdev_aliases(map_bh.b_bdev, map_bh.b_blocknr);
clean_bdev_bh_alias(&map_bh);
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 10, 0) */
unmap_underlying_metadata(map_bh.b_bdev,
map_bh.b_blocknr);
#endif
if (buffer_boundary(&map_bh)) { if (buffer_boundary(&map_bh)) {
boundary_block = map_bh.b_blocknr; boundary_block = map_bh.b_blocknr;
boundary_bdev = map_bh.b_bdev; boundary_bdev = map_bh.b_bdev;
@ -620,3 +632,4 @@ int sdfat_mpage_writepages(struct address_space *mapping,
} }
#endif /* CONFIG_SDFAT_ALIGNED_MPAGE_WRITE */ #endif /* CONFIG_SDFAT_ALIGNED_MPAGE_WRITE */

263
sdfat.c
View File

@ -68,9 +68,6 @@
/* skip iterating emit_dots when dir is empty */ /* skip iterating emit_dots when dir is empty */
#define ITER_POS_FILLED_DOTS (2) #define ITER_POS_FILLED_DOTS (2)
#if LINUX_VERSION_CODE < KERNEL_VERSION(4,8,0)
#define current_time(x) (CURRENT_TIME_SEC)
#endif
/* type index declare at sdfat.h */ /* type index declare at sdfat.h */
const char *FS_TYPE_STR[] = { const char *FS_TYPE_STR[] = {
"auto", "auto",
@ -112,6 +109,7 @@ static void sdfat_free_namebuf(DENTRY_NAMEBUF_T *nb);
/************************************************************************* /*************************************************************************
* INNER FUNCTIONS FOR FUNCTIONS WHICH HAS KERNEL VERSION DEPENDENCY * INNER FUNCTIONS FOR FUNCTIONS WHICH HAS KERNEL VERSION DEPENDENCY
*************************************************************************/ *************************************************************************/
static int __sdfat_getattr(struct inode *inode, struct kstat *stat);
static void __sdfat_writepage_end_io(struct bio *bio, int err); static void __sdfat_writepage_end_io(struct bio *bio, int err);
static inline void __lock_super(struct super_block *sb); static inline void __lock_super(struct super_block *sb);
static inline void __unlock_super(struct super_block *sb); static inline void __unlock_super(struct super_block *sb);
@ -140,6 +138,51 @@ static int __sdfat_cmpi(const struct dentry *dentry, unsigned int len,
/************************************************************************* /*************************************************************************
* FUNCTIONS WHICH HAS KERNEL VERSION DEPENDENCY * FUNCTIONS WHICH HAS KERNEL VERSION DEPENDENCY
*************************************************************************/ *************************************************************************/
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 14, 0)
/* EMPTY */
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 14, 0) */
static inline void bio_set_dev(struct bio *bio, struct block_device *bdev)
{
bio->bi_bdev = bdev;
}
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 12, 0)
#define CURRENT_TIME_SEC timespec_trunc(current_kernel_time(), NSEC_PER_SEC)
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 11, 0)
static int sdfat_getattr(const struct path *path, struct kstat *stat,
u32 request_mask, unsigned int query_flags)
{
struct inode *inode = d_backing_inode(path->dentry);
return __sdfat_getattr(inode, stat);
}
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 11, 0) */
static int sdfat_getattr(struct vfsmount *mnt, struct dentry *dentry, struct kstat *stat)
{
struct inode *inode = dentry->d_inode;
return __sdfat_getattr(inode, stat);
}
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 10, 0)
static inline void __sdfat_clean_bdev_aliases(struct block_device *bdev, sector_t block)
{
clean_bdev_aliases(bdev, block, 1);
}
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4,10,0) */
static inline void __sdfat_clean_bdev_aliases(struct block_device *bdev, sector_t block)
{
unmap_underlying_metadata(bdev, block);
}
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 9, 0) #if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 9, 0)
static int sdfat_rename(struct inode *old_dir, struct dentry *old_dentry, static int sdfat_rename(struct inode *old_dir, struct dentry *old_dentry,
struct inode *new_dir, struct dentry *new_dentry, struct inode *new_dir, struct dentry *new_dentry,
@ -219,25 +262,6 @@ static inline void inode_unlock(struct inode *inode)
#endif #endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 3, 0)
static void sdfat_writepage_end_io(struct bio *bio)
{
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 13, 0)
__sdfat_writepage_end_io(bio, bio->bi_status);
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 13, 0) */
__sdfat_writepage_end_io(bio, bio->bi_error);
#endif
}
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 3, 0) */
static void sdfat_writepage_end_io(struct bio *bio, int err)
{
if (test_bit(BIO_UPTODATE, &bio->bi_flags))
err = 0;
__sdfat_writepage_end_io(bio, err);
}
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 16, 0) #if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 16, 0)
static inline int sdfat_remount_syncfs(struct super_block *sb) static inline int sdfat_remount_syncfs(struct super_block *sb)
{ {
@ -870,6 +894,26 @@ static int sdfat_file_fsync(struct file *filp, int datasync)
/************************************************************************* /*************************************************************************
* MORE FUNCTIONS WHICH HAS KERNEL VERSION DEPENDENCY * MORE FUNCTIONS WHICH HAS KERNEL VERSION DEPENDENCY
*************************************************************************/ *************************************************************************/
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 13, 0)
static void sdfat_writepage_end_io(struct bio *bio)
{
__sdfat_writepage_end_io(bio, blk_status_to_errno(bio->bi_status));
}
#elif LINUX_VERSION_CODE >= KERNEL_VERSION(4, 3, 0)
static void sdfat_writepage_end_io(struct bio *bio)
{
__sdfat_writepage_end_io(bio, bio->bi_error);
}
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 3, 0) */
static void sdfat_writepage_end_io(struct bio *bio, int err)
{
if (test_bit(BIO_UPTODATE, &bio->bi_flags))
err = 0;
__sdfat_writepage_end_io(bio, err);
}
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 8, 0) #if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 8, 0)
static int sdfat_cmp(const struct dentry *dentry, static int sdfat_cmp(const struct dentry *dentry,
unsigned int len, const char *str, const struct qstr *name) unsigned int len, const char *str, const struct qstr *name)
@ -910,30 +954,6 @@ static int sdfat_cmpi(const struct dentry *parent, const struct inode *pinode,
} }
#endif #endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 5, 0)
static const char *sdfat_follow_link(struct dentry *dentry, struct inode *inode, struct delayed_call *done)
{
struct sdfat_inode_info *ei = SDFAT_I(inode);
return (char *)(ei->target);
}
#elif LINUX_VERSION_CODE >= KERNEL_VERSION(4, 2, 0)
static const char *sdfat_follow_link(struct dentry *dentry, void **cookie)
{
struct sdfat_inode_info *ei = SDFAT_I(dentry->d_inode);
return *cookie = (char *)(ei->target);
}
#else
static void *sdfat_follow_link(struct dentry *dentry, struct nameidata *nd)
{
struct sdfat_inode_info *ei = SDFAT_I(dentry->d_inode);
nd_set_link(nd, (char *)(ei->target));
return NULL;
}
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 7, 0) #if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 7, 0)
static ssize_t sdfat_direct_IO(struct kiocb *iocb, struct iov_iter *iter) static ssize_t sdfat_direct_IO(struct kiocb *iocb, struct iov_iter *iter)
@ -1041,6 +1061,31 @@ static inline ssize_t __sdfat_blkdev_direct_IO(int rw, struct kiocb *iocb,
#endif #endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 5, 0)
static const char *sdfat_follow_link(struct dentry *dentry, struct inode *inode, struct delayed_call *done)
{
struct sdfat_inode_info *ei = SDFAT_I(inode);
return (char *)(ei->target);
}
#elif LINUX_VERSION_CODE >= KERNEL_VERSION(4, 2, 0)
static const char *sdfat_follow_link(struct dentry *dentry, void **cookie)
{
struct sdfat_inode_info *ei = SDFAT_I(dentry->d_inode);
return *cookie = (char *)(ei->target);
}
#else
static void *sdfat_follow_link(struct dentry *dentry, struct nameidata *nd)
{
struct sdfat_inode_info *ei = SDFAT_I(dentry->d_inode);
nd_set_link(nd, (char *)(ei->target));
return NULL;
}
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 6, 0) #if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 6, 0)
static int sdfat_create(struct inode *dir, struct dentry *dentry, umode_t mode, static int sdfat_create(struct inode *dir, struct dentry *dentry, umode_t mode,
bool excl) bool excl)
@ -2221,6 +2266,16 @@ static long sdfat_generic_ioctl(struct file *filp, unsigned int cmd, unsigned lo
return sdfat_dbg_ioctl(inode, filp, cmd, arg); return sdfat_dbg_ioctl(inode, filp, cmd, arg);
} }
static int __sdfat_getattr(struct inode *inode, struct kstat *stat)
{
TMSG("%s entered\n", __func__);
generic_fillattr(inode, stat);
stat->blksize = SDFAT_SB(inode->i_sb)->fsi.cluster_size;
TMSG("%s exited\n", __func__);
return 0;
}
static void __sdfat_writepage_end_io(struct bio *bio, int err) static void __sdfat_writepage_end_io(struct bio *bio, int err)
{ {
@ -2313,6 +2368,7 @@ static int __sdfat_create(struct inode *dir, struct dentry *dentry)
{ {
struct super_block *sb = dir->i_sb; struct super_block *sb = dir->i_sb;
struct inode *inode; struct inode *inode;
struct timespec ts;
FILE_ID_T fid; FILE_ID_T fid;
loff_t i_pos; loff_t i_pos;
int err; int err;
@ -2321,6 +2377,8 @@ static int __sdfat_create(struct inode *dir, struct dentry *dentry)
TMSG("%s entered\n", __func__); TMSG("%s entered\n", __func__);
ts = CURRENT_TIME_SEC;
err = fsapi_create(dir, (u8 *) dentry->d_name.name, FM_REGULAR, &fid); err = fsapi_create(dir, (u8 *) dentry->d_name.name, FM_REGULAR, &fid);
if (err) if (err)
goto out; goto out;
@ -2328,7 +2386,7 @@ static int __sdfat_create(struct inode *dir, struct dentry *dentry)
__lock_d_revalidate(dentry); __lock_d_revalidate(dentry);
dir->i_version++; dir->i_version++;
dir->i_ctime = dir->i_mtime = dir->i_atime = current_time(dir); dir->i_ctime = dir->i_mtime = dir->i_atime = ts;
if (IS_DIRSYNC(dir)) if (IS_DIRSYNC(dir))
(void) sdfat_sync_inode(dir); (void) sdfat_sync_inode(dir);
else else
@ -2341,7 +2399,7 @@ static int __sdfat_create(struct inode *dir, struct dentry *dentry)
goto out; goto out;
} }
inode->i_version++; inode->i_version++;
inode->i_mtime = inode->i_atime = inode->i_ctime = current_time(inode); inode->i_mtime = inode->i_atime = inode->i_ctime = ts;
/* timestamp is already written, so mark_inode_dirty() is unneeded. */ /* timestamp is already written, so mark_inode_dirty() is unneeded. */
d_instantiate(dentry, inode); d_instantiate(dentry, inode);
@ -2475,12 +2533,15 @@ static int sdfat_unlink(struct inode *dir, struct dentry *dentry)
{ {
struct inode *inode = dentry->d_inode; struct inode *inode = dentry->d_inode;
struct super_block *sb = dir->i_sb; struct super_block *sb = dir->i_sb;
struct timespec ts;
int err; int err;
__lock_super(sb); __lock_super(sb);
TMSG("%s entered\n", __func__); TMSG("%s entered\n", __func__);
ts = CURRENT_TIME_SEC;
SDFAT_I(inode)->fid.size = i_size_read(inode); SDFAT_I(inode)->fid.size = i_size_read(inode);
__cancel_dfr_work(inode, 0, SDFAT_I(inode)->fid.size, __func__); __cancel_dfr_work(inode, 0, SDFAT_I(inode)->fid.size, __func__);
@ -2492,14 +2553,14 @@ static int sdfat_unlink(struct inode *dir, struct dentry *dentry)
__lock_d_revalidate(dentry); __lock_d_revalidate(dentry);
dir->i_version++; dir->i_version++;
dir->i_mtime = dir->i_atime = current_time(dir); dir->i_mtime = dir->i_atime = ts;
if (IS_DIRSYNC(dir)) if (IS_DIRSYNC(dir))
(void) sdfat_sync_inode(dir); (void) sdfat_sync_inode(dir);
else else
mark_inode_dirty(dir); mark_inode_dirty(dir);
clear_nlink(inode); clear_nlink(inode);
inode->i_mtime = inode->i_atime = current_time(inode); inode->i_mtime = inode->i_atime = ts;
sdfat_detach(inode); sdfat_detach(inode);
dentry->d_time = dir->i_version; dentry->d_time = dir->i_version;
out: out:
@ -2513,6 +2574,7 @@ static int sdfat_symlink(struct inode *dir, struct dentry *dentry, const char *t
{ {
struct super_block *sb = dir->i_sb; struct super_block *sb = dir->i_sb;
struct inode *inode; struct inode *inode;
struct timespec ts;
FILE_ID_T fid; FILE_ID_T fid;
loff_t i_pos; loff_t i_pos;
int err; int err;
@ -2527,6 +2589,8 @@ static int sdfat_symlink(struct inode *dir, struct dentry *dentry, const char *t
TMSG("%s entered\n", __func__); TMSG("%s entered\n", __func__);
ts = CURRENT_TIME_SEC;
err = fsapi_create(dir, (u8 *) dentry->d_name.name, FM_SYMLINK, &fid); err = fsapi_create(dir, (u8 *) dentry->d_name.name, FM_SYMLINK, &fid);
if (err) if (err)
goto out; goto out;
@ -2541,7 +2605,7 @@ static int sdfat_symlink(struct inode *dir, struct dentry *dentry, const char *t
__lock_d_revalidate(dentry); __lock_d_revalidate(dentry);
dir->i_version++; dir->i_version++;
dir->i_ctime = dir->i_mtime = dir->i_atime = current_time(dir); dir->i_ctime = dir->i_mtime = dir->i_atime = ts;
if (IS_DIRSYNC(dir)) if (IS_DIRSYNC(dir))
(void) sdfat_sync_inode(dir); (void) sdfat_sync_inode(dir);
else else
@ -2554,7 +2618,7 @@ static int sdfat_symlink(struct inode *dir, struct dentry *dentry, const char *t
goto out; goto out;
} }
inode->i_version++; inode->i_version++;
inode->i_mtime = inode->i_atime = inode->i_ctime = current_time(inode); inode->i_mtime = inode->i_atime = inode->i_ctime = ts;
/* timestamp is already written, so mark_inode_dirty() is unneeded. */ /* timestamp is already written, so mark_inode_dirty() is unneeded. */
SDFAT_I(inode)->target = kmalloc((len+1), GFP_KERNEL); SDFAT_I(inode)->target = kmalloc((len+1), GFP_KERNEL);
@ -2577,6 +2641,7 @@ static int __sdfat_mkdir(struct inode *dir, struct dentry *dentry)
{ {
struct super_block *sb = dir->i_sb; struct super_block *sb = dir->i_sb;
struct inode *inode; struct inode *inode;
struct timespec ts;
FILE_ID_T fid; FILE_ID_T fid;
loff_t i_pos; loff_t i_pos;
int err; int err;
@ -2585,6 +2650,8 @@ static int __sdfat_mkdir(struct inode *dir, struct dentry *dentry)
TMSG("%s entered\n", __func__); TMSG("%s entered\n", __func__);
ts = CURRENT_TIME_SEC;
err = fsapi_mkdir(dir, (u8 *) dentry->d_name.name, &fid); err = fsapi_mkdir(dir, (u8 *) dentry->d_name.name, &fid);
if (err) if (err)
goto out; goto out;
@ -2592,7 +2659,7 @@ static int __sdfat_mkdir(struct inode *dir, struct dentry *dentry)
__lock_d_revalidate(dentry); __lock_d_revalidate(dentry);
dir->i_version++; dir->i_version++;
dir->i_ctime = dir->i_mtime = dir->i_atime = current_time(dir); dir->i_ctime = dir->i_mtime = dir->i_atime = ts;
if (IS_DIRSYNC(dir)) if (IS_DIRSYNC(dir))
(void) sdfat_sync_inode(dir); (void) sdfat_sync_inode(dir);
else else
@ -2606,7 +2673,7 @@ static int __sdfat_mkdir(struct inode *dir, struct dentry *dentry)
goto out; goto out;
} }
inode->i_version++; inode->i_version++;
inode->i_mtime = inode->i_atime = inode->i_ctime = current_time(inode); inode->i_mtime = inode->i_atime = inode->i_ctime = ts;
/* timestamp is already written, so mark_inode_dirty() is unneeded. */ /* timestamp is already written, so mark_inode_dirty() is unneeded. */
d_instantiate(dentry, inode); d_instantiate(dentry, inode);
@ -2625,12 +2692,15 @@ static int sdfat_rmdir(struct inode *dir, struct dentry *dentry)
{ {
struct inode *inode = dentry->d_inode; struct inode *inode = dentry->d_inode;
struct super_block *sb = dir->i_sb; struct super_block *sb = dir->i_sb;
struct timespec ts;
int err; int err;
__lock_super(sb); __lock_super(sb);
TMSG("%s entered\n", __func__); TMSG("%s entered\n", __func__);
ts = CURRENT_TIME_SEC;
SDFAT_I(inode)->fid.size = i_size_read(inode); SDFAT_I(inode)->fid.size = i_size_read(inode);
err = fsapi_rmdir(dir, &(SDFAT_I(inode)->fid)); err = fsapi_rmdir(dir, &(SDFAT_I(inode)->fid));
@ -2640,7 +2710,7 @@ static int sdfat_rmdir(struct inode *dir, struct dentry *dentry)
__lock_d_revalidate(dentry); __lock_d_revalidate(dentry);
dir->i_version++; dir->i_version++;
dir->i_mtime = dir->i_atime = current_time(dir); dir->i_mtime = dir->i_atime = ts;
if (IS_DIRSYNC(dir)) if (IS_DIRSYNC(dir))
(void) sdfat_sync_inode(dir); (void) sdfat_sync_inode(dir);
else else
@ -2648,7 +2718,7 @@ static int sdfat_rmdir(struct inode *dir, struct dentry *dentry)
drop_nlink(dir); drop_nlink(dir);
clear_nlink(inode); clear_nlink(inode);
inode->i_mtime = inode->i_atime = current_time(inode); inode->i_mtime = inode->i_atime = ts;
sdfat_detach(inode); sdfat_detach(inode);
dentry->d_time = dir->i_version; dentry->d_time = dir->i_version;
out: out:
@ -2663,6 +2733,7 @@ static int __sdfat_rename(struct inode *old_dir, struct dentry *old_dentry,
{ {
struct inode *old_inode, *new_inode; struct inode *old_inode, *new_inode;
struct super_block *sb = old_dir->i_sb; struct super_block *sb = old_dir->i_sb;
struct timespec ts;
loff_t i_pos; loff_t i_pos;
int err; int err;
@ -2673,6 +2744,8 @@ static int __sdfat_rename(struct inode *old_dir, struct dentry *old_dentry,
old_inode = old_dentry->d_inode; old_inode = old_dentry->d_inode;
new_inode = new_dentry->d_inode; new_inode = new_dentry->d_inode;
ts = CURRENT_TIME_SEC;
SDFAT_I(old_inode)->fid.size = i_size_read(old_inode); SDFAT_I(old_inode)->fid.size = i_size_read(old_inode);
__cancel_dfr_work(old_inode, 0, 1, __func__); __cancel_dfr_work(old_inode, 0, 1, __func__);
@ -2685,7 +2758,7 @@ static int __sdfat_rename(struct inode *old_dir, struct dentry *old_dentry,
__lock_d_revalidate(new_dentry); __lock_d_revalidate(new_dentry);
new_dir->i_version++; new_dir->i_version++;
new_dir->i_ctime = new_dir->i_mtime = new_dir->i_atime = current_time(new_dir); new_dir->i_ctime = new_dir->i_mtime = new_dir->i_atime = ts;
if (IS_DIRSYNC(new_dir)) if (IS_DIRSYNC(new_dir))
(void) sdfat_sync_inode(new_dir); (void) sdfat_sync_inode(new_dir);
else else
@ -2706,7 +2779,7 @@ static int __sdfat_rename(struct inode *old_dir, struct dentry *old_dentry,
} }
old_dir->i_version++; old_dir->i_version++;
old_dir->i_ctime = old_dir->i_mtime = current_time(old_dir); old_dir->i_ctime = old_dir->i_mtime = ts;
if (IS_DIRSYNC(old_dir)) if (IS_DIRSYNC(old_dir))
(void) sdfat_sync_inode(old_dir); (void) sdfat_sync_inode(old_dir);
else else
@ -2725,7 +2798,7 @@ static int __sdfat_rename(struct inode *old_dir, struct dentry *old_dentry,
__func__); __func__);
WARN_ON(new_inode->i_nlink == 0); WARN_ON(new_inode->i_nlink == 0);
} }
new_inode->i_ctime = current_time(new_inode); new_inode->i_ctime = ts;
#if 0 #if 0
(void) sdfat_sync_inode(new_inode); (void) sdfat_sync_inode(new_inode);
#endif #endif
@ -2749,7 +2822,7 @@ static int sdfat_cont_expand(struct inode *inode, loff_t size)
if (err) if (err)
return err; return err;
inode->i_ctime = inode->i_mtime = current_time(inode); inode->i_ctime = inode->i_mtime = CURRENT_TIME_SEC;
mark_inode_dirty(inode); mark_inode_dirty(inode);
if (!IS_SYNC(inode)) if (!IS_SYNC(inode))
@ -2882,25 +2955,6 @@ static int sdfat_setattr(struct dentry *dentry, struct iattr *attr)
return error; return error;
} }
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 11, 0)
static int sdfat_getattr(const struct path *path, struct kstat *stat, u32 request_mask, unsigned int flags)
{
struct inode *inode = path->dentry->d_inode;
#else
static int sdfat_getattr(struct vfsmount *mnt, struct dentry *dentry, struct kstat *stat)
{
struct inode *inode = dentry->d_inode;
#endif
TMSG("%s entered\n", __func__);
generic_fillattr(inode, stat);
stat->blksize = SDFAT_SB(inode->i_sb)->fsi.cluster_size;
TMSG("%s exited\n", __func__);
return 0;
}
static const struct inode_operations sdfat_dir_inode_operations = { static const struct inode_operations sdfat_dir_inode_operations = {
.create = sdfat_create, .create = sdfat_create,
.lookup = sdfat_lookup, .lookup = sdfat_lookup,
@ -3010,7 +3064,7 @@ static void sdfat_truncate(struct inode *inode, loff_t old_size)
if (err) if (err)
goto out; goto out;
inode->i_ctime = inode->i_mtime = current_time(inode); inode->i_ctime = inode->i_mtime = CURRENT_TIME_SEC;
if (IS_DIRSYNC(inode)) if (IS_DIRSYNC(inode))
(void) sdfat_sync_inode(inode); (void) sdfat_sync_inode(inode);
else else
@ -3216,7 +3270,17 @@ static int sdfat_da_prep_block(struct inode *inode, sector_t iblock,
} else if (create == 1) { } else if (create == 1) {
/* Not exist: new cluster needed */ /* Not exist: new cluster needed */
BUG_ON(!BLOCK_ADDED(bmap_create)); if (!BLOCK_ADDED(bmap_create)) {
sector_t last_block;
last_block = (i_size_read(inode) + (sb->s_blocksize - 1))
>> sb->s_blocksize_bits;
sdfat_fs_error(sb, "%s: new cluster need, but "
"bmap_create == BMAP_NOT_CREATE(iblock:%lld, "
"last_block:%lld)", __func__,
(s64)iblock, (s64)last_block);
err = -EIO;
goto unlock_ret;
}
// Reserved Cluster (only if iblock is the first sector in a clu) // Reserved Cluster (only if iblock is the first sector in a clu)
if (sec_offset == 0) { if (sec_offset == 0) {
@ -3444,11 +3508,7 @@ static inline void sdfat_submit_fullpage_bio(struct block_device *bdev,
*/ */
bio = bio_alloc(GFP_NOIO, 1); bio = bio_alloc(GFP_NOIO, 1);
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4,14,0)
bio_set_dev(bio, bdev); bio_set_dev(bio, bdev);
#else
bio->bi_bdev = bdev;
#endif
bio->bi_vcnt = 1; bio->bi_vcnt = 1;
bio->bi_io_vec[0].bv_page = page; /* Inline vec */ bio->bi_io_vec[0].bv_page = page; /* Inline vec */
bio->bi_io_vec[0].bv_len = length; /* PAGE_SIZE */ bio->bi_io_vec[0].bv_len = length; /* PAGE_SIZE */
@ -3539,11 +3599,7 @@ static int sdfat_writepage(struct page *page, struct writeback_control *wbc)
if (buffer_new(bh)) { if (buffer_new(bh)) {
clear_buffer_new(bh); clear_buffer_new(bh);
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 10, 0) __sdfat_clean_bdev_aliases(bh->b_bdev, bh->b_blocknr);
clean_bdev_bh_alias(bh);
#else /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 10, 0) */
unmap_underlying_metadata(bh->b_bdev, bh->b_blocknr);
#endif
} }
} }
@ -3593,7 +3649,7 @@ static int sdfat_writepage(struct page *page, struct writeback_control *wbc)
atomic_inc(&SDFAT_SB(sb)->stat_n_pages_queued); atomic_inc(&SDFAT_SB(sb)->stat_n_pages_queued);
sdfat_submit_fullpage_bio(head->b_bdev, sdfat_submit_fullpage_bio(head->b_bdev,
head->b_blocknr << (inode->i_blkbits - sb->s_blocksize_bits), head->b_blocknr << (sb->s_blocksize_bits - SECTOR_SIZE_BITS),
nr_blocks_towrite << inode->i_blkbits, nr_blocks_towrite << inode->i_blkbits,
page); page);
@ -3655,16 +3711,32 @@ static void sdfat_write_failed(struct address_space *mapping, loff_t to)
} }
} }
static int sdfat_check_writable(struct super_block *sb)
{
if (fsapi_check_bdi_valid(sb))
return -EIO;
if (sb->s_flags & MS_RDONLY)
return -EROFS;
return 0;
}
static int __sdfat_write_begin(struct file *file, struct address_space *mapping, static int __sdfat_write_begin(struct file *file, struct address_space *mapping,
loff_t pos, unsigned int len, loff_t pos, unsigned int len,
unsigned int flags, struct page **pagep, unsigned int flags, struct page **pagep,
void **fsdata, get_block_t *get_block, void **fsdata, get_block_t *get_block,
loff_t *bytes, const char *fname) loff_t *bytes, const char *fname)
{ {
struct super_block *sb = mapping->host->i_sb;
int ret; int ret;
__cancel_dfr_work(mapping->host, pos, (loff_t)(pos + len), fname); __cancel_dfr_work(mapping->host, pos, (loff_t)(pos + len), fname);
ret = sdfat_check_writable(sb);
if (unlikely(ret < 0))
return ret;
*pagep = NULL; *pagep = NULL;
ret = cont_write_begin(file, mapping, pos, len, flags, pagep, fsdata, ret = cont_write_begin(file, mapping, pos, len, flags, pagep, fsdata,
get_block, bytes); get_block, bytes);
@ -3719,7 +3791,7 @@ static int sdfat_write_end(struct file *file, struct address_space *mapping,
sdfat_write_failed(mapping, pos+len); sdfat_write_failed(mapping, pos+len);
if (!(err < 0) && !(fid->attr & ATTR_ARCHIVE)) { if (!(err < 0) && !(fid->attr & ATTR_ARCHIVE)) {
inode->i_mtime = inode->i_ctime = current_time(inode); inode->i_mtime = inode->i_ctime = CURRENT_TIME_SEC;
fid->attr |= ATTR_ARCHIVE; fid->attr |= ATTR_ARCHIVE;
mark_inode_dirty(inode); mark_inode_dirty(inode);
} }
@ -4725,9 +4797,12 @@ static int sdfat_read_root(struct inode *inode)
{ {
struct super_block *sb = inode->i_sb; struct super_block *sb = inode->i_sb;
struct sdfat_sb_info *sbi = SDFAT_SB(sb); struct sdfat_sb_info *sbi = SDFAT_SB(sb);
struct timespec ts;
FS_INFO_T *fsi = &(sbi->fsi); FS_INFO_T *fsi = &(sbi->fsi);
DIR_ENTRY_T info; DIR_ENTRY_T info;
ts = CURRENT_TIME_SEC;
SDFAT_I(inode)->fid.dir.dir = fsi->root_dir; SDFAT_I(inode)->fid.dir.dir = fsi->root_dir;
SDFAT_I(inode)->fid.dir.flags = 0x01; SDFAT_I(inode)->fid.dir.flags = 0x01;
SDFAT_I(inode)->fid.entry = -1; SDFAT_I(inode)->fid.entry = -1;
@ -4763,7 +4838,7 @@ static int sdfat_read_root(struct inode *inode)
SDFAT_I(inode)->i_size_ondisk = i_size_read(inode); SDFAT_I(inode)->i_size_ondisk = i_size_read(inode);
sdfat_save_attr(inode, ATTR_SUBDIR); sdfat_save_attr(inode, ATTR_SUBDIR);
inode->i_mtime = inode->i_atime = inode->i_ctime = current_time(inode); inode->i_mtime = inode->i_atime = inode->i_ctime = ts;
set_nlink(inode, info.NumSubdirs + 2); set_nlink(inode, info.NumSubdirs + 2);
return 0; return 0;
} }
@ -5116,6 +5191,7 @@ static void __exit exit_sdfat_fs(void)
sdfat_destroy_inodecache(); sdfat_destroy_inodecache();
unregister_filesystem(&sdfat_fs_type); unregister_filesystem(&sdfat_fs_type);
#ifdef CONFIG_SDFAT_USE_FOR_EXFAT #ifdef CONFIG_SDFAT_USE_FOR_EXFAT
unregister_filesystem(&exfat_fs_type); unregister_filesystem(&exfat_fs_type);
#endif /* CONFIG_SDFAT_USE_FOR_EXFAT */ #endif /* CONFIG_SDFAT_USE_FOR_EXFAT */
@ -5131,3 +5207,4 @@ module_exit(exit_sdfat_fs);
MODULE_LICENSE("GPL"); MODULE_LICENSE("GPL");
MODULE_DESCRIPTION("FAT/exFAT filesystem support"); MODULE_DESCRIPTION("FAT/exFAT filesystem support");
MODULE_AUTHOR("Samsung Electronics Co., Ltd."); MODULE_AUTHOR("Samsung Electronics Co., Ltd.");

View File

@ -301,6 +301,7 @@ static inline void sdfat_save_attr(struct inode *inode, u32 attr)
extern int sdfat_statistics_init(struct kset *sdfat_kset); extern int sdfat_statistics_init(struct kset *sdfat_kset);
extern void sdfat_statistics_uninit(void); extern void sdfat_statistics_uninit(void);
extern void sdfat_statistics_set_mnt(FS_INFO_T *fsi); extern void sdfat_statistics_set_mnt(FS_INFO_T *fsi);
extern void sdfat_statistics_set_mnt_ro(void);
extern void sdfat_statistics_set_mkdir(u8 flags); extern void sdfat_statistics_set_mkdir(u8 flags);
extern void sdfat_statistics_set_create(u8 flags); extern void sdfat_statistics_set_create(u8 flags);
extern void sdfat_statistics_set_rw(u8 flags, u32 clu_offset, s32 create); extern void sdfat_statistics_set_rw(u8 flags, u32 clu_offset, s32 create);
@ -313,6 +314,7 @@ static inline int sdfat_statistics_init(struct kset *sdfat_kset)
} }
static inline void sdfat_statistics_uninit(void) {}; static inline void sdfat_statistics_uninit(void) {};
static inline void sdfat_statistics_set_mnt(FS_INFO_T *fsi) {}; static inline void sdfat_statistics_set_mnt(FS_INFO_T *fsi) {};
static inline void sdfat_statistics_set_mnt_ro(void) {};
static inline void sdfat_statistics_set_mkdir(u8 flags) {}; static inline void sdfat_statistics_set_mkdir(u8 flags) {};
static inline void sdfat_statistics_set_create(u8 flags) {}; static inline void sdfat_statistics_set_create(u8 flags) {};
static inline void sdfat_statistics_set_rw(u8 flags, u32 clu_offset, s32 create) {}; static inline void sdfat_statistics_set_rw(u8 flags, u32 clu_offset, s32 create) {};

View File

@ -68,6 +68,8 @@
#define MAX_NAME_LENGTH 255 // max len of file name excluding NULL #define MAX_NAME_LENGTH 255 // max len of file name excluding NULL
#define DOS_NAME_LENGTH 11 // DOS file name length excluding NULL #define DOS_NAME_LENGTH 11 // DOS file name length excluding NULL
#define SECTOR_SIZE_BITS 9 /* VFS sector size is 512 bytes */
#define DENTRY_SIZE 32 /* directory entry size */ #define DENTRY_SIZE 32 /* directory entry size */
#define DENTRY_SIZE_BITS 5 #define DENTRY_SIZE_BITS 5

View File

@ -8,6 +8,7 @@ enum {
SDFAT_MNT_FAT16, SDFAT_MNT_FAT16,
SDFAT_MNT_FAT32, SDFAT_MNT_FAT32,
SDFAT_MNT_EXFAT, SDFAT_MNT_EXFAT,
SDFAT_MNT_RO,
SDFAT_MNT_MAX SDFAT_MNT_MAX
}; };
@ -85,11 +86,12 @@ static ssize_t mount_show(struct kobject *kobj,
{ {
return snprintf(buff, PAGE_SIZE, "\"FAT12_MNT_I\":\"%u\"," return snprintf(buff, PAGE_SIZE, "\"FAT12_MNT_I\":\"%u\","
"\"FAT16_MNT_I\":\"%u\",\"FAT32_MNT_I\":\"%u\"," "\"FAT16_MNT_I\":\"%u\",\"FAT32_MNT_I\":\"%u\","
"\"EXFAT_MNT_I\":\"%u\"\n", "\"EXFAT_MNT_I\":\"%u\",\"RO_MNT_I\":\"%u\"\n",
statistics.mnt_cnt[SDFAT_MNT_FAT12], statistics.mnt_cnt[SDFAT_MNT_FAT12],
statistics.mnt_cnt[SDFAT_MNT_FAT16], statistics.mnt_cnt[SDFAT_MNT_FAT16],
statistics.mnt_cnt[SDFAT_MNT_FAT32], statistics.mnt_cnt[SDFAT_MNT_FAT32],
statistics.mnt_cnt[SDFAT_MNT_EXFAT]); statistics.mnt_cnt[SDFAT_MNT_EXFAT],
statistics.mnt_cnt[SDFAT_MNT_RO]);
} }
static ssize_t nofat_op_show(struct kobject *kobj, static ssize_t nofat_op_show(struct kobject *kobj,
@ -201,6 +203,11 @@ void sdfat_statistics_set_mnt(FS_INFO_T *fsi)
statistics.clus_vfat[SDFAT_VF_CLUS_MAX - 1]++; statistics.clus_vfat[SDFAT_VF_CLUS_MAX - 1]++;
} }
void sdfat_statistics_set_mnt_ro(void)
{
statistics.mnt_cnt[SDFAT_MNT_RO]++;
}
void sdfat_statistics_set_mkdir(u8 flags) void sdfat_statistics_set_mkdir(u8 flags)
{ {
if (flags != 0x03) if (flags != 0x03)

View File

@ -22,4 +22,4 @@
/* PURPOSE : sdFAT File Manager */ /* PURPOSE : sdFAT File Manager */
/* */ /* */
/************************************************************************/ /************************************************************************/
#define SDFAT_VERSION "2.0.8-lineage" #define SDFAT_VERSION "2.1.8-lineage"