avr汇编百例

;范例1
LSDAA: ADC  R16,R16    ;十进制数(在R16中)左移调整子程序
ADDAA: IN    R6,SREG    ;bcd码相加调整子程序,先保存相加后的
LDI  R17,$66    ;状态the old status
ADD  R16,R17    ;再将和预加立即数$66
IN    R17,SREG  ;输入相加后新状态(the new status)
OR    R6,R17    ;新旧状态相或
SBRS  R6,0      ;相或后进位置位则跳行
SUBI  R16,$60    ;否则减去$60(十位bcd不满足调整条件)
SBRS  R6,5      ;半进位置位则跳行
SUBI  R16,6    ;否则减去$06(个位bcd不满足调整条件)
ROR  R6      ;向高位字节BCD返还进位位!
RET
佳能960
;范例2
SUDAA: BRCC  SBD1      ;bcd码减法调整子程序,差在R16中
BRHC  SBD3     
SUBI  R16,$66    ;进位半进位都置位,将差减去立即数$66
SEC            ;并恢复借位C
RET            ;ret. with seC
SBD1:  BRHC  SBD2      ;进位半进位都清位,返回
SUBI  R16,6    ;进位清除而半进位置位,将差减去6
SBD2:  RET            ;ret. with clC
SBD3:  SUBI  R16,$60    ;进位置位而半进位清除,将差减去$60
SEC            ;并恢复借位C
RET            ;ret. with seC
;范例3
RSDAA: SBRC  R16,7    ;bcd码(在R16中)右移调整子程序
SUBI  R16,$30    ;十位BCD最高位为1(代表8),将其变为5(否则跳行)
SBRC  R16,3     
SUBI  R16,3    ;个位BCD最高位为1(代表8),将其变为5(否则跳行)
RET
;范例4
ADBCD4: MOV  R16,R15    ;4字节压缩bcd码相加子程序
ADD  R16,R11    ;R12,R13,R14,R15内为被加数,R8,R9,R10,R11内为加数
RCALL  ADDAA    ;相加后调整
MOV  R15,R16    ;并返还调整后结果
MOV  R16,R14
ADC  R16,R10
RCALL  ADDAA
MOV  R14,R16
MOV  R16,R13
ADC  R16,R9
RCALL  ADDAA
MOV  R13,R16
MOV  R16,R12
ADC  R16,R8   
RCALL  ADDAA
MOV  R12,R16
RET
;范例5
ADBCD: LDI  R16,4    ;多字节压缩bcd码相加子程序
MOV  R7,R16    ;(r7):字节数
CLC
ADLOP: LD    R16,-X    ;X-1指向被加数;
LD    R6,-Y    ;Y-1指向加数
ADC  R16,R6
RCALL  ADDAA    ;相加后调整
ST    X,R16    ;返还调整后结果
DEC  R7     
BRNE  ADLOP
RET
;范例6
SUBCD4: MOV  R16,R15    ;4字节压缩bcd码减法子程序
SUB  R16,R11    ;R12,R13,R14,R15内为被减数,R8,R9,R10,R11内为减数
RCALL  SUDAA      ;相减后调整
MOV  R15,R16    ;并返还调整后结果
MOV  R16,R14
SBC  R16,R10
RCALL  SUDAA
MOV  R14,r16
MOV  R16,R13
SBC  R16,R9
RCALL  SUDAA
MOV  R13,R16
MOV  R16,R12
SBC  R16,R8
RCALL  SUDAA
MOV  R12,R16
RET
;范例7
SUBCD: LDI  R16,4    ;多字节压缩bcd码
相减子程序
MOV  R7,R16    ;(r7):压缩bcd码字节数
CLC
SUBLP: LD    R16,-X    ;X-1指向被减数
LD    R6,-Y    ;Y-1指向减数
SBC  R16,R6
RCALL  SUDAA    ;相减后调整
ST    X,R16    ;返还调整后结果
DEC  R7
BRNE  SUBLP
RET
;范例8          ;16位被乘数*16位乘数-->32位积
MUL16: LDI  R16,17    ;(r10r11)*(r14r15)-->r12r13r14r15
ClR  R12
ClR  R13      ;积的高位字预清除
CLC            ;第1次只右移,不相加
MLOOP: BRCC  MUL1      ;
ADD  R13,R11    ;乘数右移移出位为1,将被乘数加入部分积
ADC  R12,R10
MUL1:  ROR  R12
ROR  R13
ROR  R14
ROR  R15      ;部分积连同乘数整体右移1位
DEC  R16
BRNE  MLOOP    ;17次右移后结束
RET
;范例9          ;16位整数被乘数*16位小数乘数-->16位整数积,精确到0.5
MUL165: RCALL  MUL16    ;先得到32位积
SBRS  R14,7    ;积小数部分最高位为1,将整数部分加1
第一首七言诗
RET            ;否则返回
LDI  R17,255
SUB  R13,R17只有一个地球教学实录
SBC  R12,R17    ;以减去-1($FFFF)替代加1
RET
;范例10          ;32位被除数/16位除数-->16位商,精确到1
DIV16: LDI  R16,16    ;(r12r13r14r15)/(r10r11)-->r14r15
DLOOP: LSL  R15     
ROL  R14
ROL  R13
ROL  R12      ;被除数左移1位
BRCS  DI1
SUB  R13,R11
SBC  R12,R10    ;移出位为0,被除数高位字减去除数试商
BRCC  DI2      ;够减,本位商为1
ADD  R13,R11
ADC  R12,R10    ;否则恢复被除数
RJMP  DI3      ;本位商0
DI1:  SUB  R13,R11
SBC  R12,R10    ;移出位为1,被除数高位字减去除数
DI2:  INC  R15      ;本位商1
DI3:  DEC  R16
BRNE  DLOOP
RET
;范例11          ;32位被除数/16位除数-->16位商,精确到0.5
;可能产生溢出!例$7FFFC000/$8000=$FFFF.8->$10000!
DIV165: RCALL  DIV16    ;(r12r13r14r15)/(r10r11)-->r14r15
LSL  R13     
ROL  R12      ;余数乘2
BRCS  D165      ;有进位,转5入
SUB  R13,R11
SBC  R12,R10    ;否则,余数乘2减去除数
BRCS  D164      ;不够减,转4舍
D165:  CLR  R13      ;否则将商增1
SEC           
ADC  R15,R13
ADC  R14,R13
ADC  R13,R13    ;若有溢出,溢出位在R13中
RET
D164:  CLR  R13
RET
;范例12          ;32位整数/16位整数->16整数+16位小数->4字节浮点数
;(r12r13r14r15)/(r10r11)-->r12r13r14r15
DIV16F: RCALL  DIV16    ;先做整数除法
MOV  R9,r15   
MOV  R8,r14    ;保存整数部分
CLR  R15
CLR  R14
RCALL  DIV16    ;除得小数部分
MOV  R11,R15
MOV  R15,R14
MOV  R13,R8
MOV  R14,R9    ;整数部分在r13r14,小数部分在r15r11
LDI  R17,$90    ;预
设阶码$90(整数为16位)
MOV  R12,R17
LDI  R17,32    ;设32次右移
DIV16L: SBRC  R13,7   
RJMP  NMLDN    ;最高位为1,已完成规格化
LSL  R11      ;否则继续右移R13,R14,R15,R11
ROL  R15
ROL  R14
ROL  R13     
DEC  R12      ;阶码减1
DEC  R17
BRNE  DIV16L   
CLR  R12      ;右移达32次,浮点数为零,置零阶
RET
NMLDN: SBRS  R11,7   
RJMP  DIVRT    ;欲舍去部分(R11)最高位为0,转4舍
RCALL  INC3      ;否则尾数部分增1
BRNE  DIVRT
INC  R12      ;尾数增1后变为0,改为0.5,并将阶码增1
DIVRT: LDI  R17,$7F    ;将尾数最高位清除,表示正数(负数不要清除)
AND  R13,R17    ;规格化浮点数在R12(阶码)R13R14R15(尾数)中
RET
;范例13          ;(R16,R12,R13,R14,R15)/(R10,R11)-->R13,R14,R15
DIV24: CLR  R16      ;32位整数/16位整数->24位整数,要求(R10)不为0;否则
;要求(R12)<(R11)
DIV40: LDI  17,24    ;40位整数/16位整数->24位整数 要求(R16,R12)
LXP:  LSL  R15      ; <(R10,R11)
ROL  R14
ROL  R13
ROL  R12
ROL  R16
BRCC  LXP1
SUB  R12,R11    ;右移后C=1 够减
SBC  R16,R10    ;被除数减去除数
RJMP  DIV0      ;本位商为1
LXP1:  SUB  R12,R11    ;C=0
SBC  R16,R10    ;被除数减去除数试商
BRCC  DIV0      ;C=0 够减,本位商1
ADD  R12,R11
ADC  R16,R10    ;否则恢复被除数,本位商0
RJMP  DIV1
DIV0:  INC  R15      ;记本位商1
DIV1:  DEC  R17
BRNE  LXP
LSL  R12
灰度图
ROL  R16
BRCS  GINC      ;C=1,5入
SUB  R12,R11
SBC  R16,R10
BRCS  RET3      ;不够减,舍掉
GINC:  RCALL  INC3      ;将商增1
RET3:  RET
;范例14          ;定点整数(最大$FFFFFFFF)开平方子程序
INTSQR: LDI  R16,17    ;SQR(R12,R13,R14,R15)-->(r15r8r9)
CLR  R8      ;R8,R9存储平方根
CLR  R9      ;r10,r11,r12,r13,r14,r15
CLR  R10      ; r8, r9(根)      r16 (counter)
CLR  R11      ;r10,r11:被开平方数扩展字节
LDI  R17,$40   
SQR0:  SUB  R12,R17
SBC  R11,R9
SBC  R10,R8
BRCS  SQR1
SEC            ;试根够减,本位根1
RJMP  SQR2
SQR1:  ADD  R12,R17
ADC  R11,R9
ADC  R10,R8
CLC            ;否则恢复被开平方数,本位根0
SQR2:  DEC  R16
BRNE  SQR3      ;when the No.17bit of root be getting
SQR20: ADC  R9,R15    ;R15 HAVE BEEN CLEARED!
ADC  R8,R15
ADC  R15,R15    ;将开出之根4舍5入,使根最大可达65536(=$10000)!
RET            ;for example:sqr.($ffff0001)≈$10000
SQR3:  ROL  R9
ROL  R8      ;记本位根
LSL  R15
ROL  R14
ROL  R13
ROL  R12     
ROL  R11
ROL  R10      ;被开平方数连同
其扩展字节左移一位
LSL  R15
ROL  R14
ROL  R13
ROL  R12
ROL  R11
ROL  R10      ;被开平方数连同其扩展字节再次左移一位/左移2位开出1位根
BRCS  SQR20    ;被开平方数左移2位后,若进位置位,则仅表明第17位根
;已被提前开出且该位根=1,将平方根增1,开平方结束。
RJMP  SQR0      ;否则转试下一位根   
;范例15          ;定点整数二翻十
CONV1: LDI  R17,24    ;r12r13r14r15<--(r9r10r11)左移24次
MOV  R7,R17    ;例:16777215<--$FFFFFF
CLR  R12
CLR  R13      ;68719476735<--$FFFFFFFFF
CLR  R14      ;1099511627775<--$FFFFFFFFFF
CLR  R15      ;十进制数存储区予清除
CV1:  LSL  R11
ROL  R10
ROL  R9      ;二进制数整体左移一位
MOV  R16,R15
RCALL  LSDAA
MOV  R15,R16
MOV  R16,R14
RCALL  LSDAA
MOV  R14,R16
MOV  R16,R13
RCALL  LSDAA
MOV  R13,R16   
MOV  R16,R12
RCALL  LSDAA      ;十进制数左移并调整
MOV  R12,R16
DEC  R7
BRNE  CV1
RET
;范例16          ;定点整数十翻二
CONV2: LDI  R17,24    ;(r9r10r11)-->r13r14r15,右移24次
CLR  R31      ;例:999999-->$0F423F
MOV  R7,R17    ; 99999999-->$05F5E0FF
CV2:  LSR  R9
ROR  R10
ROR  R11     
ROR  R13
ROR  R14
ROR  R15      ;十进制数连同二进制数右移一位
LDI  R30,12    ;数据指针
CV2L:  LD    R16,-Z
RCALL  RSDAA      ;十进制数右移调整
ST    Z,R16
CPI  R30,9      ;十进制数各字节调整完毕?
BRNE  CV2L
DEC  R7        ;右移次数(24次)完成?
BRNE  CV2
RET
;范例17          ;定点小数二翻十
CONV3: LDI  R17,24    ;(r13r14r15)--->r9r10r11r12右移24次
CONV31: MOV  R7,R17
CLR  R9     
CLR  R10      ;例:$0.FFFFFF-->0.99999994
CLR  R11      ;$0.FFFFFFFF-->0.999999999767
CLR  R12      ;$0.FFFFFFFFF->0.999999999985448
CLR  R31
CV3:  LSR  R13
ROR  R14
ROR  R15
ROR  R9
ROR  R10
ROR  R11
ROR  R12      ;二进制数连同十进制数右移一位
LDI  R30,9
CV3L:  LD    R16,Z
RCALL  RSDAA    ;十进制数右移调整
ST    Z+,r16
CPI  R30,13
BRNE  CV3L      ;十进制数各字节调整完毕?
DEC  R7
BRNE  CV3      ;右移次数(24次)完成?
RET
;范例18          ;定点小数十翻二
CONV4: LDI  R17,32    ;r12r13r14r15<--r8r9r10r11<--(r12r13r14r15)
MOV  R7,R17    ;左移32次
CV4:  CLC            ;例:$0.FFFFFFD5<--0.99999999
MOV  R16,R15    ;$0.FFFFFFFF92<--0.9999999999
RCALL  LSDAA
MOV  R15,R16
MOV  R16,R14
RCALL  LSDAA
MOV  R14,R16
MOV  R16,R13
RCALL  LSDAA
MOV  R13,R16
MO
V  R16,R12
RCALL  LSDAA
MOV  R12,R16    ;定点十进制小数左移并调整
ROL  R11
ROL  R10
ROL  R9
ROL  R8      ;定点二进制小数带进位位左移一位
DEC  R7
BRNE  CV4
MOV    R12,R8    ;最终结果转入R12--R15
MOV    R13,R9
MOV    R14,R10
MOV  R15,R11
RET
;范例19          ;等步距线性内插计算子程序
.EQU  TBLGTH=10
CHETA: LDI  R16,TBLGTH-1 ;r16<--表长(即字数)-1
LDI  R31,HIGH(chtbl*2);y0(函数初值)在r14r15,STEP(步长)在r10r11,自变量X在r12r13
LDI  R30,LOW(chtbl*2+1);查表指针,首指数据表第1字之高位字节!
RCALL  CPMR1    ;X与表中第一个字型数据(X0)比较
BRCC  CHRET    ;X<X0 查表结束,Y=Y0
CHET1: RCALL  CMPR1    ;X与表中下一个数据比较
BRCC  NX33      ;X<X(i+1) 到插值区间
ADD  R15,R11    ;否则Y0中加入一个STEP:Yk=Y0+k*step(步距为负时则
减去|STEP|)
ADC  R14,R10
DEC  R16     
BRNE  CHET1    ;未查到表格终值,循环;否则结束,Y取得最大值Yn
CHRET: RET
NX33:  SBIW  R30,5    ;指针退回(-5),指向Xi
MOV  R8,R14
MOV  R9,R15    ;保存Y0+i*STEP
RCALL  SUBS      ;(X-Xi)-->r16r17
MOV  R15,R17
MOV  R14,R16    ;转入r14r15
RCALL  MUL16    ;(X-Xi)*STEP-->r12r13r14r15
MOV  R10,R12
灵魂MOV  R11,R13    ;保存乘积高位字
LPM            ;X(i+1)低位字节
MOV  R13,R0
ADIW  R30,1
LPM            ;X(i+1)高位字节
MOV  R12,R0
SBIW  R30,3    ;指针指向Xi
RCALL  SUBS      ;X(i+1)-Xi-->r16r17
MOV  R12,R10
MOV  R13,R11    ;取回乘积高位字
MOV  R10,R16
MOV  R11,R17    ;X(i+1)-Xi-->r10r11
RCALL  DIV165    ;(X-Xi)*STEP/[X(i+1)-Xi]-->r14r15
ADD  R15,R9
ADC  R14,R8    ;Y0+i*STEP+(X-Xi)*STEP/[X(i+1)-Xi]-->r14r15
RET            ;若STEP为负值则改为计算(r8r9)减去(r14r15)之值
CMPR1: LPM            ;取数据高位字节
ADIW  R30,2    ;指向下一数据的高位字节
CP    R0,R12    ;与X高位字节相比较
BRNE  CPRT1    ;不相等即转出
SBIW  R30,3    ;否则调整指针
LPM            ;取数据低位字节
ADIW  R30,3    ;指向下一数据的高位字节
CP    R0,R13    ;与X低位字节相比较
CPRT1: RET            ;以进位C带回比较结果
SUBS:  LPM            ;计算(X-Xi)或[X(i+1)-Xi]并送入r16r17
MOV  R5,R0    ;取Xi低位字节
ADIW  R30,1
LPM            ;取Xi高位字节
SBIW  R30,1    ;仍指向Xi低位字节
SUB  R13,R5
MOV  R17,R13
SBC  R12,R0
MOV  R16,R12    ;计算差并将其转入R16R17
RET
;自变量x表长为12字云南开远惊现死亡地带
CHTBL:DW 19214,23404,27600,32799,37009,40211,45414,48618,51821,55029,57787,60070
;步距表长为11
STEPT: DW 356,366,379,395,415,440,471,509,555,603,657
;不等步距线性内插计算子程序,步距表首址在R6R7中
;自变量X在R12R13之中, 函数初值Y0在R14R15中
范例20          ;表长(字个数)-1在R16中
CHTSTP: LDI  R31,HIGH(chtbl*2)
LDI  R30,LOW(chtbl*2+1);查表指针
LDI  R16,LOW(stept*2)
MOV  R7,R16
LDI  R16,HIGH(stept*2)
MOV  R6,R16    ;步距表指针
LDI  R16,TBLGTH-1 ;r16<--表长(字个数)-1
RCALL  CMPR1    ;X与表首数据比较
BRCC  CHSTPT    ;X<X0 查表结束,有Y=Y0
CHSTP1: RCALL  CMPR1    ;否则与表中下一数据比较
BRCC  CHSTP3    ;X<X(i+1),到插值区间!
RCALL  GTSTP    ;查表取STEP字型变量
ADD  R15,R11    ;Y0<--Y0+STEPk
ADC  R14,R10
DEC  R16     
BRNE  CHSTP1    ;未查到表格终值循环;否则结束,Y取得最大值Yn
CHSTPT: RET           
CHSTP3: SBIW  R30,5    ;指针退回,指向Xi低位字节
MOV  R8,R14
MOV  R9,R15    ;Y0+∑STEPk送入r14 r15
RCALL  SUBS      ;(X-Xi)->r16r17
MOV  R15,R17
MOV  R14,R16    ;(X-Xi)转入R14R15
RCALL  GTSTP    ;查表取STEPi-->R10R11
RCALL  MUL16    ;(X-Xi)*STEPi-->R12R13R14R15
MOV  R10,R12
MOV  R11,R13    ;保存积高位字
LPM
MOV  R13,R0
ADIW  R30,1
LPM
MOV  R12,R0
SBIW  R30,3
RCALL  SUBS      ;(X(i+1)-Xi)-->r16 r17
MOV  R12,R10
MOV  R13,R11
MOV  R10,R16
MOV  R11,R17    ;取回积高位字 &(X(i+1)-Xi)-->r10r11
RCALL  DIV165    ;(X-Xi)*STEPi/[X(i+1)-Xi]-->r14r15
ADD  R15,R9    ;
ADC  R14,R8    ;Y0+∑STEPk+(X-Xi)*STEPi/[X(i+1)-Xi]-->r14r15
RET
GTSTP: MOV  R5,R6    ;查取STEP字型变量/POINTER in r6r7!
MOV  R6,R30
MOV  R30,R5
MOV  R5,R7
MOV  R7,R31
MOV  R31,R5    ;(r6r7)<-->Z
LPM
MOV  R11,R0
ADIW  R30,1
LPM
MOV  R10,R0    ;STEPk取到r10r11
ADIW  R30,1   
MOV  R5,R6
MOV  R6,R30
MOV  R30,R5
MOV  R5,R7
MOV  R7,R31
MOV  R31,R5    ;指针增2后送回r6r7
RET
;范例21          ;功能表程序
FUNC2: LDS  R16,$A3    ;use r0,r8,r9,r10,r11,r16&r17/& subprogram dspa
SBR  R16,$80    ;功能表程序标志
STS  $A3,R16
LDI  YH,2
LDI  YL,0      ;功能内容表SRAM地址
RCALL  FLFUNC    ;CLR r27!
LDI  R16,2
ST    X,R16    ;显示'FUNC.2'
RCALL  DL2S
CLR  R9      ;功能内容寻址偏移量R9!
CLR  R8      ;功能名称寻址偏移量(R8)=(r9)*3
FFUNC0: RCALL  DSF_      ;显示'F- '
FF0:  RCALL  DSPA      ;in subprogram dspy clr. r27!
CPI  R16,11    ;回车键按下?
BRNE  FF2P
FF0C:  RCALL  COMBNO    ;合成功能名称送入r16
CPI  R16,20    ;是最后一个功能名称?
BRNE  FF1
CLR  R9      ;是,两偏移量初

本文发布于:2024-09-22 01:38:58,感谢您对本站的认可!

本文链接:https://www.17tex.com/xueshu/421686.html

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。

标签:字节   调整   高位   子程序   整数
留言与评论(共有 0 条评论)
   
验证码:
Copyright ©2019-2024 Comsenz Inc.Powered by © 易纺专利技术学习网 豫ICP备2022007602号 豫公网安备41160202000603 站长QQ:729038198 关于我们 投诉建议