利用SD卡测试恩智浦947开发板的SDIO功能 首先是新建工程: 首先从RT Thread官当下载最新代码 https://github.com/RT-Thread/rt-thread/ 在源码目录.bsp\nxp\mcx\mcxn\frdm-mcxn947 的位置找到N947的工程,并在此打开scons 执行 scons --dist --target=mdk5 生成初始工程 此时位于dist目录中的工程就是专门为MCXN947生成的工程了,可以单独拷贝到任何目录,不依赖于当前源码目录。 在新生成的工程目录中执行 pkgs --update 这一步的目的是从服务器拉取工程中用到但是尚未下载源码的包,如果没有这一步,直接在keil中编译会报错 新的工程就建好了,可以现在keil中编译,下载一下。 接下来就是为本次验证的配置, 首先打开menuconfig工具,需要配置的有以下几项: DFS 虚拟文件系统 MMC/SD driver SDIO 外设驱动 结束后退出并保存,注意这里要重新生成以下keil工程,否则keil里是没有刚刚新的配置的。 代码验证 使用Keil编译并下载Demo程序 SD卡识别 Demo程序总已经自带了SD卡的挂载 #ifdef RT_USING_SDIO rt_thread_mdelay(2000); if (dfs_mount("sd", "/", "elm", 0, NULL) == 0) { rt_kprintf("sd mounted to /\n"); } else { rt_kprintf("sd mount to / failed\n"); } #endif 结果 所以很容易验证SD卡的挂载 接下来写一个文件读写的测试case,主要实现的功能有: 在当前目录打开或新建一个名为“test.txt”的文件 在文件中写入一段文字,关闭文件 重新打开文件,并读取打印其中的文字 代码实现如下: #include <rtdevice.h> #include "drv_pin.h" #include "dfs_fs.h" int rwTest(void) { FILE *fout; char buf[32]; const char test[] = "This is a test file"; rt_kprintf("This is SD card read&write test\r\n"); fout = fopen("test.txt", "wb"); if (fout == NULL) { printf("Failed to open file \"%s\"\n", "test.txt"); exit(-1); } fwrite(test, 1, sizeof(test), fout); fclose(fout); fout = fopen("test.txt", "r"); if (fout == NULL) { printf("Failed to open file \"%s\"\n", "test.txt"); exit(-1); } fread(buf, 1, sizeof(buf), fout); rt_kprintf("Read from file: %s \r\n", buf); } MSH_CMD_EXPORT(rwTest, rwTest); 测试结果如下: 使用ls命令查看文件,并使用cat命令查看文件内容: 按照自己的理解设计了一个读写速度测试的case,主体思路就是对512B - 64KB的读写速度进行测试,使用timer0记录时间。 代码如下: #include <rtdevice.h> #include "drv_pin.h" #include "dfs_fs.h" void readWriteTest(int size) { FILE *fout, *fin; void* buf; rt_device_t hw_dev; rt_hwtimerval_t timeout_s; /* 用于保存定时器经过时间 */ /* 查找定时器设备 */ hw_dev = rt_device_find("timer0"); rt_device_open(hw_dev, RT_DEVICE_OFLAG_RDWR); /* 设置定时器超时值为10s并启动定时器 */ timeout_s.sec = 10; /* 秒 */ timeout_s.usec = 0; /* 微秒 */ fout = fopen("test.txt", "wb"); buf = malloc(size); rt_memset(buf, 0xff, size); if (fout == NULL) { printf("Failed to open file \"%s\"\n", "test.txt"); exit(-1); } if (rt_device_write(hw_dev, 0, &timeout_s, sizeof(timeout_s)) != sizeof(timeout_s)) { rt_kprintf("set timeout value failed\n"); return; } fwrite(buf, 1, size, fout); fclose(fout); rt_device_read(hw_dev, 0, &timeout_s, sizeof(timeout_s)); rt_kprintf("%d Byte write test, time cost: Sec = %d, Usec = %d\n", size, timeout_s.sec,timeout_s.usec); fin = fopen("test.txt", "r"); if (rt_device_write(hw_dev, 0, &timeout_s, sizeof(timeout_s)) != sizeof(timeout_s)) { rt_kprintf("set timeout value failed\n"); return; } fread(buf, 1, size, fin); fclose(fin); rt_device_read(hw_dev, 0, &timeout_s, sizeof(timeout_s)); rt_kprintf("%d Byte read test, time cost: Sec = %d, Usec = %d\n", size, timeout_s.sec,timeout_s.usec); free(buf); } int speedTest(void) { rt_kprintf("This is SD card speed test\r\n"); readWriteTest(512); readWriteTest(1024); readWriteTest(2048); readWriteTest(4096); readWriteTest(8192); readWriteTest(16384); readWriteTest(32768); readWriteTest(65536); } MSH_CMD_EXPORT(speedTest, speedTest); 测试结果 初步的结论是,4K以下的读写速率相差很小,可能是主要的时间消耗在了调用和系统调度。之前在另一块产品中,主频比这个单片机低很多,而且还是使用的SPI接口,但是写一个512的扇区也只需要6ms,而这里竟然需要15ms。好在随着我不断加大测试数据量,区别在大数据读写还是很大的。
|