V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
• 请不要在回答技术问题时复制粘贴 AI 生成的内容
amiwrong123
V2EX  ›  程序员

51 单片机里,直接操作内存为什么不能点亮灯?

  •  
  •   amiwrong123 · 2022-05-15 14:39:28 +08:00 · 3721 次点击
    这是一个创建于 948 天前的主题,其中的信息可能已经有所发展或是发生改变。

    如上,如果用P1 = 0xfd;就能点亮 P1 的第一个灯,但是用*(unsigned char*)(0x90) = 0xfd;就点不亮。但是我看这两句的汇编代码都是一样的MOV (0x90), #0xfd

    第 1 条附言  ·  2022-05-15 15:29:08 +08:00

    不好意思,上面的*(unsigned char*)(0x90) = 0xfd;的汇编是错的。确实是不一样(应该先编译,再debug看汇编)。如下:

    前者P1 = 0xfd;是:

    MOV (0x90), #0xfd
    

    后者*(unsigned char*)(0x90) = 0xfd;是

    MOV      R0,#P1(0x90)
    MOV      @R0,#0xFD
    

    但看起来没有本质区别阿,MOV @R0,#0xFD这句起到的作用应该和MOV (0x90), #0xfd一样吧

    18 条回复    2022-05-22 20:57:24 +08:00
    pca7a2
        1
    pca7a2  
       2022-05-15 14:42:51 +08:00
    md5sum 对比一下
    liyang5945
        2
    liyang5945  
       2022-05-15 15:11:11 +08:00
    刚好我也在学单片机,我刚才试了一下,的确不能点亮,我猜测是通过 sfr 声明的地址才能操作端口的电平,不知道你这个汇编代码是怎么弄出来的,我对比了一下生成的 hex 文件,里面有很多处不同的
    amiwrong123
        3
    amiwrong123  
    OP
       2022-05-15 15:31:00 +08:00
    @liyang5945 #2
    点击 start debug session ,view 开启汇编窗口。
    hex 不同是因为前者只有一句汇编,后者有两句汇编。但看了汇编,感觉没有本质区别,都是往内存引用里 赋值。
    liuxu
        4
    liuxu  
       2022-05-15 16:03:12 +08:00
    wty
        5
    wty  
       2022-05-15 16:44:09 +08:00   ❤️ 2
    51 分什么直接寻址间接寻址,跟现代 X86 和 ARM 这种不太一样
    RAM 的低 128 字节作为内存(前几个字节还跟寄存器复用),可以用 MOV 和 MOV @ R0 这种操作
    高 128 字节跟 SFR 复用,只有直接 MOV 会被解释为操作 SFR ,用 MOV @ R0 操作会被解释为操作 RAM
    XRAM 需要用 MOVX 访问,Flash 需要用 MOVC 访问

    51 这种蛋疼的访问方式让指针也很麻烦,memcpy 甚至用了一个大 switch 去把每种情况都写了一遍。。。。
    statumer
        6
    statumer  
       2022-05-15 16:44:16 +08:00 via iPhone   ❤️ 1
    直接寻址访问 sfr ,间接寻址访问用户内存区
    RoyLaw
        7
    RoyLaw  
       2022-05-15 18:03:00 +08:00
    我都毕业快二十年了,大家还在玩 51 单片机嘛?你试试用二进制来操作。
    liuxu
        8
    liuxu  
       2022-05-15 19:38:16 +08:00
    @RoyLaw 我十年前毕业学的郭天祥的 51 单片机,看上去 OP 现在还是在学郭天祥的
    someonesnone
        9
    someonesnone  
       2022-05-15 20:46:53 +08:00 via iPhone
    操作 ram 和 sfr 的汇编不一样吧 所以直接写入端口寄存器需要特殊的方法
    disk
        10
    disk  
       2022-05-15 21:13:36 +08:00
    所谓本质需要追溯到汇编阶段,译码阶段甚至是执行阶段。。。注意某些特殊规定。
    zbianbiaos
        11
    zbianbiaos  
       2022-05-15 22:10:52 +08:00
    51 是哈佛结构吧(不确定啊),外设没有统一地址管理,SFR 应该是特殊映射寄存器,将一个特殊的地址空间映射到 P1 变量,而不是你能够正常寻址的用户地址空间
    anonydmer
        12
    anonydmer  
       2022-05-16 09:22:24 +08:00
    十几年前我可以点亮,现在也点不亮咯
    qwertyssp
        13
    qwertyssp  
       2022-05-16 12:05:31 +08:00
    既然都看到汇编了,这两句怎么能是等价呢?
    aru
        14
    aru  
       2022-05-16 13:51:52 +08:00
    啥时候教学才能替换为 mips 、arm 、riscv 架构的廉价单片机啊
    Takizawa
        15
    Takizawa  
       2022-05-16 22:36:33 +08:00 via Android
    @aru 等那一批人退休🌝🌝
    Halry
        16
    Halry  
       2022-05-17 18:33:25 +08:00 via iPhone
    51 不是哈弗结构,所以不能直接通过操作内存来控制外设,arm 是,所以可以直接像操作内存的方式操作外设
    amiwrong123
        17
    amiwrong123  
    OP
       2022-05-17 21:49:09 +08:00
    @Halry #16
    老哥,不是很懂为什么 是否为哈佛结构 会影响到 能否通过操作内存来控制外设。

    从知乎上来看:
    哈佛结构与冯诺依曼结构的本质区别在用是否使用同一套地址总线、数据总线,程序和数据是否统一寻址。比如代码地址是从 0~100k ,数据也是从 0~100k 这是哈佛结构,如果代码是从 0~100k ,数据是从 100~200k 并且使用同一套地址总线和数据总线这是冯诺依曼结构。

    程序和数据是否统一寻址 为什么会影响到 能否通过操作内存来控制外设阿?
    Halry
        18
    Halry  
       2022-05-22 20:57:24 +08:00 via iPhone
    @amiwrong123 抱歉,是我记混了,确实不关架构的问题
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   3921 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 32ms · UTC 00:56 · PVG 08:56 · LAX 16:56 · JFK 19:56
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.