[原创] 带有ROM的LM3S编程

mybays   2011-4-15 09:04 楼主
不知道各位使用带有ROM LM3S系列单片机的坛友们有没有碰到这个问题,flash能下载,但是验证失败。折腾了一宿,终于将这个问题解决。
将过程写下来,让以后的同学们少走弯路。

在调新的LM3S9B95开发板的时候,经常碰到的一个问题是flash编程后验证校验失败,提示信息如下:
(gdb) flash
target state: halted
target halted due to debug-request, current mode: Thread
xPSR: 0x61000000 pc: 0x00000748 msp: 0x20017fd0
erased address 0x00000000 length 262144 in 0.041978s
requesting target halt and executing a soft reset
target state: halted
target halted due to debug-request, current mode: Thread
xPSR: 0x01000000 pc: 0x01000c4c msp: 0x20000800
Algorithm flash write 111 words to 0x0, 0 remaining
wrote 446 byte from file main.axf in 0.195948s (2.222768 kb/s)
checksum mismatch - attempting binary compare
Verify operation failed address 0x00000001. Was 0x08 instead of 0x80

这也是这两天我一直在RAM里调试的原因,但是今天在必须编程固件的时候,我就必须得面对这个问题了.
用二进制文件查看器打开raw格式的固件,这里我使用的是hexdump,发现固件的前4个字是:
0000000 8000 2001 00f1 0000 01b9 0000 01bb 0000
由于hexdump没有显示4个字节的功能,所以这里就可以翻译为:
20018000 000000F1 000001B9 000001BB
第一个长字为堆栈的指针,LM3S9B95有96KB的RAM,16进制就是0x18000,基址为0x20000000.第2,3,4个长字为中断向量0,1,2的地址,可以看到程序编译结构没有问题.

根据上面的出错信息,flash的第2个字节0x00000001应该是0x80,但是读出来的却是0x08,这肯定有问题了.
是不是flash没擦除干净呢?
那就将flash全部清空:
(gdb) monitor stellaris mass_erase 0
stellaris mass erase complete
再次下载,还是出错.
是不是没有清除干净呢,再次执行monitor stellaris mass_erase 0将flash进行全部清除,然后查看flash的清除状态:
(gdb) monitor halt
target state: halted
target halted due to debug-request, current mode: Thread
xPSR: 0x61000000 pc: 0x20002062 msp: 0x20000800
(gdb) monitor stellaris mass_erase 0
stellaris mass erase complete
(gdb) monitor flash erase_check 0
AHBAP Cached values: dp_select 0x0, ap_csw 0xa2000012, ap_tar 0xffffffff
SWJ-DP STICKY ERROR
Read MEM_AP_CSW 0x23000052, MEM_AP_TAR 0x6a04
AHBAP Cached values: dp_select 0x0, ap_csw 0xa2000012, ap_tar 0xffffffff
SWJ-DP STICKY ERROR
Read MEM_AP_CSW 0x23000052, MEM_AP_TAR 0x6a04
Block read error address 0x6800, count 0x100
unknown error when checking erase state of flash bank #0 at 0x00000000
        #  0: 0x00000000 (0x400 1kB) not erased
        #  1: 0x00000400 (0x400 1kB) not erased
        #  2: 0x00000800 (0x400 1kB) not erased
        #  3: 0x00000c00 (0x400 1kB) not erased
        #  4: 0x00001000 (0x400 1kB) not erased
        #  5: 0x00001400 (0x400 1kB) not erased
        #  6: 0x00001800 (0x400 1kB) not erased
        #  7: 0x00001c00 (0x400 1kB) not erased
        #  8: 0x00002000 (0x400 1kB) not erased
        #  9: 0x00002400 (0x400 1kB) not erased
        # 10: 0x00002800 (0x400 1kB) not erased
        # 11: 0x00002c00 (0x400 1kB) not erased
        # 12: 0x00003000 (0x400 1kB) not erased
        # 13: 0x00003400 (0x400 1kB) not erased
        # 14: 0x00003800 (0x400 1kB) not erased
        # 15: 0x00003c00 (0x400 1kB) not erased
        # 16: 0x00004000 (0x400 1kB) not erased
        # 17: 0x00004400 (0x400 1kB) not erased
        # 18: 0x00004800 (0x400 1kB) not erased
        # 19: 0x00004c00 (0x400 1kB) not erased
        # 20: 0x00005000 (0x400 1kB) not erased
        # 21: 0x00005400 (0x400 1kB) not erased
        # 22: 0x00005800 (0x400 1kB) not erased
        # 23: 0x00005c00 (0x400 1kB) not erased
        # 24: 0x00006000 (0x400 1kB) not erased
        # 25: 0x00006400 (0x400 1kB) not erased
        # 26: 0x00006800 (0x400 1kB) erased
        # 27: 0x00006c00 (0x400 1kB) erased
        # 28: 0x00007000 (0x400 1kB) erased
        # 29: 0x00007400 (0x400 1kB) erased
        # 30: 0x00007800 (0x400 1kB) erased
        # 31: 0x00007c00 (0x400 1kB) erased
        # 32: 0x00008000 (0x400 1kB) erased
        # 33: 0x00008400 (0x400 1kB) erased
        # 34: 0x00008800 (0x400 1kB) erased
        # 35: 0x00008c00 (0x400 1kB) erased
        # 36: 0x00009000 (0x400 1kB) erased
        # 37: 0x00009400 (0x400 1kB) erased
        # 38: 0x00009800 (0x400 1kB) erased
        # 39: 0x00009c00 (0x400 1kB) erased
        # 40: 0x0000a000 (0x400 1kB) erased
        # 41: 0x0000a400 (0x400 1kB) erased
        # 42: 0x0000a800 (0x400 1kB) erased
        # 43: 0x0000ac00 (0x400 1kB) erased
        # 44: 0x0000b000 (0x400 1kB) erased
        # 45: 0x0000b400 (0x400 1kB) erased
        # 46: 0x0000b800 (0x400 1kB) erased
        # 47: 0x0000bc00 (0x400 1kB) erased
        # 48: 0x0000c000 (0x400 1kB) erased
        # 49: 0x0000c400 (0x400 1kB) erased
        # 50: 0x0000c800 (0x400 1kB) erased
        # 51: 0x0000cc00 (0x400 1kB) erased
        # 52: 0x0000d000 (0x400 1kB) erased
        # 53: 0x0000d400 (0x400 1kB) erased
        # 54: 0x0000d800 (0x400 1kB) erased
        # 55: 0x0000dc00 (0x400 1kB) erased
        # 56: 0x0000e000 (0x400 1kB) erased
        # 57: 0x0000e400 (0x400 1kB) erased
        # 58: 0x0000e800 (0x400 1kB) erased
        # 59: 0x0000ec00 (0x400 1kB) erased
        # 60: 0x0000f000 (0x400 1kB) erased
        # 61: 0x0000f400 (0x400 1kB) erased
        # 62: 0x0000f800 (0x400 1kB) erased
        # 63: 0x0000fc00 (0x400 1kB) erased
        # 64: 0x00010000 (0x400 1kB) erased
        # 65: 0x00010400 (0x400 1kB) erased
        # 66: 0x00010800 (0x400 1kB) erased
        # 67: 0x00010c00 (0x400 1kB) erased
        # 68: 0x00011000 (0x400 1kB) erased
        # 69: 0x00011400 (0x400 1kB) erased
        # 70: 0x00011800 (0x400 1kB) erased
        # 71: 0x00011c00 (0x400 1kB) erased
        # 72: 0x00012000 (0x400 1kB) erased
        # 73: 0x00012400 (0x400 1kB) erased
        # 74: 0x00012800 (0x400 1kB) erased
        # 75: 0x00012c00 (0x400 1kB) erased
        # 76: 0x00013000 (0x400 1kB) erased
        # 77: 0x00013400 (0x400 1kB) erased
        # 78: 0x00013800 (0x400 1kB) erased
        # 79: 0x00013c00 (0x400 1kB) erased
        # 80: 0x00014000 (0x400 1kB) erased
        # 81: 0x00014400 (0x400 1kB) erased
        # 82: 0x00014800 (0x400 1kB) erased
        # 83: 0x00014c00 (0x400 1kB) erased
        # 84: 0x00015000 (0x400 1kB) erased
        # 85: 0x00015400 (0x400 1kB) erased
        # 86: 0x00015800 (0x400 1kB) erased
        # 87: 0x00015c00 (0x400 1kB) erased
        # 88: 0x00016000 (0x400 1kB) erased
        # 89: 0x00016400 (0x400 1kB) erased
        # 90: 0x00016800 (0x400 1kB) erased
        # 91: 0x00016c00 (0x400 1kB) erased
        # 92: 0x00017000 (0x400 1kB) erased
        # 93: 0x00017400 (0x400 1kB) erased
        # 94: 0x00017800 (0x400 1kB) erased
        # 95: 0x00017c00 (0x400 1kB) erased
        # 96: 0x00018000 (0x400 1kB) erased
        # 97: 0x00018400 (0x400 1kB) erased
        # 98: 0x00018800 (0x400 1kB) erased
        # 99: 0x00018c00 (0x400 1kB) erased
        #100: 0x00019000 (0x400 1kB) erased
        #101: 0x00019400 (0x400 1kB) erased
        #102: 0x00019800 (0x400 1kB) erased
        #103: 0x00019c00 (0x400 1kB) erased
        #104: 0x0001a000 (0x400 1kB) erased
        #105: 0x0001a400 (0x400 1kB) erased
        #106: 0x0001a800 (0x400 1kB) erased
        #107: 0x0001ac00 (0x400 1kB) erased
        #108: 0x0001b000 (0x400 1kB) erased
        #109: 0x0001b400 (0x400 1kB) erased
        #110: 0x0001b800 (0x400 1kB) erased
        #111: 0x0001bc00 (0x400 1kB) erased
        #112: 0x0001c000 (0x400 1kB) erased
        #113: 0x0001c400 (0x400 1kB) erased
        #114: 0x0001c800 (0x400 1kB) erased
        #115: 0x0001cc00 (0x400 1kB) erased
        #116: 0x0001d000 (0x400 1kB) erased
        #117: 0x0001d400 (0x400 1kB) erased
        #118: 0x0001d800 (0x400 1kB) erased
        #119: 0x0001dc00 (0x400 1kB) erased
        #120: 0x0001e000 (0x400 1kB) erased
        #121: 0x0001e400 (0x400 1kB) erased
        #122: 0x0001e800 (0x400 1kB) erased
        #123: 0x0001ec00 (0x400 1kB) erased
        #124: 0x0001f000 (0x400 1kB) erased
        #125: 0x0001f400 (0x400 1kB) erased
        #126: 0x0001f800 (0x400 1kB) erased
        #127: 0x0001fc00 (0x400 1kB) erased
        #128: 0x00020000 (0x400 1kB) erased
        #129: 0x00020400 (0x400 1kB) erased
        #130: 0x00020800 (0x400 1kB) erased
        #131: 0x00020c00 (0x400 1kB) erased
        #132: 0x00021000 (0x400 1kB) erased
        #133: 0x00021400 (0x400 1kB) erased
        #134: 0x00021800 (0x400 1kB) erased
        #135: 0x00021c00 (0x400 1kB) erased
        #136: 0x00022000 (0x400 1kB) erased
        #137: 0x00022400 (0x400 1kB) erased
        #138: 0x00022800 (0x400 1kB) erased
        #139: 0x00022c00 (0x400 1kB) erased
        #140: 0x00023000 (0x400 1kB) erased
        #141: 0x00023400 (0x400 1kB) erased
        #142: 0x00023800 (0x400 1kB) erased
        #143: 0x00023c00 (0x400 1kB) erased
        #144: 0x00024000 (0x400 1kB) erased
        #145: 0x00024400 (0x400 1kB) erased
        #146: 0x00024800 (0x400 1kB) erased
        #147: 0x00024c00 (0x400 1kB) erased
        #148: 0x00025000 (0x400 1kB) erased
        #149: 0x00025400 (0x400 1kB) erased
        #150: 0x00025800 (0x400 1kB) erased
        #151: 0x00025c00 (0x400 1kB) erased
        #152: 0x00026000 (0x400 1kB) erased
        #153: 0x00026400 (0x400 1kB) erased
        #154: 0x00026800 (0x400 1kB) erased
        #155: 0x00026c00 (0x400 1kB) erased
        #156: 0x00027000 (0x400 1kB) erased
        #157: 0x00027400 (0x400 1kB) erased
        #158: 0x00027800 (0x400 1kB) erased
        #159: 0x00027c00 (0x400 1kB) erased
        #160: 0x00028000 (0x400 1kB) erased
        #161: 0x00028400 (0x400 1kB) erased
        #162: 0x00028800 (0x400 1kB) erased
        #163: 0x00028c00 (0x400 1kB) erased
        #164: 0x00029000 (0x400 1kB) erased
        #165: 0x00029400 (0x400 1kB) erased
        #166: 0x00029800 (0x400 1kB) erased
        #167: 0x00029c00 (0x400 1kB) erased
        #168: 0x0002a000 (0x400 1kB) erased
        #169: 0x0002a400 (0x400 1kB) erased
        #170: 0x0002a800 (0x400 1kB) erased
        #171: 0x0002ac00 (0x400 1kB) erased
        #172: 0x0002b000 (0x400 1kB) erased
        #173: 0x0002b400 (0x400 1kB) erased
        #174: 0x0002b800 (0x400 1kB) erased
        #175: 0x0002bc00 (0x400 1kB) erased
        #176: 0x0002c000 (0x400 1kB) erased
        #177: 0x0002c400 (0x400 1kB) erased
        #178: 0x0002c800 (0x400 1kB) erased
        #179: 0x0002cc00 (0x400 1kB) erased
        #180: 0x0002d000 (0x400 1kB) erased
        #181: 0x0002d400 (0x400 1kB) erased
        #182: 0x0002d800 (0x400 1kB) erased
        #183: 0x0002dc00 (0x400 1kB) erased
        #184: 0x0002e000 (0x400 1kB) erased
        #185: 0x0002e400 (0x400 1kB) erased
        #186: 0x0002e800 (0x400 1kB) erased
        #187: 0x0002ec00 (0x400 1kB) erased
        #188: 0x0002f000 (0x400 1kB) erased
        #189: 0x0002f400 (0x400 1kB) erased
        #190: 0x0002f800 (0x400 1kB) erased
        #191: 0x0002fc00 (0x400 1kB) erased
        #192: 0x00030000 (0x400 1kB) erased
        #193: 0x00030400 (0x400 1kB) erased
        #194: 0x00030800 (0x400 1kB) erased
        #195: 0x00030c00 (0x400 1kB) erased
        #196: 0x00031000 (0x400 1kB) erased
        #197: 0x00031400 (0x400 1kB) erased
        #198: 0x00031800 (0x400 1kB) erased
        #199: 0x00031c00 (0x400 1kB) erased
        #200: 0x00032000 (0x400 1kB) erased
        #201: 0x00032400 (0x400 1kB) erased
        #202: 0x00032800 (0x400 1kB) erased
        #203: 0x00032c00 (0x400 1kB) erased
        #204: 0x00033000 (0x400 1kB) erased
        #205: 0x00033400 (0x400 1kB) erased
        #206: 0x00033800 (0x400 1kB) erased
        #207: 0x00033c00 (0x400 1kB) erased
        #208: 0x00034000 (0x400 1kB) erased
        #209: 0x00034400 (0x400 1kB) erased
        #210: 0x00034800 (0x400 1kB) erased
        #211: 0x00034c00 (0x400 1kB) erased
        #212: 0x00035000 (0x400 1kB) erased
        #213: 0x00035400 (0x400 1kB) erased
        #214: 0x00035800 (0x400 1kB) erased
        #215: 0x00035c00 (0x400 1kB) erased
        #216: 0x00036000 (0x400 1kB) erased
        #217: 0x00036400 (0x400 1kB) erased
        #218: 0x00036800 (0x400 1kB) erased
        #219: 0x00036c00 (0x400 1kB) erased
        #220: 0x00037000 (0x400 1kB) erased
        #221: 0x00037400 (0x400 1kB) erased
        #222: 0x00037800 (0x400 1kB) erased
        #223: 0x00037c00 (0x400 1kB) erased
        #224: 0x00038000 (0x400 1kB) erased
        #225: 0x00038400 (0x400 1kB) erased
        #226: 0x00038800 (0x400 1kB) erased
        #227: 0x00038c00 (0x400 1kB) erased
        #228: 0x00039000 (0x400 1kB) erased
        #229: 0x00039400 (0x400 1kB) erased
        #230: 0x00039800 (0x400 1kB) erased
        #231: 0x00039c00 (0x400 1kB) erased
        #232: 0x0003a000 (0x400 1kB) erased
        #233: 0x0003a400 (0x400 1kB) erased
        #234: 0x0003a800 (0x400 1kB) erased
        #235: 0x0003ac00 (0x400 1kB) erased
        #236: 0x0003b000 (0x400 1kB) erased
        #237: 0x0003b400 (0x400 1kB) erased
        #238: 0x0003b800 (0x400 1kB) erased
        #239: 0x0003bc00 (0x400 1kB) erased
        #240: 0x0003c000 (0x400 1kB) erased
        #241: 0x0003c400 (0x400 1kB) erased
        #242: 0x0003c800 (0x400 1kB) erased
        #243: 0x0003cc00 (0x400 1kB) erased
        #244: 0x0003d000 (0x400 1kB) erased
        #245: 0x0003d400 (0x400 1kB) erased
        #246: 0x0003d800 (0x400 1kB) erased
        #247: 0x0003dc00 (0x400 1kB) erased
        #248: 0x0003e000 (0x400 1kB) erased
        #249: 0x0003e400 (0x400 1kB) erased
        #250: 0x0003e800 (0x400 1kB) erased
        #251: 0x0003ec00 (0x400 1kB) erased
        #252: 0x0003f000 (0x400 1kB) erased
        #253: 0x0003f400 (0x400 1kB) erased
        #254: 0x0003f800 (0x400 1kB) erased
        #255: 0x0003fc00 (0x400 1kB) erased

可以看到0x6800是一个比较可疑的地方,这个地址之前的flash都没有被清空,而且还提示了出错信息.
为了对比,就直接读取了flash的前4个字:

(gdb) monitor mdw 0 4
0x00000000: 20000800 01000c4d 01000cc5 01000d13
果然不出所料,0x00000001地址的字节果然是0x08,和刚刚的出错信息"Verify operation failed address 0x00000001. Was 0x08 instead of 0x80"一致.
继续向后看,竟然发现中断地址的基址为0x01000000,这是什么地方呢?原来这是LM3S9B95的ROM区,flash区竟然被映射到这里来了,由于以前一直使用LM3S8962的板子,上面没有ROM,所以没有碰到这个问题.碰到问题怎么办,最权威的就是数据手册了,在LM3S9B95数据手册的第六章,内部存储器,终于找到了ROM控制的寄存器RMCTL,地址为0x400FE0F0,只有一个有效bit,当此位为1时,MCU的ROM区就给映射到了0x0,为0,映射到0x0的将是flash区.

查看一下这个寄存器:
(gdb) monitor mdw 0x400FE0F0 1
0x400fe0f0: 00000001
果然问题在这.也就是说,在下载前只要将此bit置0,那么就能正常进行flash下载了.
在.gdbinit文件里,修改以前的flash下载函数为:
define flash
monitor mww 0x400fe0f0 1 1
monitor halt
monitor mww 0x400fe0f0 1 1
monitor stellaris mass_erase 0
#monitor flash erase_address 0 262144
monitor soft_reset_halt
monitor mww 0x400fe0f0 1 1
monitor flash write_image main.axf
monitor mww 0x400fe0f0 1 1
monitor verify_image main.axf
monitor reset
x/4 0
end

由于下载flash需要几个步骤,停止MCU,复位,擦除,下载.所以这个函数里有4个地方添加了monitor mww 0x400fe0f0 1 1,意思是向0x400fe0f0这个寄存器里写1,有些人可能有疑惑了,不是说让这个寄存器置0才有用吗?
本来我写的是monitor mww 0x400fe0f0 0 1,即向这个寄存器里写1,但是写完后发现没有改变,再仔细读数据手册,才发现"This bit is cleared by writing a 1 to this bit position".
修改完后,下载测试,完全正常!问题解决.
数据手册是解决问题的一手资料,出现问题后,大家一般都下意识的到论坛上发问,当然这样很好,能够省去好多时间,加快开发的进度,但是如果是新问题的话,还是得自己一步一步解决,这个时候就应该耐心的查看数据手册了.想起当年花了50块钱将Atmega128的数据手册完完整整的打印了一份,看着这么多页的LM3S系列单片机数据手册,只能作罢.

回复评论 (3)

支持楼主!
点赞  2011-4-15 11:00
有的寄存器的操作是写1清0的  datasheet中都有说明!
点赞  2011-4-16 01:08
好帖!!!
点赞  2011-4-17 09:06
电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 京公网安备 11010802033920号
    写回复