You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

P16F877间接寻址求和错误代码修正请求

PIC单片机间接寻址求和代码修正

我有两个分别位于bank 0和bank 2的数值n1与n2,希望通过间接寻址方式实现二者的求和操作。以下是我课堂上的代码,在MPLAB 8.92中测试发现存在错误,需要帮忙修正。我习惯使用x86汇编,对PIC系列单片机不太熟悉,尝试改写但未能成功。

原代码:

nbr1 equ 0xA0
nbr2 equ 0x121
som12 equ 0x1A2
; Les instructions ci-dessus utilisant la directive (equ) peuvent être remplacées par la directive cblock :
; cblock 0x20
; nbr1, nbr2, som12
; endc
w equ 0
f equ 1
; La macro suivante (bank0) est un sous-programme qui permet de configurer STATUS pour pointer sur bank#0

; ------------- Programme principal ---------------------------------------
org 0x00 ; Définir la position initiale dans la mémoire programme
debut
    ;nbr1:
    CLRF STATUS;IRP = 0
    movlw 0xA0
    movwf FSR  ;FSR=0xA0
    movlw 0xFF ; Transférer la valeur (0x0A) dans l'accumulateur w
    movwf INDF ; Transférer le contenu de W à l'adresse du nbr1

    ;nbr2:
    bsf STATUS, IRP;IRP = 1
    movlw 0x21
    movwf FSR ;FSR=0x21
    movlw 0x01 ; Transférer la valeur (0x0A) dans l'accumulateur w
    movwf INDF

    ; Charger addresse de nbr1 dans FSR
    bcf STATUS, IRP;IRP = 0
    movlw 0xA0
    movwf FSR ;FSR=0xA0
    addwf INDF,w ; Additionner w à la variable nbr2

    bsf STATUS, IRP;IRP = 1
    movlw 0xA2
    movwf FSR ;FSR=0xA2
    movwf INDF ; Stoker le résultat de la somme à partir de w sur la variable som12
    goto debut ; Réexécuter la boucle depuis le label « début »
    end

原代码核心错误

  • 求和逻辑颠倒:addwf INDF,w 是将当前W的值加到INDF(nbr1)并回存到W,但此时W里还是初始化nbr2时的0x01,并未读取nbr2的值参与运算
  • 结果存储错误:最后一步movlw 0xA2后,先给FSR赋值,紧接着又执行movwf INDF,这会把0xA2写入som12,而非求和后的W值
  • STATUS寄存器操作不严谨:CLRF STATUS会清零整个STATUS寄存器,可能误操作其他标志位(如RP0/RP1),建议单独操作IRP位

修正后的代码

nbr1 equ 0xA0          ; Bank 0 地址(IRP=0)
nbr2 equ 0x121         ; Bank 2 地址(IRP=1,低8位为0x21)
som12 equ 0x1A2        ; Bank 2 地址(IRP=1,低8位为0xA2)
w equ 0
f equ 1

org 0x00               ; 程序起始地址
debut
    ; 初始化nbr1(Bank 0)
    bcf STATUS, IRP    ; 切换到Bank 0(仅修改IRP位,避免影响其他标志)
    movlw 0xA0
    movwf FSR          ; FSR指向nbr1的低8位地址
    movlw 0xFF
    movwf INDF         ; nbr1 = 0xFF

    ; 初始化nbr2(Bank 2)
    bsf STATUS, IRP    ; 切换到Bank 2
    movlw 0x21
    movwf FSR          ; FSR指向nbr2的低8位地址
    movlw 0x01
    movwf INDF         ; nbr2 = 0x01

    ; 读取nbr1到W寄存器
    bcf STATUS, IRP
    movlw 0xA0
    movwf FSR
    movf INDF, w       ; W = nbr1(0xFF)

    ; 读取nbr2并与W相加,结果存回W
    bsf STATUS, IRP
    movlw 0x21
    movwf FSR
    addwf INDF, w      ; W = W + nbr2 = 0xFF + 0x01 = 0x00,STATUS寄存器C位会置1

    ; 存储求和结果到som12
    movlw 0xA2
    movwf FSR          ; FSR指向som12的低8位地址
    movwf INDF         ; som12 = W(0x00)

    goto debut         ; 循环执行
end

补充说明

  • 若需要处理进位(如示例中0xFF+0x01产生的进位),可额外将STATUS寄存器的C位存入指定变量
  • 始终通过bsf/bcf STATUS, IRP切换bank,避免误操作其他标志位

内容的提问来源于stack exchange,提问作者HellBoy

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.15 06:53:29