SD和SDHC和SDXC卡的区别,以及Linux移植exfat

1)本章主要讲解各类型SD卡相关知识说明,分享给将要学习或者正在学习SD卡的同学。

2)适用于对C/C++语言有基本的认识,以及对Linux环境有基本的掌握能力。

3)内容属于原创,若转载,请说明出处。

4)本人提供相关问题有偿答疑和技术支持。

SD卡,SDHC卡,SDXC卡区别在于规格不一样,SD卡最大支持2GB容量,SDHC 最大支持32GB容量,SDXC 最大支持2TB(2048GB)容量,支持SDXC卡的数码设备是兼容支持SD卡与SDHC卡的,如果设备只有支持SDHC卡,那么这个设备就不能使用SDXC卡,但兼容SD卡。如果设备只支持SD卡,则不兼容SDXC,SDHC卡

我手里就有两个卡一个是SDHC(16G)一个是SDXC(64G),注意这两种卡是有区别的:

SD卡的速度直接显示在SD卡的正面:

对应于下面的数字:

上面的标识解释:

在实际使用中发现,SDHC可以使用如下命令挂载:

mount -t vfat /dev/mmcblk0p1 /mnt/

但是SDXC却不行:

在格式化的时候发现SDHC可以格式化成FAT32格式,这个格式也是很多ARM开发板上支持的格式,但是SDXC只能格式化成exFAT格式;

因此挂载的时候需要改变挂载的格式:

mount -t exfat /dev/mmcblk0p1 /mnt

但是exfat有版权问题,默认的Linux内核是没有这个驱动支持的(最新的内核好像是支持的);不同的系统需要移植不同的exfat的驱动,如32位和64位的系统不一样:

1)克隆exfat的code:

    git clone https://github.com/arter97/exfat-linux.git

2)将code拷贝到如下:

    cp exfat-linux ../kernel/fs/exfat -rf

3)修改config将驱动编译出来exfat.ko。(默认使用的是64位系统的结构,部分Linux内核使用的是32位的,因此需要修改下变量)

diff --git a/arch/arm/configs/xxx_defconfig b/arch/arm/configs/xxx_defconfig 
index c0ef06c..6a48599 100755
--- a/arch/arm/configs/xxx_defconfig 
+++ b/arch/arm/configs/xxx_defconfig 
@@ -2536,3 +2536,4 @@ CONFIG_SG_POOL=y
CONFIG_ARCH_HAS_SG_CHAIN=y
CONFIG_SBITMAP=y
# CONFIG_VIRTUALIZATION is not set
+CONFIG_EXFAT_FS=m
diff --git a/fs/Kconfig b/fs/Kconfig
index 4bd03a2..6bc9d2f 100644
--- a/fs/Kconfig
+++ b/fs/Kconfig
@@ -243,6 +243,7 @@ source "fs/minix/Kconfig"
source "fs/omfs/Kconfig"
source "fs/hpfs/Kconfig"
source "fs/qnx4/Kconfig"
+source "fs/exfat/Kconfig"
source "fs/qnx6/Kconfig"
source "fs/romfs/Kconfig"
source "fs/pstore/Kconfig"
diff --git a/fs/Makefile b/fs/Makefile
index ed2b632..2a417ff 100644
--- a/fs/Makefile
+++ b/fs/Makefile
@@ -129,3 +129,4 @@ obj-y                += exofs/ # Multiple modules
obj-$(CONFIG_CEPH_FS)        += ceph/
obj-$(CONFIG_PSTORE)        += pstore/
obj-$(CONFIG_EFIVAR_FS)        += efivarfs/
+obj-$(CONFIG_EXFAT_FS)        += exfat/
diff --git a/dir.c b/dir.c
index a54ac92..a2bdce9 100644
--- a/dir.c
+++ b/dir.c
@@ -439,7 +439,7 @@ int exfat_init_dir_entry(struct inode *inode, struct exfat_chain *p_dir,
{
     struct super_block *sb = inode->i_sb;
     struct exfat_sb_info *sbi = EXFAT_SB(sb);
-    struct timespec64 ts = current_time(inode);
+    struct timespec ts = current_time(inode);
     sector_t sector;
     struct exfat_dentry *ep;
     struct buffer_head *bh;
diff --git a/exfat_fs.h b/exfat_fs.h
index 9979639..c4a5d64 100644
--- a/exfat_fs.h
+++ b/exfat_fs.h
@@ -190,9 +190,9 @@ struct exfat_dir_entry {
     unsigned short attr;
     loff_t size;
     unsigned int num_subdirs;
-    struct timespec64 atime;
-    struct timespec64 mtime;
-    struct timespec64 crtime;
+    struct timespec atime;
+    struct timespec mtime;
+    struct timespec crtime;
     struct exfat_dentry_namebuf namebuf;
};
@@ -303,7 +303,7 @@ struct exfat_inode_info {
     struct rw_semaphore truncate_lock;
     struct inode vfs_inode;
     /* File creation time */
-    struct timespec64 i_crtime;
+    struct timespec i_crtime;
};
static inline struct exfat_sb_info *EXFAT_SB(struct super_block *sb)
@@ -530,10 +530,10 @@ void exfat_msg(struct super_block *sb, const char *lv, const char *fmt, ...)
#define exfat_info(sb, fmt, ...)                    \
     exfat_msg(sb, KERN_INFO, fmt, ##__VA_ARGS__)
-void exfat_get_entry_time(struct exfat_sb_info *sbi, struct timespec64 *ts,
+void exfat_get_entry_time(struct exfat_sb_info *sbi, struct timespec *ts,
         u8 tz, __le16 time, __le16 date, u8 time_cs);
-void exfat_truncate_atime(struct timespec64 *ts);
-void exfat_set_entry_time(struct exfat_sb_info *sbi, struct timespec64 *ts,
+void exfat_truncate_atime(struct timespec *ts);
+void exfat_set_entry_time(struct exfat_sb_info *sbi, struct timespec *ts,
         u8 *tz, __le16 *time, __le16 *date, u8 *time_cs);
u16 exfat_calc_chksum16(void *data, int len, u16 chksum, int type);
u32 exfat_calc_chksum32(void *data, int len, u32 chksum, int type);
diff --git a/file.c b/file.c
index 50565d3..aa4b942 100644
--- a/file.c
+++ b/file.c
@@ -150,7 +150,7 @@ int __exfat_truncate(struct inode *inode, loff_t new_size)
     /* update the directory entry */
     if (!evict) {
-        struct timespec64 ts;
+        struct timespec ts;
         struct exfat_dentry *ep, *ep2;
         struct exfat_entry_set_cache *es;
diff --git a/misc.c b/misc.c
index 93e05ac..c528d34 100644
--- a/misc.c
+++ b/misc.c
@@ -64,7 +64,7 @@ void exfat_msg(struct super_block *sb, const char *level, const char *fmt, ...)
#define SECS_PER_MIN    (60)
#define TIMEZONE_SEC(x)    ((x) * 15 * SECS_PER_MIN)
-static void exfat_adjust_tz(struct timespec64 *ts, u8 tz_off)
+static void exfat_adjust_tz(struct timespec *ts, u8 tz_off)
{
     if (tz_off <= 0x3F)
         ts->tv_sec -= TIMEZONE_SEC(tz_off);
@@ -73,7 +73,7 @@ static void exfat_adjust_tz(struct timespec64 *ts, u8 tz_off)
}
/* Convert a EXFAT time/date pair to a UNIX date (seconds since 1 1 70). */
-void exfat_get_entry_time(struct exfat_sb_info *sbi, struct timespec64 *ts,
+void exfat_get_entry_time(struct exfat_sb_info *sbi, struct timespec *ts,
         u8 tz, __le16 time, __le16 date, u8 time_cs)
{
     u16 t = le16_to_cpu(time);
@@ -99,7 +99,7 @@ void exfat_get_entry_time(struct exfat_sb_info *sbi, struct timespec64 *ts,
}
/* Convert linear UNIX date to a EXFAT time/date pair. */
-void exfat_set_entry_time(struct exfat_sb_info *sbi, struct timespec64 *ts,
+void exfat_set_entry_time(struct exfat_sb_info *sbi, struct timespec *ts,
         u8 *tz, __le16 *time, __le16 *date, u8 *time_cs)
{
     struct tm tm;
@@ -129,7 +129,7 @@ void exfat_set_entry_time(struct exfat_sb_info *sbi, struct timespec64 *ts,
  * (There is no 10msIncrement field for access_time unlike create/modify_time)
  * atime also has only a 2-second resolution.
  */
-void exfat_truncate_atime(struct timespec64 *ts)
+void exfat_truncate_atime(struct timespec *ts)
{
     ts->tv_sec = round_down(ts->tv_sec, 2);
     ts->tv_nsec = 0;

insmod exfat.ko:

  • 3
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值