📄 sisp.s
字号:
rcall getc ; EOP ldi r_data, STK_INSYNC ; INSYNC rcall putc ldi r_isp, 0x50 ; Read fuse bits command rcall ispxcg ldi r_isp, 0x00 ; Must be zero, don't care on mega103 rcall ispxcg rcall ispget ; Don't care rcall ispget ; These are the bits mov r_data, r_isp rcall putc ; ATmega128 only ldi r_isp, 0x58 ; Read high fuses bits command rcall ispxcg ldi r_isp, 0x08 ; Must be 8 rcall ispxcg rcall ispget ; Don't care rcall ispget ; Here we get them mov r_data, r_isp rcall putc rjmp cmdfirm; *********************************************************************; PC command: Read Lock Bitsc73: cpi r_data, 0x73 ; 's' brne c74 rcall getc ; EOP ldi r_data, STK_INSYNC ; INSYNC rcall putc ldi r_isp, 0x58 rcall ispxcg ldi r_isp, 0x00 rcall ispxcg rcall ispget rcall ispget mov r_data, r_isp rcall putc rjmp cmdfirm; *********************************************************************; PC command: Read Pagec74: cpi r_data, 0x74 ; 't' brne c75 rcall getc mov r29, r_data rcall getc mov r28, r_data rcall getc ; 'F' or 'E' cpi r_data, 'F' brne c74ee rcall getc ; EOP ldi r_data, STK_INSYNC ; INSYNC rcall putc lds r30, paddrl lds r31, paddrhc74a: ldi r_isp, 0x20 rcall ispxcg mov r_isp, r31 rcall ispxcg mov r_isp, r30 rcall ispxcg rcall ispget mov r_data, r_isp rcall putc ldi r_isp, 0x28 rcall ispxcg mov r_isp, r31 rcall ispxcg mov r_isp, r30 rcall ispxcg rcall ispget mov r_data, r_isp rcall putc adiw r30, 1 sbiw r28, 2 brne c74a rjmp cmdfirmc74ee: rcall getc ; EOP ldi r_data, STK_INSYNC ; INSYNC rcall putc lds r30, paddrl lds r31, paddrhc74ea: ldi r_isp, 0xA0 rcall ispxcg mov r_isp, r31 rcall ispxcg mov r_isp, r30 rcall ispxcg rcall ispget mov r_data, r_isp rcall putc adiw r30, 1 sbiw r28, 1 brne c74ea rjmp cmdfirm; *********************************************************************; PC command: Read Signaturec75: cpi r_data, 0x75 ; 'u' brne c76 rcall getc ldi r_data, STK_INSYNC rcall putc ldi r_isp, 0x30 rcall ispxcg rcall ispget rcall ispget rcall ispget mov r_data, r_isp rcall putc ldi r_isp, 0x30 rcall ispxcg rcall ispget ldi r_isp, 0x01 rcall ispxcg rcall ispget mov r_data, r_isp rcall putc ldi r_isp, 0x30 rcall ispxcg rcall ispget ldi r_isp, 0x02 rcall ispxcg rcall ispget mov r_data, r_isp rcall putc rjmp cmdfirm; *********************************************************************; PC command: Read Oscillator Calibration Bytec76: cpi r_data, 0x76 ; 'v' brne c77 rcall getc ; EOP ldi r_data, STK_INSYNC ; INSYNC rcall putc ldi r_isp, 0x38 rcall ispxcg rcall ispget rcall ispget rcall ispget mov r_data, r_isp rcall putc rjmp cmdfirm; *********************************************************************; PC command: Read Fuse Bits Extendedc77: cpi r_data, 0x77 ; 'w' brne c78 rcall getc ; EOP ldi r_data, STK_INSYNC ; INSYNC rcall putc ldi r_isp, 0x50 rcall ispxcg ldi r_isp, 0x00 rcall ispxcg rcall ispget rcall ispget mov r_data, r_isp rcall putc ldi r_isp, 0x58 rcall ispxcg ldi r_isp, 0x08 rcall ispxcg rcall ispget rcall ispget mov r_data, r_isp rcall putc ldi r_isp, 0x50 rcall ispxcg ldi r_isp, 0x08 rcall ispxcg rcall ispget rcall ispget mov r_data, r_isp rcall putc rjmp cmdfirm; *********************************************************************; PC command: Read Oscillator Calibration Byte Extendedc78: cpi r_data, 0x78 ; 'x' brne cbad rcall getc mov r30, r_data rcall getc ; EOP ldi r_data, STK_INSYNC ; INSYNC rcall putc ldi r_isp, 0x38 rcall ispxcg rcall ispget mov r_isp, r30 rcall ispxcg rcall ispget mov r_data, r_isp rcall putc rjmp cmdfirm; *********************************************************************; PC command: Unknowncbad: rjmp cmdend; *********************************************************************; *** GetParmgetparm: ; ; Hardware version cpi r_parm, 0x80 brne _gp81 ldi r_data, 2 ret ; ; Software version major_gp81: cpi r_parm, 0x81 brne _gp82 ldi r_data, 1 ret ; ; Software version minor_gp82: cpi r_parm, 0x82 brne _gp83 ldi r_data, 14 ret ; ; LEDs_gp83: cpi r_parm, 0x83 brne _gp84 ldi r_data, 1 ret ; ; Target voltage_gp84: cpi r_parm, 0x84 brne _gp85 ldi r_data, 50 ret ; ; Adjustable Voltage_gp85: cpi r_parm, 0x85 brne _gp86 ldi r_data, 50 ret ; ; Oscillator timer prescaler value_gp86: cpi r_parm, 0x86 brne _gp87 ldi r_data, 0 ret ; ; Oscillator timer compare match value_gp87: cpi r_parm, 0x87 brne _gp88 ldi r_data, 0 ret ; ; Reset duration_gp88: cpi r_parm, 0x88 brne _gp89 ldi r_data, 0x30 ret ; ; SCK duration_gp89: cpi r_parm, 0x89 brne _gp90 ldi r_data, 0x30 ret ; ; Bufsiz low_gp90: cpi r_parm, 0x90 brne _gp91 ldi r_data, 64 ret ; ; Bufsiz high_gp91: cpi r_parm, 0x91 brne _gp92 ldi r_data, 0 ret ; ; Device_gp92: cpi r_parm, 0x92 brne _gp93 lds r_data, pm_devicecode ret ; ; Progmode_gp93: cpi r_parm, 0x93 brne _gp94 lds r_data, pm_progtype ret ; ; Para mode_gp94: cpi r_parm, 0x94 brne _gp95 lds r_data, pm_parmode ret ; ; Polling_gp95: cpi r_parm, 0x95 brne _gp96 lds r_data, pm_polling ret ; ; Self timed_gp96: cpi r_parm, 0x96 brne _gpuk lds r_data, pm_selftimed ret ; ; Unknown_gpuk: clr r_data ret;; *********************************************************************; UART routines; The UART is used in polling mode.; Receive a single byte into register r_data.;; This routine will not return until a byte is available.;getc: sbis _SFR_IO_ADDR(USR), RXC rjmp getc in r_data, _SFR_IO_ADDR(UDR) ret; Send a single byte passed in register r_data.;putc: sbis _SFR_IO_ADDR(USR), UDRE rjmp putc out _SFR_IO_ADDR(UDR), r_data ret; *********************************************************************; Exchange ISP Byteispget: clr r_ispispxcg: ldi r_temp, 8 clr r_shift ; ; Start of 8-bit loop_ispa: rol r_isp ; (1) brcc _ispb ; (2/1) sbi _SFR_IO_ADDR(PORTB), ISPMOSI ; (2) rjmp _ispc ; (2)_ispb: cbi _SFR_IO_ADDR(PORTB), ISPMOSI ; (2)_ispc: nop ; (1) sbi _SFR_IO_ADDR(PORTB), ISPSCK ; (2) lsl r_shift ; (1) sbic _SFR_IO_ADDR(PINB), ISPMISO ; (2/1) ori r_shift, 1 ; (1) cbi _SFR_IO_ADDR(PORTB), ISPSCK ; (2) ; ; End of 8-bit loop dec r_temp ; (1) brne _ispa ; (2/1) mov r_isp, r_shift ; (1) ret ; (4); *********************************************************************; Send out a byte to ISP as fast as possible.;; Runtime calculation:; + 7 cycles for rcall/return; + 1 cycle to initially read the port status; + 4 cycle to set the final port status; + 48 cycles for output, 6 cycles per bit; The total of 60 cycles takes 16.276 microseconds on a 3.6864 MHz MCU.; At 115 kBaud a new character is received every 86.8 microsecond.; The SCK low time is 814 nanoseconds and the high time is 543 nanoseconds.; Following the datasheet, the target requires a minimum SCK low and; high time of 2 clock cycles. So we may not be able to program targets; running with same or higher crystals than our own.; Tests with an ATmega128 showed, that it was possible to program the; chip while running on its internal oscillator down to 2 MHz.;ispput: ; (3) Costly call in r_temp, _SFR_IO_ADDR(PORTB) ; (1) Load current port status bst r_isp, 7 ; (1) Bit7 -> T bld r_temp, ISPMOSI ; (1) T -> MOSI out _SFR_IO_ADDR(PORTB), r_temp ; (1) Output, SCK still low sbi _SFR_IO_ADDR(PORTB), ISPSCK ; (2) SCK high bst r_isp, 6 ; (1) bld r_temp, ISPMOSI ; (1) out _SFR_IO_ADDR(PORTB), r_temp ; SCK back to low after about 3 cycles nop sbi _SFR_IO_ADDR(PORTB), ISPSCK ; SCK high again after about 2 cycles bst r_isp, 5 bld r_temp, ISPMOSI out _SFR_IO_ADDR(PORTB), r_temp nop sbi _SFR_IO_ADDR(PORTB), ISPSCK bst r_isp, 4 bld r_temp, ISPMOSI out _SFR_IO_ADDR(PORTB), r_temp nop sbi _SFR_IO_ADDR(PORTB), ISPSCK bst r_isp, 3 bld r_temp, ISPMOSI out _SFR_IO_ADDR(PORTB), r_temp nop sbi _SFR_IO_ADDR(PORTB), ISPSCK bst r_isp, 2 bld r_temp, ISPMOSI out _SFR_IO_ADDR(PORTB), r_temp nop sbi _SFR_IO_ADDR(PORTB), ISPSCK bst r_isp, 1 bld r_temp, ISPMOSI out _SFR_IO_ADDR(PORTB), r_temp nop sbi _SFR_IO_ADDR(PORTB), ISPSCK bst r_isp, 0 bld r_temp, ISPMOSI out _SFR_IO_ADDR(PORTB), r_temp nop sbi _SFR_IO_ADDR(PORTB), ISPSCK nop nop nop out _SFR_IO_ADDR(PORTB), r_temp ; (1) SCK low ret ; (4) Costly return; *********************************************************************; Delay;; xdelay takes about 53.6 msxdelay: ; (3) clr r_delay ; (1)delay: clr r_temp ; (1) Outer loop with r_delay * 772 cyclesdl: dec r_temp ; (1) Inner loop with 3 cycles brne dl ; (2/1) dec r_delay ; (1) brne delay ; (2/1) ret ; (4)#ifdef SISPDEBUG; *********************************************************************; Debug;puthexb: push r_data swap r_data rcall puthexc pop r_dataputhexc: push r_temp mov r_temp, r_data andi r_temp, 0x0f subi r_temp, -'0' cpi r_temp, 0x3a brlo _putx1 subi r_temp, -7_putx1: push r_data mov r_data, r_temp rcall putc pop r_data pop r_temp ret#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -