89C51 十六轉十 十轉十六常用的做法 |
|
romextromext
一般會員 ![]() ![]() 發表:6 回覆:26 積分:11 註冊:2009-08-24 發送簡訊給我 |
這是我的其中一種做法好像沒人這樣做
另一種就是寫入數值一直加 [code delphi] ; 十六進制轉十進制 T01 EQU 30H T23 EQU 31H T45 EQU 32H RT01 EQU 33H RT23 EQU 34H RT45 EQU 35H RT0 EQU 39H ;十進位讀取數值的指標 RT1 EQU 3AH ; RT2 EQU 3BH ; RT3 EQU 3CH RT4 EQU 3DH RT5 EQU 3EH RT6 EQU 3FH ;可隨便使用的指標 TM0 EQU 20H.0 ; TM1 EQU 20H.1 ; ORG 0000 JMP START ORG 0003H ORG 000BH ORG 0013H ORG 001BH JMP START ORG 0030H START: MOV IE,#82H MOV TMOD,#01H MOV SP,#5FH MOV RT0,#00 MOV RT1,#8 MOV R0,#T01 D01: MOV R1,#RT01 MOV A,@R0 RRC A MOV @R0,A JC D02 INC RT0 INC RT0 INC RT0 DJNZ RT1,D01 JMP D03 D02: CLR C ; SETB TM0 CALL K01 CALL K01 CALL K01 ; CLR TM0 DJNZ RT1,D01 D03: MOV R0,#T23 MOV RT1,#08 CPL TM0 JB TM0,D01 JMP $ K01: ;JNB TM0,K02 MOV DPTR,#TABLE MOV A,RT0 MOVC A,@A DPTR MOV RT2,A MOV A,@R1 ADDC A,RT2 DA A MOV @R1,A INC R1 INC RT0 K02: RET TABLE: DB 01H,00H,00H DB 02H,00H,00H DB 04H,00H,00H DB 08H,00H,00H DB 16H,00H,00H DB 32H,00H,00H DB 64H,00H,00H DB 28H,01H,00H DB 56H,02H,00H DB 12H,05H,00H DB 24H,10H,00H DB 48H,20H,00H DB 96H,40H,00H DB 92H,81H,00H DB 84H,63H,01H DB 68H,27H,03H DB 36H,55H,06H END [/code] [code delphi] ; 十進制轉十六進制 T01 EQU 30H T23 EQU 31H T45 EQU 32H RT01 EQU 33H RT23 EQU 34H RT45 EQU 35H RT0 EQU 39H ;十進位讀取數值的指標 RT1 EQU 3AH ; RT2 EQU 3BH ; RT3 EQU 3CH RT4 EQU 3DH RT5 EQU 3EH RT6 EQU 3FH ;可隨便使用的指標 TM0 EQU 20H.0 ; TM1 EQU 20H.1 ; TM2 EQU 20H.2 ; TM3 EQU 20H.3 ; ORG 0000 JMP START ORG 0003H ORG 000BH ORG 0013H ORG 001BH JMP START ORG 0030H START: MOV R4,#96H MOV R3,#40H ;MOV RT0,#00 ;取得16幾次方的數值指標 SDD: CLR C CLR TM0 MOV R1,#RT01 MOV R0,#T01 ;取得千百位數的數值 CALL SD00 JB TM0,SD0 MOV R0,#T23 CALL SD10 JB TM0,SD0 MOV T01,RT01 MOV T23,RT23 INC RT2 JMP SDD SD0: CJNE R7,#01,SD1 MOV R4,#56H MOV R3,#02H MOV A,RT2 SWAP A MOV RT2,A INC R7 SD1: CJNE R7,#03,SD2 MOV R4,#16H MOV R3,#00H MOV RT3,RT2 MOV RT2,#00 INC R7 SD2: CJNE R7,#05,SD3 MOV R4,#01H MOV R3,#00H MOV A,RT2 SWAP A MOV RT2,A INC R7 SD3: CJNE R7,#07,SD4 MOV T01,RT2 MOV T23,RT3 JMP $ ;←結束點 SD4: JMP SDD SD00: MOV A,@R0 SUBB A,R4 CALL SB00 CALL SB10 MOV @R1,A INC R1 INC R0 ; MOV A,@R0 JNZ SD01 JNC SD01 INC R7 SETB TM0 RET SD01: INC RT0 RET SD10: MOV A,@R0 SUBB A,R3 CALL SB00 MOV @R1,A INC R0 MOV A,@R0 JNC SD12 INC R7 SETB TM0 RET SD12: DEC RT0 RET ; 16進置的減法轉10進制 跟DA指令一個功能 SB00: JNB AC,SB01 MOV B,A ANL A,#0FH MOV DPTR,#TAB1 MOVC A,@A DPTR ANL B,#0F0H ORL B,A MOV A,B SB01: RET SB10: JNC SB11 MOV B,A SWAP A ANL A,#0FH MOV DPTR,#TAB1 MOVC A,@A DPTR ANL B,#0FH SWAP A ORL B,A MOV A,B SB11: RET TAB1: DB 01H,02H,03H,04H,05H,06H,07H,01H DB 02H,03H,04H,05H,06H,07H,08H,09H END [/code] 我想知道別人都怎麼做的 我感覺我做的都耗費很大的空間 所以拿出來討論一下
------
這啥需要簽嗎 拿筆來 編輯記錄
|
bernie_w39
資深會員 ![]() ![]() ![]() ![]() ![]() 發表:3 回覆:199 積分:280 註冊:2007-10-07 發送簡訊給我 |
|
mymj
版主 ![]() ![]() ![]() ![]() ![]() ![]() 發表:132 回覆:486 積分:608 註冊:2002-10-25 發送簡訊給我 |
|
romextromext
一般會員 ![]() ![]() 發表:6 回覆:26 積分:11 註冊:2009-08-24 發送簡訊給我 |
===================引 用 bernie_w39 文 章=================== 有一種叫作 shift plus 3 的作法不錯. 速度快, 空間也小. 我記得已經有 PO 過. 如果找不到, 我再 PO 一次. 只是我的程式是 AVR 的, 不是 8051 的. 可以在 google 上找找看. 應該有些討論. 是這個嗎 http://delphi.ktop.com.tw/board.php?cid=173&fid=1167&tid=97623 AVR的不是8051的是什麼意思阿!! 意思是不能在8051用嗎!? 這是個C語言程式我有點看不董 不過我改天會請教老師教我 謝謝大大的分享!!
------
這啥需要簽嗎 拿筆來
編輯記錄
romextromext 重新編輯於 2009-11-09 22:38:28, 註解 無‧
|
romextromext
一般會員 ![]() ![]() 發表:6 回覆:26 積分:11 註冊:2009-08-24 發送簡訊給我 |
===================引 用 mymj 文 章=================== 連到這 http://www.boerde.de/~matthias/m8051/ 有許多51的範例程式 bin2bcd.zip utils01.zip mymj 感謝大大分享網站給我 我先閱讀一下他的內容(找翻譯機XDD) 在看他程式怎麼寫的 不過組合語言跟C語言差真多 上面大大的才幾行 我組合語言要寫近兩百行
------
這啥需要簽嗎 拿筆來 |
bernie_w39
資深會員 ![]() ![]() ![]() ![]() ![]() 發表:3 回覆:199 積分:280 註冊:2007-10-07 發送簡訊給我 |
其實不是 C 與組合語言的差異, 主要是作法上的差異. 我有用組合寫過,
也沒有多長, 附在後面給你參考. 但是這是 AVR 的組合, 與 8051 不一樣. 你可能要看懂意思之後再寫過. [code c#] hexToBcd: ; r17:r16 = HEX value ; r20:r19:r18 = BCD value push r16 push r17 push r21 push r22 push xl push xh clr r18 clr r19 clr r20 clr xh ldi r21, 16 hexToBcd1: ldi xl, 20 1 hexToBcd2: ld r22, -x subi r22, -3 sbrc r22, 3 st x, r22 ld r22, x subi r22, -0x30 sbrc r22, 7 st x, r22 cpi xl, 18 brne hexToBcd2 lsl r16 rol r17 rol r18 rol r19 rol r20 dec r21 brne hexToBcd1 pop xh pop xl pop r22 pop r21 pop r17 pop r16 ret [/code] 它的原理, 就是來源的 hex, 一個 bit 個 bit 左移出來, 然後 1bit 接 1bit 的左移進 bcd, 如果是 16bits 的數值, 就作 16 次. 這樣 bcd 的數值會和 hex 一樣. 但是 bcd 在作左移時 (相當於乘以 2), 如果結果是 A-F 的話, 要作調整. 將 A-F 的數值減 10, 然後高一位加 1. 也就是 BCD 的運算. 這個運算, 等同於將數值加上 6. 另外它又用了一個很聰明的作法, 如果在左移 (乘以 2) 之後, 數值是 A-F, 換句 話說, 在左移之前的數值, 會是 5, 6, 7 之一. 所以, 在左移前先將數值加上 3 試試, 如果加上 3 之後, 數值大於等於 8 (最高 bit 為 1) 時, 就表示左移後要作 6 的調整. 而左移後要 6, 相當於左移前要 3. 就是保留目前的值. 結論: 在左移前, 先試著加 3, 如果造成最高位元為 1, 就保留加 3 後的值. 否則就 使用加 3 前的值. 一個 byte 有兩個 nibble. 兩個 nibble 分別處理, 就是上面的程式了. |
romextromext
一般會員 ![]() ![]() 發表:6 回覆:26 積分:11 註冊:2009-08-24 發送簡訊給我 |
本站聲明 |
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。 2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。 3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇! |