Serial Wire Debugging the STM32 via the Bus Pirate

2 October 2010

So 10 days ago I saw a post on Dangerous Prototypes mentioning the new STM32 Discovery board. Needless to say, I had impulse-bought a couple from Digi-Key within minutes. Unfortunately, I didn’t bother doing much research at that point, so I was unaware that the ST-Link has no Linux support until they arrived and I went to go program one. I could have just rebooted into Windows, but that seemed like admitting defeat, and I don’t really like IDEs anyway. Serendipitously, I had been reading about the Serial Wire Debug protocol for the past couple of days, and it seemed like a pretty nice little protocol, so I wondered if perhaps I could get that working.

Step 1 - The Bus Pirate

Given that I own a Bus Pirate, it seemed like the natural tool for implementing a new protocol that I had just read about. I had never used it before or even indeed verified that it worked, but I’ll spare you a long recounting of how I spent several days fighting with it, and just note that a tedious firmware upgrade process is ESSENTIAL if you bought a Bus Pirate from Sparkfun. Once that was fixed, it was a breeze setting up some basic serial communications with the Bus Pirate using the binary raw-wire mode from a Python script, although as mentioned in a previous post, the timings are slightly off compared to what one might naively expect.

Step 2 - Debug Port Communications

So given the ability to send and receive bits and bytes via the Bus Pirate, Debug Port communications were relatively straightforward. It’s important to pay attention to the fact that register numbers and data are all sent LSB-first down the wire, but otherwise it’s a nice, simple protocol.

Step 3 - Access Port Communications

So next I turned to the Cortex-M3 AHB Access Port, which would allow me to start manipulating the chip proper. I’ll again spare you several days of agonizing debugging, and just point out that when you clear the xPWRUPREQ bits, the associated features will power down. In hindsight, that makes a lot of sense. The general operation of the AHB-AP is pretty simple. Set the Control/Status Word to auto-increment if you want that feature, write the desired address into the Transfer Address Register, and manipulate the contents of the Data Read/Write register to your heart’s desire. At this point I was able to scan over the chip’s memory and make a dump of its contents, so I went ahead and made a copy of the current program in flash, just to be safe. This turned out to be very useful indeed.

Step 4 - Processor State

I knew that programming the flash would probably be tricky and possibly require the core to be halted, so I took some time at this point to do some little helper functions for state manipulation. Halting, unhalting, and restarting the processor are all pretty easy, simply involving writing some magic numbers to magic memory locations.

Step 5 - Programming the Flash

This stumped me for a while until I found the STM32 Flash Programming manual. After that it took some fiddling, but ultimately worked out pretty nicely. The process involves writing a sequence of keys to an unlock register before the control register can be written, then using the control register to erase the whole memory (in theory I could do it page-by-page, but that seemed harder and wasn’t necessary). Then the programming process consists of setting the FLASH_CR_PRG bit to indicate that programming is incoming, setting the AHB-AP to do writes in 16-bit packed mode, and writing the program data to memory starting at 0x08000000.

Step 6 - Optimizing

When I started this step, the script took 11 seconds to program a 3k firmware to the chip. When I finished, it took 1.5 seconds, and a good portion of that is required to avoid overflowing the write buffer (at least I think that’s the reason it errors if I try to decrease the interval between successive words). Those reads are very costly, so the optimizing essentially was just finding clever ways to avoid reading data from the Bus Pirate whenever possible, and only doing it in big blocks when required.

Conclusion

And that was it, modulo some issues with .bin file endianness and me having some trouble getting a decent firmware to compile properly. The code for the programming script, along with some precompiled firmwares which blink the blue LED at different rates, can be grabbed off GitHub, although there is currently no error recovery whatsoever, and only the most basic error detection.

Serial Wire Debugging the STM32 via the Bus Pirate的更多相关文章

  1. Introduction to Cortex Serial Wire Debugging

    Serial Wire Debug (SWD) provides a debug port for severely pin limited packages, often the case for ...

  2. Serial Wire Viewer (SWV)

    Being able to display values for counters, sensors and other debugging information is an important p ...

  3. Programming Internal Flash Over the Serial Wire Debug <SWD> Interface -- EFM32

    1 Debug Interface Overview 1.1 Serial Wire Debug Serial Wire Debug (SWD) is a two-wire protocol for ...

  4. Implementation of Serial Wire JTAG flash programming in ARM Cortex M3 Processors

    Implementation of Serial Wire JTAG flash programming in ARM Cortex M3 Processors The goal of the pro ...

  5. Serial Wire Debug (SWD) Interface -- PSoc5

    PSoC 5 supports programming through the serial wire debug (SWD) interface. There are two signals in ...

  6. SW-DP (Serial Wire Debug Port) Analyzer plugin for the Saleae Logic

    SW-DP (Serial Wire Debug Port) Analyzer plugin for the Saleae Logic The SW-DP protocol is described ...

  7. 各种版本的ST-LINK仿真器

    1.ST官方正式出版了两种仿真器:ST-LINK.ST-LINK/V2,其他型号(ST-LINK II,ST-LINK III,…)要么是国内公司生产,要么是开发板自带的:2.在ST官网ST-LINK ...

  8. KL46 custom board SWD reset is never asserted - SWS Waveform

    KL46 custom board SWD reset is never asserted Hi everybody, I'm trying to program a custom board bas ...

  9. windows下STM32开发环境的搭建

    一.概述 1.说明 笔者已经写了一篇Linux下STM32开发环境的搭建 ,这两篇文章的最区别在于开发环境所处的系统平台不一样,而其实这个区别对于开发环境的搭建其实影响不大,制作局部上的操作上发生了改 ...

随机推荐

  1. JavaScript 计时

    http://www.w3school.com.cn/js/js_timing.asp JavaScript 计时事件 通过使用 JavaScript,我们有能力作到在一个设定的时间间隔之后来执行代码 ...

  2. Burp-Suit之Interder

    登陆页面:http://localhost/pentest/brute/login.php 设置代理,使用Burp截断: 发送到Intruder进行爆破,这里我先说明一下Intruder页面 Inte ...

  3. spring事务详解(一)初探讨

    一.什么是事务 维基百科:数据库事务(简称:事务)是数据库管理系统执行过程中的一个逻辑单位,由一个有限的数据库操作序列构成.理解:事务(Transaction)是数据库区别于文件系统的重要特性之一.传 ...

  4. 分析占用了大量CPU处理时间的是Java进程中哪个线程

    下面是详细步骤: 1. 首先确定进程的 ID ,可以使用 jps -v 或者 top 命令直接查看 2. 查看该进程中哪个线程占用大量 CPU,执行 top -H -p [PID] 结果如下: 可以发 ...

  5. @PostConstruct和@PreConstruct

    详情参见:https://www.cnblogs.com/landiljy/p/5764515.html 1.@PostConstruct说明 被@PostConstruct修饰的方法会在服务器加载S ...

  6. Springboot 之 自定义配置文件及读取配置文件

    本文章来自[知识林] 读取核心配置文件 核心配置文件是指在resources根目录下的application.properties或application.yml配置文件,读取这两个配置文件的方法有两 ...

  7. Java多态概述

    多态 所谓多态,实际上就是一个对象的多种状态: 下面例子中,Tiger可以看做Tiger,也可以看做Animal Cat  可以看做Cat,也可以看做Animal Dog 可以看做Dog,也可以看做A ...

  8. HTTPS那-攻击实例与防御

    在<HTTPS-SSL证书>我描述了使用SSL证书时一些需要注意的安全问题,在这一篇文章里面我再演示一下针对HTTPS攻击的一些实例,通过这些实例能更安全的使用HTTPS.知己知彼百战不殆 ...

  9. GeoHash解析及java实现

    GeoHash解析请参考这里: http://www.open-open.com/lib/view/open1417940079964.html java实现GeoHash,代码已注释. import ...

  10. 【LOJ】#2567. 「APIO2016」划艇

    题解 显然有个很暴力的dp,\(dp[i][j]\)表示选到第\(i\)个数,末尾的数是\(j\)的方案数 但是第二维就开不下了,怎么办呢 考虑离散化整个区间,我们记录\(dp[i][j][k]\)表 ...