李亚鹏的射雕英雄传:【转】纯linux下jlink调试

来源:百度文库 编辑:中财网 时间:2024/05/05 01:42:57

纯linux下jlink调试

上一篇文章说到在ads中如何裸奔代码(bin文件),很遗憾,如果用gcc编译的elf文件ads并不能很好支持,当然带调试信息的elf文件debug起来总是比较方便的;当然以下是各种方案:
1 linux gcc编译,windows ads或者iar调试;
2 linux gcc编译,windows keil或者realview调试;
3 windows 下ads或者keil或者iar编译调试;
4 windows 下用cygwin或者用GNUARM之类的编译,然后用gdb insight 配合gdb server调试。
5 虚拟机linux gcc编译,然后运行gdb通过串口tcp远程调试win主机的target,需要win端有一个gdbserver,如jlink gdbserver;
6 纯linux下 gcc编译,gdb+openocd+jlink或者wiggler调试,今天重点就是这个。

(1)(2)上一篇文章讲过了,(3)相信大多数人都现在用着,(4)也很多资料介绍。
(5)我之前实验过,vmware,insight启动后提示connection reset by peer。by the way:由于jlink gdbserver的端口(2331)无法更改,我的insight也神神秘秘的target selection对话框无法输入,默认端口是1000,真让人抓狂!这个问题很多人问,其实insight启动后会在当前用户主目录执行.gdbtkinit这个文件,里面保存了很多配置信息,大家可以进去看看,端口也是在里面更改的。


 

 

 

准备工作:
1)本地gcc编译器,一般linux自带的就可以。
2)交叉gcc编译器,现成的或者用crosstool自己编译一个,可以参照我前面的文章。
3)insight源码。
4)openocd源码。

安装insight跟openocd:
1)安装insight
# ./configure --prefix=/opt/crosstool/insight --target=arm-softfloat-linux --enable-sim
# make
# make install
2)安装
openocd(0.3.0)
# ./configure --prefix=/opt/crosstool/openocd --enable-parport--enable-jlink
# make
# make install

配置openocd:

1)好好看看官方的文档,openocd每一个版本之间的命令差异很大。
2)按照良好的编程习惯,openocd推荐你按照以下步骤配置openocd
配置
interface
配置
openocd
配置
board
配置
target
../openocd-0.3.0/share/openocd/scripts有很多样板脚本可以参考。

官方建议大家把共享的脚本写在一个cfg里面,差异化的按类别写,多个脚本可以用-f在openocd启动时候指定,也可以在一个cfg文件像c语言一样include另外一个cfg文件,我写成一个脚本方便调试,大家可别学我哦。
脚本放在当前程序调试文件夹,openocd启动时候自动搜索openocd.cfg文件执行脚本命令。
以下是我的openocd.cfg

#-------------------------------------------------------------------------
# Target configuration for the Samsung 44b0 system on chip
# Tested on a S3C44b0 Evaluation board
# Processor : ARM7tdmi
# Info: JTAG tap: s3c44b0.cpu tap/device found: 0x1f0f0f0f
#  (Manufacturer:
#-------------------------------------------------------------------------

if { [info exists CHIPNAME] } {
   set  _CHIPNAME $CHIPNAME
} else {
   set  _CHIPNAME s3c44b0
}

if { [info exists ENDIAN] } {
   set  _ENDIAN $ENDIAN
} else {
  # this defaults to a bigendian
   set  _ENDIAN little
}

if { [info exists CPUTAPID ] } {
   set _CPUTAPID $CPUTAPID
} else {
  # force an error till we get a good number
   set _CPUTAPID 0x1f0f0f0f
}

#jtag scan chain
jtag newtap $_CHIPNAME cpu -irlen 4 -ircapture 0x1 -irmask 0x0f -expected-id $_CPUTAPID

set _TARGETNAME [format "%s.cpu" $_CHIPNAME]
target create $_TARGETNAME arm7tdmi -endian $_ENDIAN -chain-position $_TARGETNAME -variant arm7tdmi
#$_TARGETNAME configure -work-area-virt 0 -work-area-phys 0x40000000  -work-area-size 0x4000 -work-area-backup 1

#-------------------------------------------------------------------------
#interface
#-------------------------------------------------------------------------
interface jlink

#-------------------------------------------------------------------------
#reset configuration
#-------------------------------------------------------------------------
jtag_nsrst_delay 200
jtag_ntrst_delay 200
reset_config trst_and_srst

#-------------------------------------------------------------------------
# JTAG ADAPTER SPECIFIC
# IMPORTANT! See README at top of this file.
#-------------------------------------------------------------------------

    jtag_khz 3000


#-------------------------------------------------------------------------
# GDB Setup
#-------------------------------------------------------------------------
    telnet_port 4444
    gdb_port 2331
    tcl_port 6666
    echo " "
    echo "-------------------------------------------"
    echo "--- login with - telnet localhost 4444  ---"
    echo "--- gdb_port 2331                       ---"
    echo "-------------------------------------------"
    echo " "  
    gdb_breakpoint_override soft
    gdb_memory_map disable

#------------------------------------------------
# ARM SPECIFIC
#------------------------------------------------


  #  arm7_9 dcc_downloads enable
  #  arm7_9 fast_memory_access enable

    arm7_9 dbgrq disable
 
#------------------------------------------------
# Processor Initialialization
# Note: Processor writes can only occur when
# the state is in SYSTEM. When you call init_44b0
#------------------------------------------------

proc init_44b0 { } {

    halt
    s3c44b0.cpu curstate
    arm7_9 write_xpsr 0xd3 0
#-----------------------------------------------------------------
#-----------------------------System configure----------------------
#-----------------------------------------------------------------
#SYSCFG;INTMSK;WTCON
#PLLCON,10MHZ OSC,66M OUT
#SBUSCON;BWSCON;BANKCON0;BANKCON1;BANKCON2;BANKCON3;BANKCON4;BANKCON5;BANKCON6;BANKCON7
#REFRESH;BANKSIZE;MRSRB6;MRSRB7

    mww phys 0x01C00000 0x0E      
    mww phys 0x01E0000C 0x07FFFFFF
    mww phys 0x01D30000 0x0       
    mww phys 0x01D80000 0x0003A031
    mww phys 0x01C40000 0x80001B1B 
    mww phys 0x01C80000 0x11110112    
    mww phys 0x01C80004 0x00000600      
    mww phys 0x01C80008 0x00000700     
    mww phys 0x01C8000C 0x00000700      
    mww phys 0x01C80010 0x00000700       
    mww phys 0x01C80014 0x00000700       
    mww phys 0x01C80018 0x00000700       
    mww phys 0x01C8001C 0x00018000      
    mww phys 0x01C80020 0x00018000      
    mww phys 0x01C80024 0x0086041A       
    mww phys 0x01C80028 0x00000016      
    mww phys 0x01C8002C 0x00000020       
    mww phys 0x01C80030 0x00000020       
  
#-----------------------------------------------------------------
#-----------------------------Port configure----------------------
#-----------------------------------------------------------------
#PCONA#;PDATA;PCONC;PUPC;PDATC;PDATD;PCOND;PUPD;PCONE;PDATE;PUPE;
#PCONF;PUPF;PDATF;PDATG;PCONG;PUPG;PDATB;PCONB


    mww phys 0x01D20000 0x000001FF
    mww phys 0x01D20004 0x00000000
    mww phys 0x01D20010 0xfff5ff55
    mww phys 0x01D20014 0x00000000
    mww phys 0x01D20018 0x00003000
    mww phys 0x01D2001C 0x0000AAAA
    mww phys 0x01D20020 0x00000055
    mww phys 0x01D20024 0x00000000
    mww phys 0x01D20028 0x0000556B
    mww phys 0x01D2002C 0x00000357
    mww phys 0x01D20030 0x00000006
    mww phys 0x01D20034 0x0022445A
    mww phys 0x01D20038 0x00000000
    mww phys 0x01D2003C 0x000001D3
    mww phys 0x01D20040 0x00000000
    mww phys 0x01D20044 0x000000FF
    mww phys 0x01D20048 0x00000000
    mww phys 0x01D20008 0x0000004F
    mww phys 0x01D2000C 0x0000004F
}

$_TARGETNAME configure -event gdb-attach init_44b0

init
#----------------------------------------------------------------------------
#----------------------------------- END ------------------------------------
#----------------------------------------------------------------------------

配置.gdbinit
GDB 在启动的时候会按一定的路径顺序(通常是先当前目录而后用户目录)寻找 .gdbinit 文件,一旦找到,就会自动执行里面的命令。这个功能允许用户把常用的一些命令放在这个文件里,这样就不用每次进入 gdb 后再去手动执行这些命令。事实上,.gdbinit 就是一个脚本,甚至可在里面把常用的若干 gdb命令序列定义成一个新命令,这样只要在 gdb 里面输入这个新命令就等于自动执行了被定义的那个命令序列。

以下是我的.gdbinit文件

#GDB 6.8 and higher set any memory area not in the memory map as inaccessible, this can be changed to the old behaviour by using the following gdb command.
set mem inaccessible-by-default off

#Previous versions of OpenOCD required the following gdb options to increase the packet size and speed up gdb communication.
#This is now handled in the qSupported PacketSize.
#
但是现在如果去掉,还是出现(openocd那边):Warning:acknowledgment received, but no packet pending
#Warning:negative reply, retrying
#Error: GDB missing ack(2) - assumed good
#Warning:negative reply, retrying
#之类的错误,gdb的console窗口也会出现错误。

set remote memory-write-packet-size 1024
set remote memory-write-packet-size fixed
set remote memory-read-packet-size 1024
set remote memory-read-packet-size fixed

target remote localhost:2331
monitor sleep 500
monitor poll
monitor soft_reset_halt

 

 

接下来现启动openocd服务,等待gdb或者insight来连接。
命令我就不写了
//______________________________________________//
force soft breakpoints
use of EmbeddedICE dbgrq instead of breakpoint for target halt disabled
Info : J-Link initialization started / target CPU reset initiated
Info : J-Link ARM V7 compiled Jun 30 2009 11:05:27
Info : JLink caps 0xb9ff7bbf
Info : JLink hw version 70000
Info : JLink max mem block 9152
Info : Vref = 3.222 TCK = 1 TDI = 0 TDO = 0 TMS = 0 SRST = 0 TRST = 0

Info : J-Link JTAG Interface ready
Info : clock speed 3000 kHz
Info : JTAG tap: s3c44b0.cpu tap/device found: 0x1f0f0f0f (mfg: 0x787, part: 0xf0f0, ver: 0x1)
Info : Embedded ICE version 1

注意:openocd执行时候需要读写jlink,普通用户可能没有这个权限,需要admin权限,而jlink不是usbfs设备,暂时没有弄给普通用户添加jlink的权限。普通用户执行openocd会出现如下错误:

force soft breakpoints
use of EmbeddedICE dbgrq instead of breakpoint for target halt disabled
Info : J-Link initialization started / target CPU reset initiated
Error: J-Link command 0xde failed (-1)
Error: J-Link command 0xdc failed (-1)
Error: J-Link command 0x01 failed (-1)
Error: J-Link command EMU_CMD_VERSION failed (-1)

然后启动insight:命令我就不写了呵呵


 

最后下载,然后就可以调试了,也可以在gdb控制台输入命令来调试。

可爱的hello world 出现了: