]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blame - sim/cris/dv-rv.c
sim: formally assume unistd.h always exists (via gnulib)
[thirdparty/binutils-gdb.git] / sim / cris / dv-rv.c
CommitLineData
aad3b3cb
HPN
1/* The remote-virtual-component simulator framework
2 for GDB, the GNU Debugger.
3
213516ef 4 Copyright 2006-2023 Free Software Foundation, Inc.
aad3b3cb
HPN
5
6 This file is part of GDB.
7
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
4744ac1b 10 the Free Software Foundation; either version 3 of the License, or
aad3b3cb
HPN
11 (at your option) any later version.
12
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.
17
18 You should have received a copy of the GNU General Public License
4744ac1b 19 along with this program. If not, see <http://www.gnu.org/licenses/>. */
aad3b3cb 20
6df01ab8
MF
21/* This must come before any other includes. */
22#include "defs.h"
aad3b3cb
HPN
23
24#include "sim-main.h"
25#include "hw-main.h"
26
27#include "hw-tree.h"
28
29#include <ctype.h>
aad3b3cb 30#include <errno.h>
aad3b3cb 31#include <string.h>
aad3b3cb 32#include <unistd.h>
aad3b3cb 33#include <stdlib.h>
aad3b3cb
HPN
34#ifdef HAVE_SYS_TYPES_H
35#include <sys/types.h>
36#endif
37
aad3b3cb 38#include <sys/time.h>
aad3b3cb 39
aad3b3cb 40#include <sys/select.h>
aad3b3cb
HPN
41
42/* Not guarded in dv-sockser.c, so why here. */
43#include <netinet/in.h>
44#include <arpa/inet.h>
45#include <netdb.h>
46#include <sys/socket.h>
47
48
49/* DEVICE
50
51
52 rv - Remote Virtual component
53
54
55 DESCRIPTION
56
57
58 Socket connection to a remote simulator component, for example one
59 for testing a verilog construction. Protocol defined below.
60
61 There is a set of 32-bit I/O ports, with a mapping from local to
62 remote addresses. There is a set of interrupts expressed as a
63 bit-mask, with a mapping from remote to local. There is a set of
64 memory ranges (actual memory defined elsewhere), also with a
65 mapping from remote to local addresses, that is expected to be
66 accessible to the remote simulator in 32-byte chunks (simulating
67 DMA). There is a mapping from remote cycles (or an appropriate
68 elsewhere defined time-slice) to local cycles.
69
70 PROPERTIES
71
72 reg = <address> <size>
73 The address (within the parent bus) that this device is to
74 be located.
75
76 remote-reg = <remote-address>
77 The address of reg on the remote side. Defaults to 0.
78
79 mem = <address> <size>
80 Specify an address-range (within the parent bus) that the remote
81 device can access. The memory is assumed to be already defined.
82 If there's no memory defined but the remote side asks for a memory
83 access, the simulation is aborted.
84
85 remote-mem = <remote-address>
86 The address of mem on the remote side. Defaults to 0.
87
88 mbox = <address>
89 Address of the mailbox interface. Writes to this address with the
90 local address of a mailbox command, a complete packet with length
91 and command; (4 or 6)) invokes the mailbox interface. Reads are
92 invalid. Replies are written to the same address. Address space
93 from <address> up-to-and-including <address>+3 is allocated.
94
95 max-poll-ticks = <local-count>
96 Sets the maximum interval between polling the external component,
97 expressed in internal cycles. Defaults to 10000.
98
99 watchdog-interval = <seconds>
100 Sets the wallclock seconds between watchdog packets sent to the
101 remote side (may be larger if there's no rv activity in that time).
102 Defaults to 30. If set to 0, no watchdog packets are sent.
103
104 intnum = <local-int-0> <local-int-1> ... <local-int-31>
105 Defines a map from remote bit numbers to local values to be emitted
106 on the "int" port, with the external bit number as the ordinal - 1
107 of the local translation. E.g. 43 121 would mean map external
108 (1<<0) to internal 43 and external (1<<1) to internal 121. The
109 default is unity; no translation. If more than one bit is set in
110 the remote interrupt word, the intmultiple property can be used to
111 control the translation.
112
113 intmultiple = <intvalue>
114 When more than one bit is set in the remote interrupt word, you may
115 want to map this situation to a separate interrupt value. If this
116 property is non-zero, it is used as that value. If it is zero, the
117 local value for the "int" port is the bitwise-or of the translated
118 local values.
119
120 host = <hostid>
121 The hostname or address where the simulator to be used listens.
122 Defaults to "127.0.0.1"
123
124 port = <portnumber>
125 The hostname or address where the simulator to be used listens.
126 Defaults to 10000.
127
128 dummy = <value>
129 or
130 dummy = <filename>
131 Don't connect to a remote side; use initial dummy contents from
132 <filename> (which has to be at least as big as the <size> argument
133 of reg above) or filled with byte-value <value>. Mailboxes are not
134 supported (can be defined but can not be used) and remote-memory
135 accesses don't apply. The main purpose for this property is to
136 simplify use of configuration and simulated hardware that is
137 e.g. only trivially initialized but not actually used.
138
139
140 PORTS
141
142 int (output)
143 Driven as a result of a remote interrupt request. The value is a
144 32-bit bitset of active interrupts.
145
146
147 BUGS
148
149 All and none.
150
151
152 PROTOCOL
153
154 This is version 1.0 of this protocol, defining packet format and
155 actions in a supposedly upward-compatible manner where client and
156 servers of different versions are expected to interoperate; the
157 format and the definitions below are hopefully generic enough to
158 allow this.
159
160 Each connection has a server and a client (this code); the roles
161 are known beforehand. The client usually corresponds to a CPU and
162 memory system and the server corresponds to a memory-mapped
163 register hardware interface and/or a DMA controller. They
164 communicate using packets with specific commands, of which some
165 require replies from the other side; most are intiated by the
166 client with one exception. A reply uses the same format as the
167 command.
168
169 Packets are at least three bytes long, where the first two bytes
170 form a header, a 16-bit little-endian number that is the total
171 length of the packet including the header. There is also a
172 one-byte command. The payload is optional, depending on the
173 command.
174
175 [[16-bit-low-byte-of-length] [16-bit-high-byte-of-length]
176 [command/reply] [payload byte 0] [payload byte 1]
177 ... [payload byte (length-of-packet - 3)]]
178
179 Commands:
180
181 A client or server that reads an undocumented command may exit with
182 a hard error. Payload not defined or disallowed below is ignored.
183
184 It is expected that future client versions find out the version of
185 the server side by polling with base commands, assuming earlier
186 versions if a certain reply isn't seen, with newly defined payload
187 parts where earlier versions left it undefined. New commands and
188 formats are sent only to the other side after the client and server
189 has found out each others version. Not all servers support all
190 commands; the type of server and supported set of commands is
191 expected to be known beforehand.
192
193 RV_READ_CMD = 0
194 Initiated by the client, requires a reply from the server. The
195 payload from the client is at least 4 bytes, forming a 4-byte
196 little-endian address, the rest being undefined. The reply from
197 the server is at least 8 bytes, forming the same address data as in
198 the request and the second 4-byte data being the little-endian
199 contents.
200
201 RV_WRITE_CMD = 1
202 Initiated by the client, requires a reply from the server. Payload
203 from the client is at least 8 bytes, forming a 4-byte little-endian
204 word being the address, the rest being the little-endian contents
205 to write. The reply from the server is 8 bytes unless elsewhere
206 agreed otherwise, forming the same address and data as in the
207 request. The data sent back may have been altered to correspond to
208 defined parts but can safely be discarded.
209
210 RV_IRQ_CMD = 2
211 Initiated by the server, no reply. The payload is 4 bytes, forming
212 a little-endian word with bits numbers corresponding to currently
213 active interrupt sources; value (1<<N) indicating interrupt source
214 N being active.
215
216 RV_MEM_RD_CMD = 3
217 Initiated by the server, requires a reply. A client must know
218 beforehand when (in command sequence or constant) the server can
219 send this command and if so must then not send any commands of its
220 own (including watchdog commands); the server is allowed to assume
221 that incoming data is only replies to this command. The format is
222 8 bytes of data; 4 bytes of little-endian address followed by a
223 32-bit little endian word with the number of bytes to read. The
224 reply is the same address and number of bytes, followed by the data
225 that had been read.
226
227 RV_MEM_WR_CMD = 4
228 Initiated by the server, no reply. The format is the same as a
229 reply to RV_MEM_RD_CMD; a 32-bit little-endian address, followed by
230 the 32-bit little-endian number of bytes to write (redundant
231 information but must be consistent with the packet header).
232
233 RV_MBOX_HANDLE_CMD = 5
234 Initiated by the client, requires a reply. The payload is 4
235 undefined bytes followed by an binary blob, the size of the
236 blob given by the packet header. The reply is a 32-bit little
237 endian number at the same index as the undefined bytes. Actual
238 semantics are application-specific.
239
240 RV_MBOX_PUT_CMD = 6
241 Initiated by the client, requires a reply, with the reply using the
242 RV_MBOX_HANDLE_CMD reply format (i.e. *both* that command and
243 32-bit little-endian number). The payload is a 32-bit little
244 endian number followed by an undefined payload, at most 20 bytes
245 long. The reply is a 32-bit little endian number. Actual
246 semantics are application-specific.
247
248 RV_WATCHDOG_CMD = 7
249 Initiated by the client, no reply. A version 1.0 client sends no
250 payload; a version 1.0 server should ignore any such payload. A
251 version 1.0 server must not send a reply.
252
253
254 Possible future enhancements:
255
256 Synchronization; server and client reports the number of elapsed
257 cycles (unit to-be-defined) at each request or notification.
258 Pretty much the top-of-the-todo-list item.
259
260 Large addresses; 1.0 being restricted to 32-bit addresses.
261
262 Variable-size data; currently restricted to 32-bit register
263 accesses.
264
265 Specified data endianness (not the packet header) perhaps as part
266 of an initial format request; currently little-endian only.
267
268
269 Usage notes:
270 When used with servers sending RV_MEM_RD_CMD but being
271 narrow-minded about indata, set watchdog-interval to 0. Use
272 multiple rv instances when there are e.g. separate register and
273 memory servers. Alway log, setting "/rv/trace? true", at the
274 development phase. Borrow from the test-suite.
275 */
276
277#define RV_FAMILY_NAME "rv"
278
279enum rv_command {
280 RV_READ_CMD = 0,
281 RV_WRITE_CMD = 1,
282 RV_IRQ_CMD = 2,
283 RV_MEM_RD_CMD = 3,
284 RV_MEM_WR_CMD = 4,
285 RV_MBOX_HANDLE_CMD = 5,
286 RV_MBOX_PUT_CMD = 6,
287 RV_WATCHDOG_CMD = 7
288};
289
290
291typedef struct _hw_rv_device
292{
293 /* Mapping of remote interrupt bit-numbers to local ones. */
2875d098 294 uint32_t remote_to_local_int[32];
aad3b3cb
HPN
295
296 /* When multiple bits are set, a non-zero value here indicates that
297 this value should be used instead. */
2875d098 298 uint32_t intmultiple;
aad3b3cb
HPN
299
300 /* Local address of registers. */
2875d098 301 uint32_t reg_address;
aad3b3cb
HPN
302
303 /* Size of register bank in bytes. */
2875d098 304 uint32_t reg_size;
aad3b3cb
HPN
305
306 /* Remote address of registers. */
2875d098 307 uint32_t remote_reg_address;
aad3b3cb
HPN
308
309 /* Local address of DMA:able memory. */
2875d098 310 uint32_t mem_address;
aad3b3cb
HPN
311
312 /* Size of DMA:able memory in bytes. */
2875d098 313 uint32_t mem_size;
aad3b3cb
HPN
314
315 /* Bitmask for valid DMA request size. */
2875d098 316 uint32_t mem_burst_mask;
aad3b3cb
HPN
317
318 /* Remote address of DMA:able memory. */
2875d098 319 uint32_t remote_mem_address;
aad3b3cb
HPN
320
321 /* (Local) address of mbox; where to put a pointer to the mbox to be
322 sent. */
2875d098 323 uint32_t mbox_address;
aad3b3cb
HPN
324
325 /* Probably not 127.0.0.1:10000. */
326 const char *host;
327 int port;
328
329 /* If non-NULL, points to memory to use instead of connection. */
2875d098 330 uint8_t *dummy;
aad3b3cb
HPN
331
332 /* File descriptor for the socket. Set to -1 when error. Only one
333 of dummy and this is active. */
334 int fd;
335
336 /* Stashed errno, as we don't emit an error right away. */
337 int saved_errno;
338
339 /* This, plus latency because the CPU might not be checking until a
340 CTI insn (usually a branch or a jump) is the interval in cycles
341 between the rv is polled for e.g. DMA requests. */
2875d098 342 uint32_t max_tick_poll_interval;
aad3b3cb
HPN
343
344 /* Running counter for exponential backoff up to
345 max_tick_poll_interval to avoid polling the connection
346 unnecessarily often. Set to 1 when rv activity (read/write
347 register, DMA request) is detected. */
2875d098 348 uint32_t next_period;
aad3b3cb
HPN
349
350 /* This is the interval in wall-clock seconds between watchdog
351 packets are sent to the remote side. Zero means no watchdog
352 packets. */
2875d098 353 uint32_t watchdog_interval;
aad3b3cb
HPN
354
355 /* Last time we sent a watchdog packet. */
356 struct timeval last_wdog_time;
357
358 /* Mostly used as a kludge for knowing which rv:s have poll events
359 active. */
360 struct hw_event *poll_callback;
361} hw_rv_device;
362
363
364/* We might add ports in the future, so keep this an enumeration. */
365enum
366 {
367 INT_PORT
368 };
369
370/* Our ports. */
371static const struct hw_port_descriptor hw_rv_ports[] = {
372 { "int", INT_PORT, 0, output_port },
373 { NULL }
374};
375
376/* Send LEN bytes of data from BUF to the socket. Abort on
377 errors. */
378
379static void
380hw_rv_write (struct hw *me,
381 void *buf,
382 unsigned int len)
383{
384 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
2875d098 385 uint8_t *bufp = buf;
aad3b3cb
HPN
386
387 /* If we don't have a valid fd here, it's because we got an error
388 initially, and we suppressed that error. */
363a6e9f 389 if (rv->fd == -1)
aad3b3cb
HPN
390 hw_abort (me, "couldn't open a connection to %s:%d because: %s",
391 rv->host, rv->port, strerror (rv->saved_errno));
392
393 while (len > 0)
394 {
395 ssize_t ret = write (rv->fd, bufp, len);
396 if (ret < 0)
397 /* FIXME: More graceful exit. */
398 hw_abort (me, "write to %s:%d failed: %s\n", rv->host, rv->port,
399 strerror (errno));
400
401 len -= ret;
402 bufp += ret;
403 }
404}
405
406/* Read LEN bytes of data into BUF from the socket. Set the file
407 descriptor to -1 if there's an error. */
408
409static void
410hw_rv_read (struct hw *me,
411 void *buf,
412 unsigned int len)
413{
414 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
2875d098 415 uint8_t *bufp = buf;
aad3b3cb
HPN
416
417 while (len > 0)
418 {
419 ssize_t ret = read (rv->fd, bufp, len);
420
421 /* We get all zero if the remote end quits, but no error
422 indication; even select says there's data active. */
423 if (ret <= 0)
424 {
425 if (close (rv->fd) != 0)
426 /* FIXME: More graceful exit. */
427 hw_abort (me, "read from %s:%d failed: %d\n", rv->host, rv->port, errno);
428 rv->fd = -1;
429 return;
430 }
431
432 len -= ret;
433 bufp += ret;
434 }
435}
436
437/* Construct and send a packet of data of type CMD and len
438 LEN_NOHEADER (not counting the header...). */
439
440static void
441hw_rv_send (struct hw *me,
442 unsigned int cmd,
443 void *msg,
444 unsigned int len_noheader)
445{
446 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
2875d098
MF
447 uint8_t buf[32+3];
448 uint8_t *bufp;
aad3b3cb
HPN
449 unsigned int len = len_noheader + 3;
450 int ret;
451
452 buf[0] = len & 255;
453 buf[1] = (len >> 8) & 255;
454 buf[2] = cmd;
455
456 if (len > sizeof (buf))
457 {
458 hw_rv_write (me, buf, 3);
459 len = len_noheader;
460 bufp = msg;
461 }
462 else
463 {
464 memcpy (buf + 3, msg, len_noheader);
465 bufp = buf;
466 }
467
468 hw_rv_write (me, bufp, len);
469}
470
471/* Handle incoming DMA requests as per the RV_MEM_RD_CMD packet.
472 Abort on errors. */
473
474static void
475hw_rv_read_mem (struct hw *me, unsigned int len)
476{
477 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
478 /* If you change this size, please adjust the mem2 testcase. */
2875d098
MF
479 uint8_t buf[32+8];
480 uint8_t *bufp = buf;
481 uint32_t leaddr;
482 uint32_t addr;
483 uint32_t lelen;
484 uint32_t i;
aad3b3cb
HPN
485
486 if (len != 8)
487 hw_abort (me, "expected DMA read request len 8+3, got %d+3", len);
488
489 hw_rv_read (me, &leaddr, 4);
490 hw_rv_read (me, &lelen, 4);
491 len = LE2H_4 (lelen);
492 addr = LE2H_4 (leaddr);
493
494 if (addr < rv->remote_mem_address
495 || addr >= rv->remote_mem_address + rv->mem_size)
496 hw_abort (me, "DMA read at remote 0x%x; outside [0x%x..0x%x-1]",
497 (unsigned) addr, (unsigned) rv->remote_mem_address,
498 (unsigned) (rv->remote_mem_address + rv->mem_size));
499 addr = addr - rv->remote_mem_address + rv->mem_address;
500
501 if (len == 0)
502 hw_abort (me, "DMA read request for 0 bytes isn't supported");
503
504 if (len & ~rv->mem_burst_mask)
505 hw_abort (me, "DMA trying to read %d bytes; not matching mask of 0x%x",
506 len, rv->mem_burst_mask);
507 if (len + 8 > sizeof (buf))
508 bufp = hw_malloc (me, len + 8);
509
510 HW_TRACE ((me, "DMA R 0x%x..0x%x", addr, addr + len -1));
511 hw_dma_read_buffer (me, bufp + 8, 0, addr, len);
512 if (hw_trace_p (me))
513 for (i = 0; i < len; i += 4)
514 HW_TRACE ((me, "0x%x: %02x %02x %02x %02x",
515 addr + i,
516 bufp[i+8], bufp[i+9], bufp[i+10], bufp[i+11]));
517
518 memcpy (bufp, &leaddr, 4);
519 memcpy (bufp + 4, &lelen, 4);
520 hw_rv_send (me, RV_MEM_RD_CMD, bufp, len + 8);
521 if (bufp != buf)
522 hw_free (me, bufp);
523}
524
525/* Handle incoming DMA requests as per the RV_MEM_WR_CMD packet.
526 Abort on errors. */
527
528static void
529hw_rv_write_mem (struct hw *me, unsigned int plen)
530{
531 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
532 /* If you change this size, please adjust the mem2 testcase. */
2875d098
MF
533 uint8_t buf[32+8];
534 uint8_t *bufp = buf;
535 uint32_t leaddr;
536 uint32_t addr;
537 uint32_t lelen;
538 uint32_t len;
539 uint32_t i;
aad3b3cb
HPN
540
541 hw_rv_read (me, &leaddr, 4);
542 hw_rv_read (me, &lelen, 4);
543 len = LE2H_4 (lelen);
544 addr = LE2H_4 (leaddr);
545
546 if (len != plen - 8)
547 hw_abort (me,
548 "inconsistency in DMA write request packet: "
549 "envelope %d+3, inner %d bytes", plen, len);
550
551 if (addr < rv->remote_mem_address
552 || addr >= rv->remote_mem_address + rv->mem_size)
553 hw_abort (me, "DMA write at remote 0x%x; outside [0x%x..0x%x-1]",
554 (unsigned) addr, (unsigned) rv->remote_mem_address,
555 (unsigned) (rv->remote_mem_address + rv->mem_size));
556
557 addr = addr - rv->remote_mem_address + rv->mem_address;
558 if (len == 0)
559 hw_abort (me, "DMA write request for 0 bytes isn't supported");
560
561 if (len & ~rv->mem_burst_mask)
562 hw_abort (me, "DMA trying to write %d bytes; not matching mask of 0x%x",
563 len, rv->mem_burst_mask);
564 if (len + 8 > sizeof (buf))
565 bufp = hw_malloc (me, len + 8);
566
567 hw_rv_read (me, bufp + 8, len);
568 HW_TRACE ((me, "DMA W 0x%x..0x%x", addr, addr + len - 1));
569 hw_dma_write_buffer (me, bufp + 8, 0, addr, len, 0);
570 if (hw_trace_p (me))
571 for (i = 0; i < len; i += 4)
572 HW_TRACE ((me, "0x%x: %02x %02x %02x %02x",
573 addr + i,
574 bufp[i+8], bufp[i+9], bufp[i+10], bufp[i+11]));
575 if (bufp != buf)
576 hw_free (me, bufp);
577}
578
579static void
580hw_rv_irq (struct hw *me, unsigned int len)
581{
582 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
2875d098
MF
583 uint32_t intbitsle;
584 uint32_t intbits_ext;
585 uint32_t intval = 0;
aad3b3cb
HPN
586 int i;
587
588 if (len != 4)
589 hw_abort (me, "IRQ with %d data not supported", len);
590
591 hw_rv_read (me, &intbitsle, 4);
592 intbits_ext = LE2H_4 (intbitsle);
593 for (i = 0; i < 32; i++)
594 if ((intbits_ext & (1 << i)) != 0)
595 intval |= rv->remote_to_local_int[i];
596 if ((intbits_ext & ~(intbits_ext - 1)) != intbits_ext
597 && rv->intmultiple != 0)
598 intval = rv->intmultiple;
599
600 HW_TRACE ((me, "IRQ 0x%x", intval));
601 hw_port_event (me, INT_PORT, intval);
602}
603
604/* Handle incoming interrupt notifications as per the RV_IRQ_CMD
605 packet. Abort on errors. */
606
607static void
608hw_rv_handle_incoming (struct hw *me,
609 int expected_type,
2875d098 610 uint8_t *buf,
aad3b3cb
HPN
611 unsigned int *return_len)
612{
613 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
2875d098 614 uint8_t cbuf[32];
aad3b3cb
HPN
615 unsigned int len;
616 unsigned int cmd;
617
618 while (1)
619 {
620 hw_rv_read (me, cbuf, 3);
621
363a6e9f 622 if (rv->fd == -1)
aad3b3cb
HPN
623 return;
624
625 len = cbuf[0] + cbuf[1] * 256 - 3;
626 cmd = cbuf[2];
627
628 /* These come in "asynchronously"; not as a reply. */
629 switch (cmd)
630 {
631 case RV_IRQ_CMD:
632 hw_rv_irq (me, len);
633 break;
634
635 case RV_MEM_RD_CMD:
636 hw_rv_read_mem (me, len);
637 break;
638
639 case RV_MEM_WR_CMD:
640 hw_rv_write_mem (me, len);
641 break;
642 }
643
644 /* Something is incoming from the other side, so tighten up all
645 slack at the next wait. */
646 rv->next_period = 1;
647
648 switch (cmd)
649 {
650 case RV_MEM_RD_CMD:
651 case RV_MEM_WR_CMD:
652 case RV_IRQ_CMD:
653 /* Don't try to handle more than one of these if we were'nt
654 expecting a reply. */
655 if (expected_type == -1)
656 return;
657 continue;
658 }
659
660 /* Require a match between this supposed-reply and the command
661 for the rest. */
662 if (cmd != expected_type)
663 hw_abort (me, "unexpected reply, expected command %d, got %d",
664 expected_type, cmd);
665
666 switch (cmd)
667 {
668 case RV_MBOX_PUT_CMD:
669 case RV_MBOX_HANDLE_CMD:
670 case RV_WRITE_CMD:
671 case RV_READ_CMD:
672 hw_rv_read (me, buf, len <= *return_len ? len : *return_len);
673 *return_len = len;
674 break;
675 }
676 break;
677 }
678}
679
680/* Send a watchdog packet. Make a note of wallclock time. */
681
682static void
683hw_rv_send_wdog (struct hw *me)
684{
685 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
686 HW_TRACE ((me, "WD"));
687 gettimeofday (&rv->last_wdog_time, NULL);
688 hw_rv_send (me, RV_WATCHDOG_CMD, "", 0);
689}
690
691/* Poll the remote side: see if there's any incoming traffic; handle a
692 packet if so. Send a watchdog packet if it's time to do so.
693 Beware that the Linux select call indicates traffic for a socket
694 that the remote side has closed (which may be because it was
695 finished; don't hork until we need to write something just because
696 we're polling). */
697
698static void
699hw_rv_poll_once (struct hw *me)
700{
701 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
702 fd_set rfds;
703 fd_set efds;
704 struct timeval now;
705 int ret;
706 struct timeval tv;
707
363a6e9f 708 if (rv->fd == -1)
aad3b3cb
HPN
709 /* Connection has died or was never initiated. */
710 return;
711
712 FD_ZERO (&rfds);
713 FD_SET (rv->fd, &rfds);
714 FD_ZERO (&efds);
715 FD_SET (rv->fd, &efds);
716 tv.tv_sec = 0;
717 tv.tv_usec = 0;
718
719 ret = select (rv->fd + 1, &rfds, NULL, &efds, &tv);
720 gettimeofday (&now, NULL);
721
722 if (ret < 0)
723 hw_abort (me, "select failed: %d\n", errno);
724
725 if (rv->watchdog_interval != 0
726 && now.tv_sec - rv->last_wdog_time.tv_sec >= rv->watchdog_interval)
727 hw_rv_send_wdog (me);
728
729 if (FD_ISSET (rv->fd, &rfds))
730 hw_rv_handle_incoming (me, -1, NULL, NULL);
731}
732
733/* Initialize mapping of remote-to-local interrupt data. */
734
735static void
736hw_rv_map_ints (struct hw *me)
737{
738 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
739 int i;
740
741 for (i = 0; i < 32; i++)
742 rv->remote_to_local_int[i] = 1 << i;
743
744 if (hw_find_property (me, "intnum") != NULL)
745 for (i = 0; i < 32; i++)
746 {
747 signed_cell val = -1;
748 if (hw_find_integer_array_property (me, "intnum", i, &val) > 0)
749 {
750 if (val > 0)
751 rv->remote_to_local_int[i] = val;
752 else
753 hw_abort (me, "property \"intnum@%d\" must be > 0; is %d",
754 i, (int) val);
755 }
756 }
757}
758
759/* Handle the after-N-ticks "poll event", calling the poll-the-fd
760 method. Update the period. */
761
762static void
763do_poll_event (struct hw *me, void *data)
764{
765 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
2875d098 766 uint32_t new_period;
aad3b3cb
HPN
767
768 if (rv->dummy != NULL)
769 return;
770
771 hw_rv_poll_once (me);
772 if (rv->fd >= 0)
773 rv->poll_callback
774 = hw_event_queue_schedule (me, rv->next_period, do_poll_event, NULL);
775
776 new_period = rv->next_period * 2;
777 if (new_period <= rv->max_tick_poll_interval)
778 rv->next_period = new_period;
779}
780
781/* HW tree traverse function for hw_rv_add_init. */
782
783static void
784hw_rv_add_poller (struct hw *me, void *data)
785{
786 hw_rv_device *rv;
787
788 if (hw_family (me) == NULL
789 || strcmp (hw_family (me), RV_FAMILY_NAME) != 0)
790 return;
791
792 rv = (hw_rv_device *) hw_data (me);
793 if (rv->poll_callback != NULL)
794 return;
795
796 rv->poll_callback
797 = hw_event_queue_schedule (me, 1, do_poll_event, NULL);
798}
799
800/* Simulator module init function for hw_rv_add_init. */
801
802/* FIXME: For the call so hw_tree_traverse, we need to know that the
803 first member of struct sim_hw is the struct hw *root, but there's
804 no accessor method and struct sim_hw is defined in sim-hw.c only.
805 Hence this hack, until an accessor is added, or there's a traverse
806 function that takes a SIM_DESC argument. */
807struct sim_hw { struct hw *tree; };
808
809static SIM_RC
810hw_rv_add_rv_pollers (SIM_DESC sd)
811{
812 hw_tree_traverse (STATE_HW (sd)->tree, hw_rv_add_poller, NULL, NULL);
813 return SIM_RC_OK;
814}
815
816/* We need to add events for polling, but we can't add one from the
817 finish-function, and there are no other call points, at least for
818 instances without "reg" (when there are just DMA requests from the
819 remote end; no locally initiated activity). Therefore we add a
820 simulator module init function, but those don't have private
821 payload arguments; just a SD argument. We cope by parsing the HW
822 root and making sure *all* "rv":s have poll callbacks installed.
823 Luckily, this is just an initialization step, and not many
824 simultaneous instances of rv are expected: we get a N**2 complexity
825 for visits to each rv node by this method. */
826
827static void
828hw_rv_add_init (struct hw *me)
829{
830 sim_module_add_init_fn (hw_system (me), hw_rv_add_rv_pollers);
831}
832
833/* Open up a connection to the other side. Abort on errors. */
834
835static void
836hw_rv_init_socket (struct hw *me)
837{
838 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
839 int sock;
840 struct sockaddr_in server;
841
842 rv->fd = -1;
843
844 if (rv->dummy != NULL)
845 return;
846
847 memset (&server, 0, sizeof (server));
848 server.sin_family = AF_INET;
849 server.sin_addr.s_addr = inet_addr (rv->host);
850
851 /* Solaris 2.7 lacks this macro. */
852#ifndef INADDR_NONE
853#define INADDR_NONE -1
854#endif
855
856 if (server.sin_addr.s_addr == INADDR_NONE)
857 {
858 struct hostent *h;
859 h = gethostbyname (rv->host);
860 if (h != NULL)
861 {
862 memcpy (&server.sin_addr, h->h_addr, h->h_length);
863 server.sin_family = h->h_addrtype;
864 }
865 else
866 hw_abort (me, "can't resolve host %s", rv->host);
867 }
868
869 server.sin_port = htons (rv->port);
870 sock = socket (AF_INET, SOCK_STREAM, 0);
871
363a6e9f 872 if (sock == -1)
aad3b3cb
HPN
873 hw_abort (me, "can't get a socket for %s:%d connection",
874 rv->host, rv->port);
875
876 if (connect (sock, (struct sockaddr *) &server, sizeof server) >= 0)
877 {
878 rv->fd = sock;
879
880 /* FIXME: init packet here. Maybe start packet too. */
881 if (rv->watchdog_interval != 0)
882 hw_rv_send_wdog (me);
883 }
884 else
885 /* Stash the errno for later display, if some connection activity
886 is requested. Don't emit an error here; we might have been
887 called just for test purposes. */
888 rv->saved_errno = errno;
889}
890
891/* Local rv register reads end up here. */
892
893static unsigned int
894hw_rv_reg_read (struct hw *me,
895 void *dest,
896 int space,
897 unsigned_word addr,
898 unsigned int nr_bytes)
899{
900 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
2875d098
MF
901 uint8_t addr_data[8] = "";
902 uint32_t a_l = H2LE_4 (addr - rv->reg_address + rv->remote_reg_address);
aad3b3cb
HPN
903 unsigned int len = 8;
904
905 if (nr_bytes != 4)
906 hw_abort (me, "must be four byte read");
907
908 if (addr == rv->mbox_address)
909 hw_abort (me, "invalid read of mbox address 0x%x",
910 (unsigned) rv->mbox_address);
911
912 memcpy (addr_data, &a_l, 4);
913 HW_TRACE ((me, "REG R 0x%x", addr));
914 if (rv->dummy != NULL)
915 {
916 len = 8;
917 memcpy (addr_data + 4, rv->dummy + addr - rv->reg_address, 4);
918 }
919 else
920 {
921 hw_rv_send (me, RV_READ_CMD, addr_data, len);
922 hw_rv_handle_incoming (me, RV_READ_CMD, addr_data, &len);
923 }
924
925 if (len != 8)
926 hw_abort (me, "read %d != 8 bytes returned", len);
927 HW_TRACE ((me, ":= 0x%02x%02x%02x%02x",
928 addr_data[7], addr_data[6], addr_data[5], addr_data[4]));
929 memcpy (dest, addr_data + 4, 4);
930 return nr_bytes;
931}
932
933/* Local rv mbox requests (handle or put) end up here. */
934
935static void
936hw_rv_mbox (struct hw *me, unsigned_word address)
937{
2875d098 938 uint8_t buf[256+3];
aad3b3cb
HPN
939 unsigned int cmd;
940 unsigned int rlen;
2875d098 941 uint32_t i;
aad3b3cb
HPN
942 unsigned int len
943 = hw_dma_read_buffer (me, buf, 0, address, 3);
944
945 if (len != 3)
946 hw_abort (me, "mbox read %d != 3 bytes returned", len);
947
948 cmd = buf[2];
949 if (cmd != RV_MBOX_HANDLE_CMD && cmd != RV_MBOX_PUT_CMD)
950 hw_abort (me, "unsupported mbox command %d", cmd);
951
952 len = buf[0] + buf[1]*256;
953
954 if (len > sizeof (buf))
955 hw_abort (me, "mbox cmd %d send size %d unsupported", cmd, len);
956
957 rlen = hw_dma_read_buffer (me, buf + 3, 0, address + 3, len - 3);
958 if (rlen != len - 3)
959 hw_abort (me, "mbox read %d != %d bytes returned", rlen, len - 3);
960
961 HW_TRACE ((me, "MBOX %s 0x%x..0x%x",
962 cmd == RV_MBOX_HANDLE_CMD ? "H" : "P",
963 address, address + len - 1));
964 for (i = 0; i < rlen; i += 8)
965 HW_TRACE ((me, "0x%x: %02x %02x %02x %02x %02x %02x %02x %02x",
966 address + 3 + i,
967 buf[3+i], buf[4+i], buf[5+i], buf[6+i], buf[7+i], buf[8+i],
968 buf[9+i], buf[10+i]));
969
970 len -= 3;
971 hw_rv_send (me, cmd, buf + 3, len);
972
973 /* Note: both ..._PUT and ..._HANDLE get the ..._HANDLE reply. */
974 hw_rv_handle_incoming (me, RV_MBOX_HANDLE_CMD, buf + 3, &len);
975 if (len > sizeof (buf))
976 hw_abort (me, "mbox cmd %d receive size %d unsupported", cmd, len);
977 HW_TRACE ((me, "-> 0x%x..0x%x", address, address + len + 3 - 1));
978 for (i = 0; i < len; i += 8)
979 HW_TRACE ((me, "0x%x: %02x %02x %02x %02x %02x %02x %02x %02x",
980 address + 3 + i,
981 buf[3+i], buf[4+i], buf[5+i], buf[6+i], buf[7+i], buf[8+i],
982 buf[9+i], buf[10+i]));
983
984 len += 3;
985 buf[0] = len & 255;
986 buf[1] = len / 256;
987 rlen = hw_dma_write_buffer (me, buf, 0, address, len, 0);
988 if (rlen != len)
989 hw_abort (me, "mbox write %d != %d bytes", rlen, len);
990}
991
992/* Local rv register writes end up here. */
993
994static unsigned int
995hw_rv_reg_write (struct hw *me,
996 const void *source,
997 int space,
998 unsigned_word addr,
999 unsigned int nr_bytes)
1000{
1001 hw_rv_device *rv = (hw_rv_device *) hw_data (me);
1002
2875d098
MF
1003 uint8_t addr_data[8] = "";
1004 uint32_t a_l = H2LE_4 (addr - rv->reg_address + rv->remote_reg_address);
aad3b3cb
HPN
1005 unsigned int len = 8;
1006
1007 if (nr_bytes != 4)
1008 hw_abort (me, "must be four byte write");
1009
1010 memcpy (addr_data, &a_l, 4);
1011 memcpy (addr_data + 4, source, 4);
1012
1013 if (addr == rv->mbox_address)
1014 {
2875d098 1015 uint32_t mbox_addr_le;
aad3b3cb
HPN
1016 if (rv->dummy != NULL)
1017 hw_abort (me, "mbox not supported for a dummy instance");
1018 memcpy (&mbox_addr_le, source, 4);
1019 hw_rv_mbox (me, LE2H_4 (mbox_addr_le));
1020 return nr_bytes;
1021 }
1022
1023 HW_TRACE ((me, "REG W 0x%x := 0x%02x%02x%02x%02x", addr,
1024 addr_data[7], addr_data[6], addr_data[5], addr_data[4]));
1025 if (rv->dummy != NULL)
1026 {
1027 len = 8;
1028 memcpy (rv->dummy + addr - rv->reg_address, addr_data + 4, 4);
1029 }
1030 else
1031 {
1032 hw_rv_send (me, RV_WRITE_CMD, addr_data, len);
1033 hw_rv_handle_incoming (me, RV_WRITE_CMD, addr_data, &len);
1034 }
1035
1036 if (len != 8)
1037 hw_abort (me, "read %d != 8 bytes returned", len);
1038
1039 /* We had an access: tighten up all slack. */
1040 rv->next_period = 1;
1041
1042 return nr_bytes;
1043}
1044
1045/* Instance initializer function. */
1046
1047static void
1048hw_rv_finish (struct hw *me)
1049{
1050 hw_rv_device *rv = HW_ZALLOC (me, hw_rv_device);
1051 int i;
1052 const struct hw_property *mem_prop;
1053 const struct hw_property *dummy_prop;
1054 const struct hw_property *mbox_prop;
1055
1056 set_hw_data (me, rv);
1057
1058#undef RV_GET_IPROP
1059#undef RV_GET_PROP
1060#define RV_GET_PROP(T, N, M, D) \
1061 do \
1062 { \
1063 if (hw_find_property (me, N) != NULL) \
1064 rv->M = hw_find_ ## T ## _property (me, N); \
1065 else \
1066 rv->M = (D); \
1067 } \
1068 while (0)
1069#define RV_GET_IPROP(N, M, D) RV_GET_PROP (integer, N, M, D)
1070
1071 RV_GET_PROP (string, "host", host, "127.0.0.1");
1072 RV_GET_IPROP ("port", port, 10000);
1073 RV_GET_IPROP ("remote-reg", remote_reg_address, 0);
1074 RV_GET_IPROP ("max-poll-ticks", max_tick_poll_interval, 10000);
1075 RV_GET_IPROP ("watchdog-interval", watchdog_interval, 30);
1076 RV_GET_IPROP ("remote-mem", remote_mem_address, 0);
1077 RV_GET_IPROP ("mem-burst-mask", mem_burst_mask, 0xffff);
1078 RV_GET_IPROP ("intmultiple", intmultiple, 0);
1079
1080 set_hw_io_read_buffer (me, hw_rv_reg_read);
1081 set_hw_io_write_buffer (me, hw_rv_reg_write);
1082 set_hw_ports (me, hw_rv_ports);
1083 rv->next_period = 1;
1084
1085 /* FIXME: We only support zero or one reg and zero or one mem area. */
1086 if (hw_find_property (me, "reg") != NULL)
1087 {
1088 reg_property_spec reg;
1089 if (hw_find_reg_array_property (me, "reg", 0, &reg))
1090 {
1091 unsigned_word attach_address;
1092 int attach_space;
1093 unsigned int attach_size;
1094
1095 hw_unit_address_to_attach_address (hw_parent (me),
1096 &reg.address,
1097 &attach_space,
1098 &attach_address,
1099 me);
1100 rv->reg_address = attach_address;
1101 hw_unit_size_to_attach_size (hw_parent (me),
1102 &reg.size,
1103 &attach_size, me);
1104 rv->reg_size = attach_size;
1105 if ((attach_address & 3) != 0)
1106 hw_abort (me, "register block must be 4 byte aligned");
1107 hw_attach_address (hw_parent (me),
1108 0,
1109 attach_space, attach_address, attach_size,
1110 me);
1111 }
1112 else
1113 hw_abort (me, "property \"reg\" has the wrong type");
1114 }
1115
1116 dummy_prop = hw_find_property (me, "dummy");
1117 if (dummy_prop != NULL)
1118 {
1119 if (rv->reg_size == 0)
1120 hw_abort (me, "dummy argument requires a \"reg\" property");
1121
1122 if (hw_property_type (dummy_prop) == integer_property)
1123 {
2875d098
MF
1124 uint32_t dummyfill = hw_find_integer_property (me, "dummy");
1125 uint8_t *dummymem = hw_malloc (me, rv->reg_size);
aad3b3cb
HPN
1126 memset (dummymem, dummyfill, rv->reg_size);
1127 rv->dummy = dummymem;
1128 }
1129 else
1130 {
1131 const char *dummyarg = hw_find_string_property (me, "dummy");
2875d098 1132 uint8_t *dummymem = hw_malloc (me, rv->reg_size);
aad3b3cb
HPN
1133 FILE *f = fopen (dummyarg, "rb");
1134
1135 if (f == NULL)
1136 hw_abort (me, "opening dummy-file \"%s\": %s",
1137 dummyarg, strerror (errno));
1138 if (fread (dummymem, 1, rv->reg_size, f) != rv->reg_size)
1139 hw_abort (me, "reading dummy-file \"%s\": %s",
1140 dummyarg, strerror (errno));
1141 fclose (f);
1142 rv->dummy = dummymem;
1143 }
1144 }
1145
1146 mbox_prop = hw_find_property (me, "mbox");
1147 if (mbox_prop != NULL)
1148 {
1149 if (hw_property_type (mbox_prop) == integer_property)
1150 {
1151 signed_cell attach_address_sc
1152 = hw_find_integer_property (me, "mbox");
1153
2875d098 1154 rv->mbox_address = (uint32_t) attach_address_sc;
aad3b3cb
HPN
1155 hw_attach_address (hw_parent (me),
1156 0,
2875d098 1157 0, (uint32_t) attach_address_sc, 4, me);
aad3b3cb
HPN
1158 }
1159 else
1160 hw_abort (me, "property \"mbox\" has the wrong type");
1161 }
1162
1163 mem_prop = hw_find_property (me, "mem");
1164 if (mem_prop != NULL)
1165 {
1166 signed_cell attach_address_sc;
1167 signed_cell attach_size_sc;
1168
1169 /* Only specific names are reg_array_properties, the rest are
1170 array_properties. */
1171 if (hw_property_type (mem_prop) == array_property
1172 && hw_property_sizeof_array (mem_prop) == 2 * sizeof (attach_address_sc)
1173 && hw_find_integer_array_property (me, "mem", 0, &attach_address_sc)
1174 && hw_find_integer_array_property (me, "mem", 1, &attach_size_sc))
1175 {
1176 /* Unfortunate choice of types forces us to dance around a bit. */
2875d098
MF
1177 rv->mem_address = (uint32_t) attach_address_sc;
1178 rv->mem_size = (uint32_t) attach_size_sc;
aad3b3cb
HPN
1179 if ((attach_address_sc & 3) != 0)
1180 hw_abort (me, "memory block must be 4 byte aligned");
1181 }
1182 else
1183 hw_abort (me, "property \"mem\" has the wrong type");
1184 }
1185
1186 hw_rv_map_ints (me);
1187
1188 hw_rv_init_socket (me);
1189
1190 /* We need an extra initialization pass, after all others currently
1191 scheduled (mostly, after the simulation events machinery has been
1192 initialized so the events we want don't get thrown out). */
1193 hw_rv_add_init (me);
1194}
1195
1196/* Our root structure; see dv-* build machinery for usage. */
1197
1198const struct hw_descriptor dv_rv_descriptor[] = {
1199 { RV_FAMILY_NAME, hw_rv_finish },
1200 { NULL }
1201};