这个命令是 uboot实现了 对flash 的读写初始化功能,挂载在spi总线下;

执行sf probe 就是对spi总线和 flash的初始化;

命令声明: u_BOOT_CMD大家都知道就是定义uboot模式下的命令行;然后uboot在main_loop下循环检测串口指令来解析调用相应命令

U_BOOT_CMD(sf,   5,  1,  do_spi_flash,"SPI flash sub-system","probe [[bus:]cs] [hz] [mode]    - init flash device on given SPI bus\n""                and chip select\n""sf read addr offset|partition len    - read `len' bytes starting at\n""                        `offset' or from start of mtd\n""                   `partition'to memory at `addr'\n""sf write addr offset|partition len    - write `len' bytes from memory\n""                       at `addr' to flash at `offset'\n""                    or to start of mtd `partition'\n""sf erase offset|partition [+]len   - erase `len' bytes from `offset'\n""                   or from start of mtd `partition'\n""                   `+len' round up `len' to block size\n""sf update addr offset|partition len  - erase and write `len' bytes from memory\n""                     at `addr' to flash at `offset'\n""                    or to start of mtd `partition'\n""sf protect lock/unlock sector len   - protect/unprotect 'len' bytes starting\n""                      at address 'sector'\n"SF_TEST_HELP
);

最初就是调用这个函数:

static int do_spi_flash(cmd_tbl_t *cmdtp, int flag, int argc,char * const argv[])
{const char *cmd;int ret;/* need at least two arguments */if (argc < 2)goto usage;cmd = argv[1];--argc;++argv;if (strcmp(cmd, "probe") == 0) {ret = do_spi_flash_probe(argc, argv);goto done;}/* The remaining commands require a selected device */if (!flash) {puts("No SPI flash selected. Please run `sf probe'\n");return 1;}if (strcmp(cmd, "read") == 0 || strcmp(cmd, "write") == 0 ||strcmp(cmd, "update") == 0)ret = do_spi_flash_read_write(argc, argv);else if (strcmp(cmd, "erase") == 0)ret = do_spi_flash_erase(argc, argv);else if (strcmp(cmd, "protect") == 0)ret = do_spi_protect(argc, argv);
#ifdef CONFIG_CMD_SF_TESTelse if (!strcmp(cmd, "test"))ret = do_spi_flash_test(argc, argv);
#endifelseret = -1;done:if (ret != -1)return ret;usage:return CMD_RET_USAGE;
}

就是调用这个函数:

static int do_spi_flash_probe(int argc, char * const argv[])
{unsigned int bus = CONFIG_SF_DEFAULT_BUS;unsigned int cs = CONFIG_SF_DEFAULT_CS;unsigned int speed = CONFIG_SF_DEFAULT_SPEED;unsigned int mode = CONFIG_SF_DEFAULT_MODE;char *endp;
#ifdef CONFIG_DM_SPI_FLASHstruct udevice *new, *bus_dev;int ret;/* In DM mode defaults will be taken from DT */speed = 0, mode = 0;
#elsestruct spi_flash *new;
#endifif (argc >= 2) {cs = simple_strtoul(argv[1], &endp, 0);if (*argv[1] == 0 || (*endp != 0 && *endp != ':'))return -1;if (*endp == ':') {if (endp[1] == 0)return -1;bus = cs;cs = simple_strtoul(endp + 1, &endp, 0);if (*endp != 0)return -1;}}if (argc >= 3) {speed = simple_strtoul(argv[2], &endp, 0);if (*argv[2] == 0 || *endp != 0)return -1;}if (argc >= 4) {mode = simple_strtoul(argv[3], &endp, 16);if (*argv[3] == 0 || *endp != 0)return -1;}#ifdef CONFIG_DM_SPI_FLASH/* Remove the old device, otherwise probe will just be a nop */ret = spi_find_bus_and_cs(bus, cs, &bus_dev, &new);if (!ret) {device_remove(new, DM_REMOVE_NORMAL);}flash = NULL;ret = spi_flash_probe_bus_cs(bus, cs, speed, mode, &new);if (ret) {printf("Failed to initialize SPI flash at %u:%u (error %d)\n",bus, cs, ret);return 1;}flash = dev_get_uclass_priv(new);
#elseif (flash)spi_flash_free(flash);new = spi_flash_probe(bus, cs, speed, mode);flash = new;if (!new) {printf("Failed to initialize SPI flash at %u:%u\n", bus, cs);return 1;}flash = new;
#endifreturn 0;
}

函数内部都是对flash的操作,就是内存向flash 写入; 从flash读取写入内存;擦除flash 块等操作

命令是:

那么sf 命令功能也就清楚了,就是对flash操作的指令;

sf probe初始化flash 或者说初始化spi总线;

sf read addr offset|partition len    - read `len' bytes starting at\n"

sf write addr offset|partition len    - write `len' bytes from memory\n"

addr :内存地址

offset|partition: flash的偏移地址

len:读取的大小(字节为单位)

举例:

sf probe; sf read 0x2000000 0 0x400000

初始化 spi; 从 flash 0 地址 读取 0x400000 个字节 ,读取到0x2000000 ,结束地址就是0x2000000+0x400000;

从flash 中读取,然后通过md 查看内存中数据;

sf erase offset|partition [+]len    - erase `len' bytes from `offset'

sf write addr offset|partition len    - write `len' bytes from memory\n"

sf write 之前一定要先执行初始化和 擦除

sf probe && sf erase 0x1a00000 +4

&& sf write 0x2000000 0x1a00000 4  && sf read 0x2000010 0x1a00000 4

初始化,擦除  flash 0x1a00000 地址为起点,擦除大小 4个字节(这里+4没错哈,人家就是这约定的),

吧内存中0x2000000 的值写入到 0x1a00000 写四个字节大小

从flash 0x1a00000的地址读取四个字节, 读取到内存0x2000010

验证:

这样可以验证我们能不能写入成功;下面是我操作的步骤;

我们先通过mw 向内存 0x2000000 写123456789 但是我操作有问题哈;

之后擦除flash 然后选个空间 吧 0x2000000 对应的值123456789写进去

我们换个内存地址再读取出来;

我多写了几个地址没问题哈能写进去的;

uboot中环境变量 sf相关推荐

  1. uboot中环境变量的加载、写入过程详解

    1.uboot启动中环境变量的加载 1.1.uboot加载环境变量流程分析 (1)首先使用默认的环境变量default_environment[]: (2)然后加载SD卡中env分区的环境变量,校验读 ...

  2. uboot中环境变量的实现

    1.环境变量介绍 uboot中环境变量的作用类似于全局变量,需要某个环境变量的值时调用getenv函数就可以得到.环境变量会指导程序的运行,不必修改代码重新编译,通过修改环境变量就可以改变uboot的 ...

  3. uboot默认环境变量修改

    uboot的默认环境变量决定了系统是通过何种方式启动的,对于定制化的嵌入式系统,uboot的定制化修改也是必要的. uboot有两种修改方式: 1.直接修改源码或者修改uboot配置 2.在uboot ...

  4. 从bootm 命令讲起/U-boot的环境变量: bootcmd 和bootargs

    从bootm 命令讲起 1 找到linux的内核入口 Bootm命令通过读取uImage的头部0×40字节的信息,将uImage定位到正确的地址,同时找到linux的内核入口地址. 这个地方就涉及到u ...

  5. uboot的环境变量

    注:本文是学习朱老师课程整理的笔记,基于uboot-1.3.4和s5pc11x分析. 环境变量的作用 可以不用修改uboot的源代码,而是通过修改环境变量来影响uboot运行时的一些数据和特性.譬如说 ...

  6. uboot之环境变量

    一.环境变量基础知识 1.环境变量的作用 环境变量的最大作用就是在我们不需要改变源代码的情况下,改变程序的执行情况.比如我们的bootdelay时间,通过修改对应的环境变量的值,就可以改变uboot开 ...

  7. java se环境变量设置_JavaSE中环境变量的配置

    在说Java中环境变量配置之前,还是先说说JDK和JRE吧. JRE(Java Runtime Environment),即Java的运行环境.主要包括JVM(Java Virtual Machine ...

  8. setlocal启动批处理文件中环境变量的本地化

    setlocal启动批处理文件中环境变量的本地化 在执行 SETLOCAL 之后所做的环境改动只限于批处理文件.要还原原先的设置,必须执行 ENDLOCAL. 学习了:https://baike.ba ...

  9. bashrc文件中环境变量配置错误,导致linux命令无法正常使用的解决方案

    分析原因 bashrc文件中环境变量配置错误,导致linux无法正常使用. 其实解决问题的方法很简单:把你在bashrc文件中写错的东西注释掉或者改写正确即可. 可是此时图形界面登陆不了,vim用不了 ...

最新文章

  1. 谈谈对Spring IOC的理解
  2. AppManager
  3. codeforces D Good Substrings(hash)
  4. android开发之图表
  5. Java synchronized的CPU层面实现细节
  6. redis 上亿数据_票房上亿,稳居第一?肖战《诛仙》日本上映,真实数据到底怎样...
  7. 看YYModel源码的一些收获
  8. Java 中实现定时服务 在ssh框架中跟普通工程里面创建的方式
  9. oracle数据库监听频道异常,数据库监听不定期出现异常故障处理
  10. JS中元素的属性(class、style)操作
  11. 100套高质量的免费 PSD 界面设计素材【系列一】
  12. kafka topic:1_Topic️主题建模:超越令牌输出
  13. linux raid 卡日志,Linux系统下RAID卡异常日志收集方法、系统及存储介质与流程
  14. 关于输入阻抗和输出阻抗的理解
  15. 2020十二周学习生活小反思
  16. 基于开源WordPress的高校数字图书馆应用构建
  17. 老Java程序员花2天写了个连连看,我竟连不过我女儿,我了个去!
  18. 一般图最大匹配问题-带花树开花算法
  19. 绝对受用的求职经验分享
  20. java中时间的转换相关问题整理

热门文章

  1. php 5.3 版本for mac下载,PHP for Mac下载
  2. 数值计算大作业:Jacobi与Gauss -Seidel迭代求解线性方程组(Matlab实现)
  3. 缓冲区溢出漏洞那些事:C -gets函数
  4. [转载]千手观音是如何练成的?
  5. ViT-B参数量计算
  6. 学通PHP的24堂课(配光盘)(软件开发羊皮卷)
  7. 无线桥接后无法访问服务器,无线桥接后不能登录ip地址 桥接后副路由器进不去-192路由网...
  8. 那一年的北风--序言3
  9. 全闪存时代真的来了吗?反正紫光华山是认真了
  10. 国家统计标准(包括行政区划、行业类别等实用信息)