这月太忙了。
忙考试,忙社团,忙不过来。
刚刚又发现香港签注过期了,10天后就要去香港,6月2日考SAT。十天之内能不能办好就只能拼人品了。
我总是考虑事情不周全。
STM32的JTAG接口复用之后,CPU便不听JTAG使唤,其实这种问题很容易解决,只需按住reset键并连接JTAG,在OpenOCD执行soft_reset_halt同时松开reset键,这样CPU在JTAG复用之前就被halt住了。
同理,对于其他ARM Cortex MCU也适用。
为了防止JTAG被锁死,可以在JTAG复用之前添加一些检测程序,具体代码在Google能找到不少,这里略过。
之前我一直使用8位并行的方式驱动12864(ST7920主控),它的DB0-DB7、RS、RW、E这些端口占用11个GPIO,实为不爽。周六和ChiNvo聊到12864屏幕,得知了串行方式的显示效果(只占3个GPIO,效率没有下降),为了支持串行模式,我写了个12864屏幕驱动。
为什么不去网上找别人写的驱动?因为别人的代码风格实在难以忍受:一大堆乱套的define,密密麻麻的代码还不加空格,命名极不规范等等。
与别人的驱动还有一个不同点:由于受到Arduino和STM32固件库的影响,我写的是面向对象的(类似Arduino里的LiquidCrystal,不过是纯C),轻松驱动多个12864,而且支持三种传输模式(串行、8位并行、4位并行)。
至于这种代码的效率问题,交给编译器优化就好了。不能为了节省几个指令的时间而牺牲架构,如果效率那么重要,直接上纯汇编了。在微控制器上使用面向对象编程必然是趋势,也是Arduino和mbed这种prototyping platforms受欢迎的原因。
目前这个是针对AVR 8-bit微控制器写的,以后有时间稍微改一下,放到ARM Cortex-M3上运行。
欢迎到GitHub上关注这个项目,代码我会尽快push上去。
刚得知20号就要比赛,抓紧干活去。
博客挂掉之前,写过一次这个文章,现在再写一遍。
使用Xcode调试过程中,可能经常遇到SIGABRT而卡在main函数里,要解决这个问题,需要用到Xcode的Breakpoint navigator。
点击左下角的+,选择“Add Exception Breakpoint…”
点击Done。问题即解决。
计算机:MacBook Pro 15″ Mid-2010
微控制器:STM32F103ZET6
调试器:OpenJTAG(基于FT2232D)
操作系统:Mac OS X Lion 10.7.3
集成开发环境:Eclipse with CDT
调试工具:OpenOCD
工具链:YAGARTO for Mac OS X (arm-none-eabi)
OpenOCD是开源调试软件,支持各种常用的JTAG调试器,比如J-Link、FT2232。我的是基于FT2232的OpenJTAG,要使OpenOCD支持它,需要libFTDI库。先用MacPorts或Homebrew安装libFTDI:
$ sudo port install libftdi
$ brew install libftdi
然后到http://sourceforge.net/projects/openocd/files/openocd/下载OpenOCD,配置并编译:
$ ./configure --enable-maintainer-mode --enable-ft2232_libftdi $ make $ sudo make install
下载openocd.cfg,解压后放在调试用的目录,连接OpenJTAG到电脑,并给开发板上电,在openocd.cfg所在目录执行:
$ openocd
如果在终端看到如下信息,就表明连接成功:
Xinranmsns-MacBook-Pro:Debug xinranmsn$ openocd Open On-Chip Debugger 0.6.0-dev-00381-gbce7009 (2012-03-11-22:56) Licensed under GNU GPL v2 For bug reports, read http://openocd.sourceforge.net/doc/doxygen/bugs.html Info : only one transport option; autoselect 'jtag' 1000 kHz adapter_nsrst_delay: 100 jtag_ntrst_delay: 100 cortex_m3 reset_config sysresetreq Info : clock speed 1000 kHz Info : JTAG tap: stm32f1x.cpu tap/device found: 0x3ba00477 (mfg: 0x23b, part: 0xba00, ver: 0x3) Info : JTAG tap: stm32f1x.bs tap/device found: 0x06414041 (mfg: 0x020, part: 0x6414, ver: 0x0) Info : stm32f1x.cpu: hardware has 6 breakpoints, 4 watchpoints
打开一个新的终端窗口,执行:
$ nc localhost 4444
登录到了OpenOCD的telnet server
Xinranmsns-MacBook-Pro:~ xinranmsn$ nc localhost 4444 ????????Open On-Chip Debugger >
这时可以熟悉一下OpenOCD的基本命令了,比如targets、halt、reset和flash等等。
在http://www.yagarto.de/index.html下载YAGARTO GNU ARM Toolchain。新建目录/usr/local/arm/arm-none-eabi,把YAGARTO安装包拖动到这个目录安装。编辑~/.profile文件,添加一行
export PATH=$PATH:/usr/local/arm/arm-none-eabi/bin
保存文件,重新打开终端,输入arm,敲几下tab,如果能看到arm-none-eabi-的工具链,那么安装成功。但并不表明工具链已经配置好…… 请参阅我的这篇文章http://www.xinranmsn.com/?p=17,重新编译安装arm-none-eabi-gdb。
未完待续,可参考翁恺老师的文章http://blog.sina.com.cn/s/blog_591c85490100zwtu.html
OpenJTAG带一个JTAG接口和一个RS232串口,分别是由FT2232芯片的串口A和串口B控制的。如果想使用OpenJTAG的RS232串口,则需按以下方法配置。
在http://www.ftdichip.com/Drivers/VCP.htm下载串口驱动(Mac OS X 64-bit),安装。
安装之后,在/dev/中是看不到串口的,因为官方的驱动不包含OpenJTAG(PID和VID不同)。
连接OpenJTAG到电脑,打开System Information,在左侧栏找到USB,点击OpenJTAG,如图
把Product ID和Vendor ID换算成十进制,稍后要用到。
编辑/System/Library/Extensions/FTDIUSBSerialDriver.kext/Contents/Info.plist,查找Olimex关键字,把Olimex的整个dictionary替换换成如下内容:
<key>OpenJTAG B</key>
<dict>
<key>CFBundleIdentifier</key>
<string>com.FTDI.driver.FTDIUSBSerialDriver</string>
<key>IOClass</key>
<string>FTDIUSBSerialDriver</string>
<key>IOProviderClass</key>
<string>IOUSBInterface</string>
<key>bConfigurationValue</key>
<integer>1</integer>
<key>bInterfaceNumber</key>
<integer>1</integer>
<key>idProduct</key>
<integer>20760</integer>
<key>idVendor</key>
<integer>5207</integer>
</dict>
把十进制的Product ID和Vendor ID填入idProduct和idVendor对应的integer值,如果跟我的ID不一样,以你自己的为准。
保存文件。
在终端执行
$ sudo kextload /System/Library/Extensions/FTDIUSBSerialDriver.kext
加载后不会有任何提示。为了检查是否成功加载串口,执行
$ ls /dev | grep cu
如果出现了cu.usbserial-000013FDB就说明串口已成功加载。
去年在微博关注了以@新车间为主的各大创客空间,知道了Arduino这个东西,于是买了一个Arduino UNO玩玩。
这个东西上手很快,有封装完美的库,比之前纯单片机编程方便太多了,根本不用考虑各种特殊寄存器。常用器件,比如舵机、步进电机、LCD,都能拿来直接用,两三行代码就搞定。
暑假用Arduino做了个循线小车,是用旧四轮玩具车改装的。车上有两个电机,一个用来转弯,另一个用来前进,用L298N控制电机,极少量代码就实现了循线功能。但是这个小车也有很多弊端,Arduino UNO本身占空太大,还使用了大量的插线,组装比较繁琐。
做完这个小车之后,就没再用Arduino做过东西,而拿它来测试各种器件。因为它直接USB连接到电脑,几行代码搞定。如果用纯单片机搭建(比如ATmega16),需要在面包板上布置好最小系统和SPI下载线,必要时还得接上串口,再对照datasheet写一段程序,实在是麻烦。
对于电子初学者来说,Arduino是个非常好的平台。我比较推荐的是Arduino Nano,体积小,直接插到面包板或自己焊接的排孔上,在一些电子比赛中,这个最合适不过了。
用OpenOCD和GDB调试(arm-none-eabi)总是失败,GDB提示错误“Remote ‘g’ packet reply is too long”,很郁闷。查了一些资料,这是GDB本身的问题,需要修改代码后重新编译。
下载GDB 7.4源码,打开源码文件夹中的gdb/remote.c,找到process_g_packet函数,如图:
将下面这部分注释掉
在其下方加入
if (buf_len > 2 * rsa->sizeof_g_packet) {
rsa->sizeof_g_packet = buf_len;
for (i = 0; i < gdbarch_num_regs (gdbarch); i++) {
if (rsa->regs[i].pnum == -1)
continue;
if (rsa->regs[i].offset >= rsa->sizeof_g_packet)
rsa->regs[i].in_g_packet = 0;
else
rsa->regs[i].in_g_packet = 1;
}
}
修改后的如下图
随后就可以编译安装了(configure的prefix是我的工具链目录)
$ ./configure --prefix=/usr/local/arm/arm-none-eabi --target=arm-none-eabi $ make $ sudo make install
再次调试的时候可以发现问题已解决。