Update/correct copyright notices.
[deliverable/binutils-gdb.git] / gdb / w89k-rom.c
CommitLineData
c906108c
SS
1/* Remote target glue for the WinBond ROM monitor running on the "Cougar"
2 W89k eval board.
3
b6ba6518 4 Copyright 1995, 1998, 2000, 2001 Free Software Foundation, Inc.
c906108c 5
c5aa993b 6 This file is part of GDB.
c906108c 7
c5aa993b
JM
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
c906108c 12
c5aa993b
JM
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
c906108c 17
c5aa993b
JM
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 59 Temple Place - Suite 330,
21 Boston, MA 02111-1307, USA. */
c906108c
SS
22
23#include "defs.h"
24#include "gdbcore.h"
25#include "target.h"
26#include "monitor.h"
27#include "serial.h"
28#include "xmodem.h"
4e052eda 29#include "regcache.h"
c906108c
SS
30
31
a14ed312 32static void w89k_open (char *args, int from_tty);
c906108c
SS
33
34/*
35 * this array of registers need to match the indexes used by GDB. The
36 * whole reason this exists is cause the various ROM monitors use
37 * different strings than GDB does, and doesn't support all the
38 * registers either. So, typing "info reg sp" becomes a "r30".
39 */
40
41static char *w89k_regnames[NUM_REGS] =
42{
43 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
44 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
45 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
46 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31",
47 "SAR", "PC", NULL, NULL, NULL, "EIEM", "IIR", "IVA",
48 "IOR", "IPSW", NULL, NULL, NULL, NULL, NULL,
49 NULL, NULL, NULL, NULL, NULL, NULL, NULL,
50 "CCR", NULL, NULL, "TR0", "TR1",
51};
52
53static void
fba45db2 54w89k_supply_register (char *regname, int regnamelen, char *val, int vallen)
c906108c
SS
55{
56 int numregs;
57 int regno;
58
59 numregs = 1;
60 regno = -1;
61
62 if (regnamelen == 2)
63 switch (regname[0])
64 {
65 case 'r':
66 numregs = 4;
67 switch (regname[1])
68 {
69 case '0':
70 regno = R0_REGNUM;
71 break;
72 case '4':
73 regno = R0_REGNUM + 4;
74 break;
75 case '8':
76 regno = R0_REGNUM + 8;
77 break;
78 }
79 break;
80 case 'P':
81 if (regname[1] == 'C')
82 regno = PC_REGNUM;
83 break;
84 }
85 else if (regnamelen == 3)
86 switch (regname[0])
87 {
88 case 'r':
89 numregs = 4;
90 if (regname[1] == '1' && regname[2] == '2')
91 regno = R0_REGNUM + 12;
92 else if (regname[1] == '1' && regname[2] == '6')
93 regno = R0_REGNUM + 16;
94 else if (regname[1] == '2' && regname[2] == '0')
95 regno = R0_REGNUM + 20;
96 else if (regname[1] == '2' && regname[2] == '4')
97 regno = R0_REGNUM + 24;
98 else if (regname[1] == '2' && regname[2] == '8')
99 regno = R0_REGNUM + 28;
100 break;
101 case 'R':
102 if (regname[1] == 'C' && regname[2] == 'R')
103 regno = RCR_REGNUM;
104 break;
105 case 'C':
106 if (regname[1] == 'C' && regname[2] == 'R')
107 regno = CCR_REGNUM;
108 break;
109 case 'S':
110 if (regname[1] == 'A' && regname[2] == 'R')
111 regno = SAR_REGNUM;
112 break;
113 case 'I':
114 if (regname[1] == 'I' && regname[2] == 'R')
115 regno = IIR_REGNUM;
116 else if (regname[1] == 'O' && regname[2] == 'R')
117 regno = IOR_REGNUM;
118 break;
119 case 'T':
120 numregs = 4;
121 if (regname[1] == 'R')
122 if (regname[2] == '0')
123 regno = TR0_REGNUM;
124 else if (regname[2] == '4')
125 regno = TR0_REGNUM + 4;
126 break;
127 }
128 else if (regnamelen == 4)
129 switch (regname[0])
130 {
131 case 'E':
132 if (regname[1] == 'I')
133 if (regname[2] == 'E' && regname[3] == 'M')
134 regno = EIEM_REGNUM;
135 break;
136 case 'I':
137 if (regname[1] == 'P' && regname[2] == 'S' && regname[3] == 'W')
138 regno = IPSW_REGNUM;
139 break;
140 }
141 else if (regnamelen == 5)
142 switch (regname[0])
143 {
144 case 'I':
145 if (regname[1] == 'A'
146 && regname[2] == 'O'
147 && regname[3] == 'Q'
148 && regname[4] == 'B')
149 regno = PCOQ_TAIL_REGNUM;
150 break;
151 }
152
153 if (regno >= 0)
154 while (numregs-- > 0)
155 val = monitor_supply_register (regno++, val);
156}
157
158static int hashmark = 1; /* flag set by "set hash" */
159
c5aa993b 160extern struct monitor_ops w89k_cmds; /* fwd decl */
c906108c
SS
161
162static void
fba45db2 163w89k_load (serial_t desc, char *file, int hashmark)
c906108c
SS
164{
165 bfd *abfd;
166 asection *s;
167 char *buffer;
168 int i;
169
170 buffer = alloca (XMODEM_PACKETSIZE);
171
172 abfd = bfd_openr (file, 0);
173 if (!abfd)
174 {
175 printf_filtered ("Unable to open file %s\n", file);
176 return;
177 }
178
179 if (bfd_check_format (abfd, bfd_object) == 0)
180 {
181 printf_filtered ("File is not an object file\n");
182 return;
183 }
c5aa993b 184
c906108c
SS
185 for (s = abfd->sections; s; s = s->next)
186 if (s->flags & SEC_LOAD)
187 {
188 bfd_size_type section_size;
189
190 printf_filtered ("%s\t: 0x%4x .. 0x%4x ", s->name, s->vma,
191 s->vma + s->_raw_size);
192 gdb_flush (gdb_stdout);
193
194 monitor_printf (w89k_cmds.load, s->vma);
195 if (w89k_cmds.loadresp)
196 monitor_expect (w89k_cmds.loadresp, NULL, 0);
197
198 xmodem_init_xfer (desc);
199
200 section_size = bfd_section_size (abfd, s);
201
202 for (i = 0; i < section_size; i += XMODEM_DATASIZE)
203 {
204 int numbytes;
205
206 numbytes = min (XMODEM_DATASIZE, section_size - i);
207
208 bfd_get_section_contents (abfd, s, buffer + XMODEM_DATAOFFSET, i,
209 numbytes);
210
211 xmodem_send_packet (desc, buffer, numbytes, hashmark);
212
213 if (hashmark)
214 {
215 putchar_unfiltered ('#');
216 gdb_flush (gdb_stdout);
217 }
218 } /* Per-packet (or S-record) loop */
219
220 xmodem_finish_xfer (desc);
221
222 monitor_expect_prompt (NULL, 0);
223
224 putchar_unfiltered ('\n');
225 } /* Loadable sections */
c5aa993b
JM
226
227 if (hashmark)
c906108c
SS
228 putchar_unfiltered ('\n');
229}
230
231/*
232 * Define the monitor command strings. Since these are passed directly
233 * through to a printf style function, we need can include formatting
234 * strings. We also need a CR or LF on the end.
235 */
236
237static struct target_ops w89k_ops;
238
c5aa993b
JM
239static char *w89k_inits[] =
240{"\n", NULL};
c906108c 241
c5aa993b 242static struct monitor_ops w89k_cmds;
c906108c 243static void
c5aa993b 244init_w89k_cmds (void)
c906108c 245{
c5aa993b
JM
246 w89k_cmds.flags = MO_GETMEM_NEEDS_RANGE | MO_FILL_USES_ADDR; /* flags */
247 w89k_cmds.init = w89k_inits; /* Init strings */
248 w89k_cmds.cont = "g\n"; /* continue command */
249 w89k_cmds.step = "t\n"; /* single step */
250 w89k_cmds.stop = "\003"; /* Interrupt char (^C) */
251 w89k_cmds.set_break = "bp %x\n"; /* set a breakpoint */
252 w89k_cmds.clr_break = "bc %x\n"; /* clear a breakpoint */
253 w89k_cmds.clr_all_break = "bc *\n"; /* clear all breakpoints */
254 w89k_cmds.fill = "f %x %x %x\n"; /* memory fill cmd */
255 w89k_cmds.setmem.cmdb = "eb %x %x\n"; /* setmem.cmdb (addr, value) */
256 w89k_cmds.setmem.cmdw = "eh %x %x\n"; /* setmem.cmdw (addr, value) */
257 w89k_cmds.setmem.cmdl = "ew %x %x\n"; /* setmem.cmdl (addr, value) */
258 w89k_cmds.setmem.cmdll = NULL; /* setmem.cmdll (addr, value) */
259 w89k_cmds.setmem.resp_delim = NULL; /* setreg.resp_delim */
260 w89k_cmds.setmem.term = NULL; /* setreg.term */
261 w89k_cmds.setmem.term_cmd = NULL; /* setreg.term_cmd */
262 w89k_cmds.getmem.cmdb = "db %x %x\n"; /* getmem.cmdb (startaddr, endaddr) */
263 w89k_cmds.getmem.cmdw = "dh %x %x\n"; /* getmem.cmdw (startaddr, endaddr) */
264 w89k_cmds.getmem.cmdl = "dw %x %x\n"; /* getmem.cmdl (startaddr, endaddr) */
265 w89k_cmds.getmem.cmdll = NULL; /* getmem.cmdll (startaddr, endaddr) */
266 w89k_cmds.getmem.resp_delim = " "; /* getmem.resp_delim */
267 w89k_cmds.getmem.term = NULL; /* getmem.term */
268 w89k_cmds.getmem.term_cmd = NULL; /* getmem.term_cmd */
269 w89k_cmds.setreg.cmd = "r %s %x\n"; /* setreg.cmd (name, value) */
270 w89k_cmds.setreg.resp_delim = NULL; /* setreg.resp_delim */
271 w89k_cmds.setreg.term = NULL; /* setreg.term */
272 w89k_cmds.setreg.term_cmd = NULL; /* setreg.term_cmd */
273 w89k_cmds.getreg.cmd = "r %s\n"; /* getreg.cmd (name) */
274 w89k_cmds.getreg.resp_delim = "\r"; /* getreg.resp_delim */
275 w89k_cmds.getreg.term = NULL; /* getreg.term */
276 w89k_cmds.getreg.term_cmd = NULL; /* getreg.term_cmd */
277 w89k_cmds.dump_registers = "r\n"; /* dump_registers */
278 w89k_cmds.register_pattern = "\\(\\w+\\)\\( +[0-9a-fA-F]+\\b\\)+";
279 w89k_cmds.supply_register = w89k_supply_register; /* supply_register */
280 w89k_cmds.load_routine = w89k_load; /* load routine */
281 w89k_cmds.load = "u %x\n"; /* download command */
282 w89k_cmds.loadresp = "\021"; /* load response (^Q) */
283 w89k_cmds.prompt = "ROM>"; /* monitor command prompt */
284 w89k_cmds.line_term = "\n"; /* end-of-line terminator */
285 w89k_cmds.cmd_end = NULL; /* optional command terminator */
286 w89k_cmds.target = &w89k_ops; /* target operations */
287 w89k_cmds.stopbits = SERIAL_1_STOPBITS; /* number of stop bits */
288 w89k_cmds.regnames = w89k_regnames; /* register names */
289 w89k_cmds.magic = MONITOR_OPS_MAGIC; /* magic */
290} /* init_w89k_cmds */
291
c906108c 292static void
fba45db2 293w89k_open (char *args, int from_tty)
c906108c
SS
294{
295 monitor_open (args, &w89k_cmds, from_tty);
296}
297
298void
fba45db2 299_initialize_w89k (void)
c906108c 300{
c5aa993b 301 init_w89k_cmds ();
c906108c
SS
302 init_monitor_ops (&w89k_ops);
303
304 w89k_ops.to_shortname = "w89k";
305 w89k_ops.to_longname = "WinBond's debug monitor for the W89k Eval board";
306 w89k_ops.to_doc = "Debug on a WinBond W89K eval board.\n\
307Specify the serial device it is connected to (e.g. /dev/ttya).";
308 w89k_ops.to_open = w89k_open;
309
310 add_target (&w89k_ops);
311}
This page took 0.117356 seconds and 4 git commands to generate.