startup: removed capture_catch
[openocd.git] / tcl / target / davinci.cfg
1 #
2 # Utility code for DaVinci-family chips
3 #
4
5 # davinci_pinmux: assigns PINMUX$reg <== $value
6 proc davinci_pinmux {soc reg value} {
7 mww [expr [dict get $soc sysbase] + 4 * $reg] $value
8 }
9
10 # mrw: "memory read word", returns value of $reg
11 proc mrw {reg} {
12 set value ""
13 mem2array value 32 $reg 1
14 return $value(0)
15 }
16
17 # mmw: "memory modify word", updates value of $reg
18 # $reg <== ((value & ~$clearbits) | $setbits)
19 proc mmw {reg setbits clearbits} {
20 set old [mrw $reg]
21 set new [expr ($old & ~$clearbits) | $setbits]
22 mww $reg $new
23 }
24
25 #
26 # pll_setup: initialize PLL
27 # - pll_addr ... physical addr of controller
28 # - mult ... pll multiplier
29 # - config ... dict mapping { prediv, postdiv, div[1-9] } to dividers
30 #
31 # For PLLs that don't have a given register (e.g. plldiv8), or where a
32 # given divider is non-programmable, caller provides *NO* config mapping.
33 #
34
35 # PLL version 0x02: tested on dm355
36 # REVISIT: On dm6446/dm357 the PLLRST polarity is different.
37 proc pll_v02_setup {pll_addr mult config} {
38 set pll_ctrl_addr [expr $pll_addr + 0x100]
39 set pll_ctrl [mrw $pll_ctrl_addr]
40
41 # 1 - clear CLKMODE (bit 8) iff using on-chip oscillator
42 # NOTE: this assumes we should clear that bit
43 set pll_ctrl [expr $pll_ctrl & ~0x0100]
44 mww $pll_ctrl_addr $pll_ctrl
45
46 # 2 - clear PLLENSRC (bit 5)
47 set pll_ctrl [expr $pll_ctrl & ~0x0020]
48 mww $pll_ctrl_addr $pll_ctrl
49
50 # 3 - clear PLLEN (bit 0) ... enter bypass mode
51 set pll_ctrl [expr $pll_ctrl & ~0x0001]
52 mww $pll_ctrl_addr $pll_ctrl
53
54 # 4 - wait at least 4 refclk cycles
55 sleep 1
56
57 # 5 - set PLLRST (bit 3)
58 set pll_ctrl [expr $pll_ctrl | 0x0008]
59 mww $pll_ctrl_addr $pll_ctrl
60
61 # 6 - set PLLDIS (bit 4)
62 set pll_ctrl [expr $pll_ctrl | 0x0010]
63 mww $pll_ctrl_addr $pll_ctrl
64
65 # 7 - clear PLLPWRDN (bit 1)
66 set pll_ctrl [expr $pll_ctrl & ~0x0002]
67 mww $pll_ctrl_addr $pll_ctrl
68
69 # 8 - clear PLLDIS (bit 4)
70 set pll_ctrl [expr $pll_ctrl & ~0x0010]
71 mww $pll_ctrl_addr $pll_ctrl
72
73 # 9 - optional: write prediv, postdiv, and pllm
74 # NOTE: for dm355 PLL1, postdiv is controlled via MISC register
75 mww [expr $pll_addr + 0x0110] [expr ($mult - 1) & 0xff]
76 if { [dict exists $config prediv] } {
77 set div [dict get $config prediv]
78 set div [expr 0x8000 | ($div - 1)]
79 mww [expr $pll_addr + 0x0114] $div
80 }
81 if { [dict exists $config postdiv] } {
82 set div [dict get $config postdiv]
83 set div [expr 0x8000 | ($div - 1)]
84 mww [expr $pll_addr + 0x0128] $div
85 }
86
87 # 10 - optional: set plldiv1, plldiv2, ...
88 # NOTE: this assumes some registers have their just-reset values:
89 # - PLLSTAT.GOSTAT is clear when we enter
90 # - ALNCTL has everything set
91 set go 0
92 if { [dict exists $config div1] } {
93 set div [dict get $config div1]
94 set div [expr 0x8000 | ($div - 1)]
95 mww [expr $pll_addr + 0x0118] $div
96 set go 1
97 }
98 if { [dict exists $config div2] } {
99 set div [dict get $config div2]
100 set div [expr 0x8000 | ($div - 1)]
101 mww [expr $pll_addr + 0x011c] $div
102 set go 1
103 }
104 if { [dict exists $config div3] } {
105 set div [dict get $config div3]
106 set div [expr 0x8000 | ($div - 1)]
107 mww [expr $pll_addr + 0x0120] $div
108 set go 1
109 }
110 if { [dict exists $config div4] } {
111 set div [dict get $config div4]
112 set div [expr 0x8000 | ($div - 1)]
113 mww [expr $pll_addr + 0x0160] $div
114 set go 1
115 }
116 if { [dict exists $config div5] } {
117 set div [dict get $config div5]
118 set div [expr 0x8000 | ($div - 1)]
119 mww [expr $pll_addr + 0x0164] $div
120 set go 1
121 }
122 if {$go != 0} {
123 # write pllcmd.GO; poll pllstat.GO
124 mww [expr $pll_addr + 0x0138] 0x01
125 set pllstat [expr $pll_addr + 0x013c]
126 while {[expr [mrw $pllstat] & 0x01] != 0} { sleep 1 }
127 }
128 mww [expr $pll_addr + 0x0138] 0x00
129
130 # 11 - wait at least 5 usec for reset to finish
131 # (assume covered by overheads including JTAG messaging)
132
133 # 12 - clear PLLRST (bit 3)
134 set pll_ctrl [expr $pll_ctrl & ~0x0008]
135 mww $pll_ctrl_addr $pll_ctrl
136
137 # 13 - wait at least 8000 refclk cycles for PLL to lock
138 # if we assume 24 MHz (slowest osc), that's 1/3 msec
139 sleep 3
140
141 # 14 - set PLLEN (bit 0) ... leave bypass mode
142 set pll_ctrl [expr $pll_ctrl | 0x0001]
143 mww $pll_ctrl_addr $pll_ctrl
144 }
145
146 # PLL version 0x03: tested on dm365
147 proc pll_v03_setup {pll_addr mult config} {
148 set pll_ctrl_addr [expr $pll_addr + 0x100]
149 set pll_secctrl_addr [expr $pll_addr + 0x108]
150 set pll_ctrl [mrw $pll_ctrl_addr]
151
152 # 1 - power up the PLL
153 set pll_ctrl [expr $pll_ctrl & ~0x0002]
154 mww $pll_ctrl_addr $pll_ctrl
155
156 # 2 - clear PLLENSRC (bit 5)
157 set pll_ctrl [expr $pll_ctrl & ~0x0020]
158 mww $pll_ctrl_addr $pll_ctrl
159
160 # 2 - clear PLLEN (bit 0) ... enter bypass mode
161 set pll_ctrl [expr $pll_ctrl & ~0x0001]
162 mww $pll_ctrl_addr $pll_ctrl
163
164 # 3 - wait at least 4 refclk cycles
165 sleep 1
166
167 # 4 - set PLLRST (bit 3)
168 set pll_ctrl [expr $pll_ctrl | 0x0008]
169 mww $pll_ctrl_addr $pll_ctrl
170
171 # 5 - wait at least 5 usec
172 sleep 1
173
174 # 6 - clear PLLRST (bit 3)
175 set pll_ctrl [expr $pll_ctrl & ~0x0008]
176 mww $pll_ctrl_addr $pll_ctrl
177
178 # 9 - optional: write prediv, postdiv, and pllm
179 mww [expr $pll_addr + 0x0110] [expr ($mult / 2) & 0x1ff]
180 if { [dict exists $config prediv] } {
181 set div [dict get $config prediv]
182 set div [expr 0x8000 | ($div - 1)]
183 mww [expr $pll_addr + 0x0114] $div
184 }
185 if { [dict exists $config postdiv] } {
186 set div [dict get $config postdiv]
187 set div [expr 0x8000 | ($div - 1)]
188 mww [expr $pll_addr + 0x0128] $div
189 }
190
191 # 10 - write start sequence to PLLSECCTL
192 mww $pll_secctrl_addr 0x00470000
193 mww $pll_secctrl_addr 0x00460000
194 mww $pll_secctrl_addr 0x00400000
195 mww $pll_secctrl_addr 0x00410000
196
197 # 11 - optional: set plldiv1, plldiv2, ...
198 # NOTE: this assumes some registers have their just-reset values:
199 # - PLLSTAT.GOSTAT is clear when we enter
200 set aln 0
201 if { [dict exists $config div1] } {
202 set div [dict get $config div1]
203 set div [expr 0x8000 | ($div - 1)]
204 mww [expr $pll_addr + 0x0118] $div
205 set aln [expr $aln | 0x1]
206 } else {
207 mww [expr $pll_addr + 0x0118] 0
208 }
209 if { [dict exists $config div2] } {
210 set div [dict get $config div2]
211 set div [expr 0x8000 | ($div - 1)]
212 mww [expr $pll_addr + 0x011c] $div
213 set aln [expr $aln | 0x2]
214 } else {
215 mww [expr $pll_addr + 0x011c] 0
216 }
217 if { [dict exists $config div3] } {
218 set div [dict get $config div3]
219 set div [expr 0x8000 | ($div - 1)]
220 mww [expr $pll_addr + 0x0120] $div
221 set aln [expr $aln | 0x4]
222 } else {
223 mww [expr $pll_addr + 0x0120] 0
224 }
225 if { [dict exists $config oscdiv] } {
226 set div [dict get $config oscdiv]
227 set div [expr 0x8000 | ($div - 1)]
228 mww [expr $pll_addr + 0x0124] $div
229 } else {
230 mww [expr $pll_addr + 0x0124] 0
231 }
232 if { [dict exists $config div4] } {
233 set div [dict get $config div4]
234 set div [expr 0x8000 | ($div - 1)]
235 mww [expr $pll_addr + 0x0160] $div
236 set aln [expr $aln | 0x8]
237 } else {
238 mww [expr $pll_addr + 0x0160] 0
239 }
240 if { [dict exists $config div5] } {
241 set div [dict get $config div5]
242 set div [expr 0x8000 | ($div - 1)]
243 mww [expr $pll_addr + 0x0164] $div
244 set aln [expr $aln | 0x10]
245 } else {
246 mww [expr $pll_addr + 0x0164] 0
247 }
248 if { [dict exists $config div6] } {
249 set div [dict get $config div6]
250 set div [expr 0x8000 | ($div - 1)]
251 mww [expr $pll_addr + 0x0168] $div
252 set aln [expr $aln | 0x20]
253 } else {
254 mww [expr $pll_addr + 0x0168] 0
255 }
256 if { [dict exists $config div7] } {
257 set div [dict get $config div7]
258 set div [expr 0x8000 | ($div - 1)]
259 mww [expr $pll_addr + 0x016c] $div
260 set aln [expr $aln | 0x40]
261 } else {
262 mww [expr $pll_addr + 0x016c] 0
263 }
264 if { [dict exists $config div8] } {
265 set div [dict get $config div8]
266 set div [expr 0x8000 | ($div - 1)]
267 mww [expr $pll_addr + 0x0170] $div
268 set aln [expr $aln | 0x80]
269 } else {
270 mww [expr $pll_addr + 0x0170] 0
271 }
272 if { [dict exists $config div9] } {
273 set div [dict get $config div9]
274 set div [expr 0x8000 | ($div - 1)]
275 mww [expr $pll_addr + 0x0174] $div
276 set aln [expr $aln | 0x100]
277 } else {
278 mww [expr $pll_addr + 0x0174] 0
279 }
280 if {$aln != 0} {
281 # clear pllcmd.GO
282 mww [expr $pll_addr + 0x0138] 0x00
283 # write alingment flags
284 mww [expr $pll_addr + 0x0140] $aln
285 # write pllcmd.GO; poll pllstat.GO
286 mww [expr $pll_addr + 0x0138] 0x01
287 set pllstat [expr $pll_addr + 0x013c]
288 while {[expr [mrw $pllstat] & 0x01] != 0} { sleep 1 }
289 }
290 mww [expr $pll_addr + 0x0138] 0x00
291 set addr [dict get $config ctladdr]
292 while {[expr [mrw $addr] & 0x0e000000] != 0x0e000000} { sleep 1 }
293
294 # 12 - set PLLEN (bit 0) ... leave bypass mode
295 set pll_ctrl [expr $pll_ctrl | 0x0001]
296 mww $pll_ctrl_addr $pll_ctrl
297 }
298
299 # NOTE: dm6446 requires EMURSTIE set in MDCTL before certain
300 # modules can be enabled.
301
302 # prepare a non-DSP module to be enabled; finish with psc_go
303 proc psc_enable {module} {
304 set psc_addr 0x01c41000
305 # write MDCTL
306 mmw [expr $psc_addr + 0x0a00 + (4 * $module)] 0x03 0x1f
307 }
308
309 # prepare a non-DSP module to be reset; finish with psc_go
310 proc psc_reset {module} {
311 set psc_addr 0x01c41000
312 # write MDCTL
313 mmw [expr $psc_addr + 0x0a00 + (4 * $module)] 0x01 0x1f
314 }
315
316 # execute non-DSP PSC transition(s) set up by psc_enable, psc_reset, etc
317 proc psc_go {} {
318 set psc_addr 0x01c41000
319 set ptstat_addr [expr $psc_addr + 0x0128]
320
321 # just in case PTSTAT.go isn't clear
322 while { [expr [mrw $ptstat_addr] & 0x01] != 0 } { sleep 1 }
323
324 # write PTCMD.go ... ignoring any DSP power domain
325 mww [expr $psc_addr + 0x0120] 1
326
327 # wait for PTSTAT.go to clear (again ignoring DSP power domain)
328 while { [expr [mrw $ptstat_addr] & 0x01] != 0 } { sleep 1 }
329 }
330
331 #
332 # A reset using only SRST is a "Warm Reset", resetting everything in the
333 # chip except ARM emulation (and everything _outside_ the chip that hooks
334 # up to SRST). But many boards don't expose SRST via their JTAG connectors
335 # (it's not present on TI-14 headers).
336 #
337 # From the chip-only perspective, a "Max Reset" is a "Warm" reset ... except
338 # without any board-wide side effects, since it's triggered using JTAG using
339 # either (a) ARM watchdog timer, or (b) ICEpick.
340 #
341 proc davinci_wdog_reset {} {
342 set timer2_phys 0x01c21c00
343
344 # NOTE -- on entry
345 # - JTAG communication with the ARM *must* be working OK; this
346 # may imply using adaptive clocking or disabling WFI-in-idle
347 # - current target must be the DaVinci ARM
348 # - that ARM core must be halted
349 # - timer2 clock is still enabled (PSC 29 on most chips)
350
351 #
352 # Part I -- run regardless of being halted via JTAG
353 #
354 # NOTE: for now, we assume there's no DSP that could control the
355 # watchdog; or, equivalently, SUSPSRC.TMR2SRC says the watchdog
356 # suspend signal is controlled via ARM emulation suspend.
357 #
358
359 # EMUMGT_CLKSPEED: write FREE bit to run despite emulation halt
360 mww phys [expr $timer2_phys + 0x28] 0x00004000
361
362 #
363 # Part II -- in case watchdog hasn't been set up
364 #
365
366 # TCR: disable, force internal clock source
367 mww phys [expr $timer2_phys + 0x20] 0
368
369 # TGCR: reset, force to 64-bit wdog mode, un-reset ("initial" state)
370 mww phys [expr $timer2_phys + 0x24] 0
371 mww phys [expr $timer2_phys + 0x24] 0x110b
372
373 # clear counter (TIM12, TIM34) and period (PRD12, PRD34) registers
374 # so watchdog triggers ASAP
375 mww phys [expr $timer2_phys + 0x10] 0
376 mww phys [expr $timer2_phys + 0x14] 0
377 mww phys [expr $timer2_phys + 0x18] 0
378 mww phys [expr $timer2_phys + 0x1c] 0
379
380 # WDTCR: put into pre-active state, then active
381 mww phys [expr $timer2_phys + 0x28] 0xa5c64000
382 mww phys [expr $timer2_phys + 0x28] 0xda7e4000
383
384 #
385 # Part III -- it's ready to rumble
386 #
387
388 # WDTCR: write invalid WDKEY to trigger reset
389 mww phys [expr $timer2_phys + 0x28] 0x00004000
390 }

Linking to existing account procedure

If you already have an account and want to add another login method you MUST first sign in with your existing account and then change URL to read https://review.openocd.org/login/?link to get to this page again but this time it'll work for linking. Thank you.

SSH host keys fingerprints

1024 SHA256:YKx8b7u5ZWdcbp7/4AeXNaqElP49m6QrwfXaqQGJAOk gerrit-code-review@openocd.zylin.com (DSA)
384 SHA256:jHIbSQa4REvwCFG4cq5LBlBLxmxSqelQPem/EXIrxjk gerrit-code-review@openocd.org (ECDSA)
521 SHA256:UAOPYkU9Fjtcao0Ul/Rrlnj/OsQvt+pgdYSZ4jOYdgs gerrit-code-review@openocd.org (ECDSA)
256 SHA256:A13M5QlnozFOvTllybRZH6vm7iSt0XLxbA48yfc2yfY gerrit-code-review@openocd.org (ECDSA)
256 SHA256:spYMBqEYoAOtK7yZBrcwE8ZpYt6b68Cfh9yEVetvbXg gerrit-code-review@openocd.org (ED25519)
+--[ED25519 256]--+
|=..              |
|+o..   .         |
|*.o   . .        |
|+B . . .         |
|Bo. = o S        |
|Oo.+ + =         |
|oB=.* = . o      |
| =+=.+   + E     |
|. .=o   . o      |
+----[SHA256]-----+
2048 SHA256:0Onrb7/PHjpo6iVZ7xQX2riKN83FJ3KGU0TvI0TaFG4 gerrit-code-review@openocd.zylin.com (RSA)