⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 bootm8v.bas

📁 bootloaer for mega 8 another one
💻 BAS
📖 第 1 页 / 共 2 页
字号:
   mov   lo_byte,hex_reg                                    'Save in LS Byte register
   rcall _char_to_byte                                      'Call routine to convert two characters to byte
   mov   hi_byte,hex_reg                                    'Save in MS Byte register

_verify_data_pair:                                          'Verify this data pair
   brts  _ver_end                                           'Do verify test only if VERIFY mode selected
   ldi   ser_reg, asc("!")                                  'Verify Error Flag
 _ver_lo:
   lpm                                                      'Get the byte at this address
   cp    r0,lo_byte                                         'Compare to current LS byte
   breq  _ver_hi                                            'Branch if equal, otherwise send message
   rcall _send_ser                                          'Call routine to send a character
 _ver_hi:
   inc   ZL                                                 'Increment the address to the high byte
   lpm                                                      'Get the byte at this address
   dec   ZL                                                 'Decrement the address back to the low byte
   cp    r0,hi_byte                                         'Compare to current LS byte
   breq  _ver_end                                           'Branch if equal, otherwise send message
   rcall _send_ser                                          'Call routine to send a character
 _ver_end:


_store_word:                                                'Store current R1/R0 Word in page buffer at proper address
   mov   r0,lo_byte                                         'Save in R0, LS Byte of page write buffer
   mov   r1,hi_byte                                         'Save in R1, MS Byte of page write buffer
   ldi   spm_reg,1                                          'Load SPM Enable (SPMEN)
   rcall _exec_spm                                          'Execute current SPM, return is in exec_spm

_check_byte_count:                                          'Check if this was the last word of the line
   subi  byte_cnt,2                                         'Decrement the Byte Count by two bytes
   breq _read_checksum                                      'Done with this data, read checksum
   subi  ZL,$FE                                             'Not done, increment the low address byte by two
   rjmp  _read_data_pairs                                   'Go back and read the next two characters


_read_checksum:                                             'Byte count = record size, next is checksum for this line
   rcall _char_to_byte                                      'Call routine to convert two characters to byte
   breq  _checksum_ok                                       'Must have added to zero, checksum is okay
  _checksum_err:                                            'Checksum or other decoding error detected
   ldi   ser_reg, asc("C")                                  'Load "C" to send as Checksum error flag
   rcall _send_ser                                          'Call routine to send a character
  _checksum_ok:

'Done decoding and storing one complete input line, so check if this page is full

_chk_page_full:                                             'Check if this page is full
   mov   tmp_reg, ZL                                        'Load the address low byte into the temp reg
   andi  tmp_reg,((Pagesize - 1 )*2)                        'AND with page size for this device, mask bits
   cpi   tmp_reg,((Pagesize - 1 )*2)                        'Compare with page size for this device

   brne  _read_lines                                        'Page buffer is not full, read another line

_write_current_page:                                        'Write current page if the page buffer is full
   andi  ZL,$C0                                             'Page address in Z12 - Z6, ensure that Z5 - Z0 are 0

 _erase_page:                                               'Erase Page,
   ldi   spm_reg,3                                          'Load Page Erase (PGERS) and SPM Enable (SPMEN)
   rcall _exec_spm                                          'Execute current SPM

 _write_page:                                               'Page address range is Z12-Z6 for Mega8
   ldi   spm_reg,5                                          'Load page write (PGWRT) and SPM Enable (SPMEN)
   rcall _exec_spm                                          'Execute current SPM

 _enable_page:                                              'Re-enable the Read-While-Write section
   rcall _wait_spm                                          'Check if current write is complete
   ldi   spm_reg,11                                         'Set RWWSRE and SPMEN only
   rcall _exec_spm                                          'Execute current SPM

_check_end_of_file:                                         'Check if this is the end of the file - T Flag
   tst   rec_size                                           'Test if record size is zero for this line
   brne  _read_lines                                        'Not the last page, continue to read in data lines

_exit_bootloader:                                           'Done, exit the bootloader code
   ldi   ser_reg, asc("D")                                  'Load "D" to send as done flag
   rcall _send_ser                                          'Call routine to send a character

   jmp $0000                                                'Jump to main program reset vector

'*******************************************************************************
'Send a serial character
_send_ser:                                                  'Send a serial characater
   sbis  UCSRA,UDRE                                         'Check if USART data register is empty
   rjmp  _send_ser                                          'Not ready yet, wait
  !out   UDR,ser_reg                                        'Send serial register
 ret
'*******************************************************************************
'Get one line from the serial port and store at start of SRAM
_receive_hex_line:
   ldi   XH,$01                                             'Set pointers to SRAM location $0100
   ldi   XL,$00                                             'Above all registers

   ldi   ser_reg, asc(".")                                  'No data now, so load "." to show progress
   rcall _send_ser                                          'Call routine to send a character

 _receive_hex_line_char:                                    'Get a character from UART and add to buffer
   sbis  UCSRA,RXC                                          'Check UART for a serial character received
   rjmp  _receive_hex_line_char                             'No, check again...
   in    tmp_reg,UDR                                        'Store input character in temp register

'   mov   ser_reg, tmp_reg               'Echo this character for troubleshooting
'   rcall _send_ser                      'Call routine to send a character

   cpi   tmp_reg,13                                         'Compare with <CR>, input line terminator
   breq  _receive_hex_line_end                              'Yes, line is finished, branch to end
   st    x+,tmp_reg                                         'Otherwise store value then increment buffer and
   rjmp  _receive_hex_line_char                             'Go back and get next character

 _receive_hex_line_end:                                     'This input line is finished, so
 ret                                                        'Done with this line, so return
'*******************************************************************************
'Get two characters from buffer, add to checksum and return with result in hex_reg
_char_to_byte:
   ld    hex_reg,x+                                         'Load character into hex_reg, increment X
   subi  hex_reg,$41                                        'ASCII Value minus $41, "A"
   brcc  _char_to_byte1                                     'Branch if value was greater than $41
   subi  hex_reg,$F9                                        'Not greater, subtract $F9
 _char_to_byte1:
   subi  hex_reg,$F6                                        'Subtract $F6
   lsl   hex_reg                                            'Shift this data
   lsl   hex_reg                                            'Left for four bits
   lsl   hex_reg                                            'To move it into the
   lsl   hex_reg                                            'High nibble

   ld    tmp_reg,x+                                         'Get next character,
   subi  tmp_reg,$41                                        'ASCII Value minus $41, "A"
   brcc  _char_to_byte2                                     'Branch if value was greater than $41
   subi  tmp_reg,$F9                                        'Not greater, subtract $F9
 _char_to_byte2:
   subi  tmp_reg,$F6                                        'Subtract $F6

   add   hex_reg,tmp_reg                                    'Add into hex register
   add   chk_sum,hex_reg                                    'Add it into the checksum for this line
  ret
'*******************************************************************************
_exec_spm:                                                  'Execute the current SPM instruction
   brtc   _exec_spm_end                                     'Do SPMs only if PROGRAMMING mode selected

  !out   spmcr,spm_reg                                      'Send to SPM Control Register
   spm                                                      'Do SPM instruction

 _wait_spm:                                                 'Check if current flash write is complete
   in    spm_reg,spmcr                                      'Get the SPM control Register
   sbrc  spm_reg,spmen                                      'Check if SPM Enable flag is clear
   rjmp  _wait_spm                                          'No, go back and wait for SPMEN flag cleared

 _exec_spm_end:                                             'End of SPM routine
   ret                                                      'Flag cleared, Return
'*******************************************************************************

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -