3 OpenOCD RPC example, covered by GNU GPLv3 or later
4 Copyright (C) 2014 Andreas Ortmann (ortmann@finf.uni-hannover.de)
12 target halted due to debug-request, current mode: Thread
13 xPSR: 0x01000000 pc: 0x00000188 msp: 0x10000fd8
15 variable @ 0x10000000: 0x01c9c380
17 variable @ 0x10000000: 0xdeadc0de
19 memory (before): ['0xdeadc0de', '0x00000011', '0xaaaaaaaa', '0x00000023',
20 '0x00000042', '0x0000ffff']
22 memory (after): ['0x00000001', '0x00000000', '0xaaaaaaaa', '0x00000023',
23 '0x00000042', '0x0000ffff']
30 return map(strToHex
, data
) if isinstance(data
, list) else int(data
, 16)
33 return "<None>" if data
is None else ("0x%08x" % data
)
35 def compareData(a
, b
):
36 for i
, j
, num
in zip(a
, b
, itertools
.count(0)):
38 print("difference at %d: %s != %s" % (num
, hexify(i
), hexify(j
)))
42 COMMAND_TOKEN
= '\x1a'
43 def __init__(self
, verbose
=False):
44 self
.verbose
= verbose
45 self
.tclRpcIp
= "127.0.0.1"
46 self
.tclRpcPort
= 6666
47 self
.bufferSize
= 4096
49 self
.sock
= socket
.socket(socket
.AF_INET
, socket
.SOCK_STREAM
)
55 def __exit__(self
, type, value
, traceback
):
59 self
.sock
.connect((self
.tclRpcIp
, self
.tclRpcPort
))
68 """Send a command string to TCL RPC. Return the result that was read."""
69 data
= (cmd
+ OpenOcd
.COMMAND_TOKEN
).encode("utf-8")
77 """Read from the stream until the token (\x1a) was received."""
80 chunk
= self
.sock
.recv(self
.bufferSize
)
82 if bytes(OpenOcd
.COMMAND_TOKEN
, encoding
="utf-8") in chunk
:
88 data
= data
.decode("utf-8").strip()
89 data
= data
[:-1] # strip trailing \x1a
93 def readVariable(self
, address
):
94 raw
= self
.send("mdw 0x%x" % address
).split(": ")
95 return None if (len(raw
) < 2) else strToHex(raw
[1])
97 def readMemory(self
, wordLen
, address
, n
):
98 self
.send("array unset output") # better to clear the array before
99 self
.send("mem2array output %d 0x%x %d" % (wordLen
, address
, n
))
101 output
= [*map(int, self
.send("return $output").split(" "))]
102 d
= dict([tuple(output
[i
:i
+ 2]) for i
in range(0, len(output
), 2)])
104 return [d
[k
] for k
in sorted(d
.keys())]
106 def writeVariable(self
, address
, value
):
107 assert value
is not None
108 self
.send("mww 0x%x 0x%x" % (address
, value
))
110 def writeMemory(self
, wordLen
, address
, n
, data
):
111 array
= " ".join(["%d 0x%x" % (a
, b
) for a
, b
in enumerate(data
)])
113 self
.send("array unset 1986ве1т") # better to clear the array before
114 self
.send("array set 1986ве1т { %s }" % array
)
115 self
.send("array2mem 1986ве1т 0x%x %s %d" % (wordLen
, address
, n
))
117 if __name__
== "__main__":
120 print(*args
, end
="\n\n")
122 with
OpenOcd() as ocd
:
125 show(ocd
.send("capture { echo \"echo says hi!\" }")[:-1])
126 show(ocd
.send("capture \"halt\"")[:-1])
128 # Read the first few words at the RAM region (put starting address of RAM
129 # region into 'addr')
132 value
= ocd
.readVariable(addr
)
133 show("variable @ %s: %s" % (hexify(addr
), hexify(value
)))
135 ocd
.writeVariable(addr
, 0xdeadc0de)
136 show("variable @ %s: %s" % (hexify(addr
), hexify(ocd
.readVariable(addr
))))
138 data
= [1, 0, 0xaaaaaaaa, 0x23, 0x42, 0xffff]
142 read
= ocd
.readMemory(wordlen
, addr
, n
)
143 show("memory (before):", list(map(hexify
, read
)))
145 ocd
.writeMemory(wordlen
, addr
, n
, data
)
147 read
= ocd
.readMemory(wordlen
, addr
, n
)
148 show("memory (after):", list(map(hexify
, read
)))
150 compareData(read
, data
)