2 * hl_gw.c -- Hostlink gateway, low-level hostlink functions.
4 * Copyright (c) 2024 Synopsys Inc.
6 * The authors hereby grant permission to use, copy, modify, distribute,
7 * and license this software and its documentation for any purpose, provided
8 * that existing copyright notices are retained in all copies and that this
9 * notice is included verbatim in any distributions. No written agreement,
10 * license, or royalty fee is required for any of the authorized uses.
11 * Modifications to this software may be copyrighted by their authors
12 * and need not follow the licensing terms described here, provided that
13 * the new terms are clearly indicated on the first page of each file where
25 * Maximum message size without service information,
26 * see also HL_PAYLOAD_RESERVED.
29 #define HL_IOCHUNK 1024
33 * Each syscall argument have 4 bytes of service information in hostlink
34 * protocol (2 bytes for type and 2 for size). Here we reserve space for
37 #define HL_PAYLOAD_RESERVED (32 * 4)
39 /* "No message here" mark. */
40 #define HL_NOADDRESS 0xFFFFFFFF
42 /* Hostlink gateway structure. */
44 uint32_t version
; /* Current version is 1. */
45 uint32_t target2host_addr
; /* Packet address from target to host. */
46 uint32_t host2target_addr
; /* Packet address from host to target. */
47 uint32_t buf_addr
; /* Address for host to write answer. */
48 uint32_t payload_size
; /* Buffer size without packet header. */
49 uint32_t options
; /* For future use. */
50 uint32_t break_to_mon_addr
; /* For future use. */
51 } __uncached __packed
;
53 /* Hostlink packet header. */
55 uint32_t packet_id
; /* Packet id. Always set to 1 here. */
56 uint32_t total_size
; /* Size of packet including header. */
57 uint32_t priority
; /* For future use. */
58 uint32_t type
; /* For future use. */
59 uint32_t checksum
; /* For future use. */
60 } __uncached __packed
;
62 /* Main hostlink structure. */
64 volatile struct _hl_hdr hdr
; /* General hostlink information. */
65 /* Start of the hostlink buffer. */
66 volatile struct _hl_pkt_hdr pkt_hdr
;
67 volatile char payload
[HL_IOCHUNK
+ HL_PAYLOAD_RESERVED
];
68 } __aligned (HL_MAX_DCACHE_LINE
) __uncached __packed
;
72 * Main structure. Do not rename because simulator will look for the
73 * '__HOSTLINK__' symbol.
75 volatile struct _hl __HOSTLINK__
= {
78 .target2host_addr
= HL_NOADDRESS
82 /* Get hostlink payload pointer. */
83 volatile __uncached
void *
86 return (volatile __uncached
void *) &__HOSTLINK__
.payload
[0];
89 /* Get hostlink payload size (iochunk + reserved space). */
91 _hl_payload_size (void)
93 return sizeof (__HOSTLINK__
.payload
);
96 /* Get used space size in the payload. */
98 _hl_payload_used (volatile __uncached
void *p
)
100 return (volatile __uncached
char *) p
101 - (volatile __uncached
char *) _hl_payload ();
104 /* Fill hostlink packet header. */
106 _hl_pkt_init (volatile __uncached
struct _hl_pkt_hdr
*pkt
, int size
)
109 pkt
->total_size
= ALIGN (size
, 4) + sizeof (*pkt
);
115 /* Get hostlink iochunk size. */
117 _hl_iochunk_size (void)
122 /* Get free space size in the payload. */
124 _hl_payload_left (volatile __uncached
void *p
)
126 return _hl_payload_size () - _hl_payload_used (p
);
129 /* Send hostlink packet to the host. */
131 _hl_send (volatile __uncached
void *p
)
133 volatile __uncached
struct _hl_hdr
*hdr
= &__HOSTLINK__
.hdr
;
134 volatile __uncached
struct _hl_pkt_hdr
*pkt_hdr
= &__HOSTLINK__
.pkt_hdr
;
136 _hl_pkt_init (pkt_hdr
, _hl_payload_used (p
));
138 #if defined (__ARC64__)
140 * Here we pass only low 4 bytes of the packet address (pkt_hdr).
141 * The high part of the address is obtained from __HOSTLINK__ address.
143 hdr
->buf_addr
= (uintptr_t) pkt_hdr
& 0xFFFFFFFF;
145 hdr
->buf_addr
= (uint32_t) pkt_hdr
;
147 hdr
->payload_size
= _hl_payload_size ();
148 hdr
->host2target_addr
= HL_NOADDRESS
;
149 hdr
->version
= HL_VERSION
;
151 hdr
->break_to_mon_addr
= 0;
153 /* This tells the debugger we have a command.
154 * It is responsibility of debugger to set this back to HL_NOADDRESS
155 * after receiving the packet.
156 * Please note that we don't wait here because some implementations
157 * use _hl_blockedPeek() function as a signal that we send a messege.
159 hdr
->target2host_addr
= hdr
->buf_addr
;
163 * Wait for host response and return pointer to hostlink payload.
164 * Symbol _hl_blockedPeek() is used by the simulator as message signal.
166 volatile __uncached
char * __noinline
167 _hl_blockedPeek (void)
169 while (__HOSTLINK__
.hdr
.host2target_addr
== HL_NOADDRESS
)
174 return _hl_payload ();
177 /* Get message from host. */
178 volatile __uncached
char *
181 return _hl_blockedPeek ();
184 /* Mark hostlink buffer as "No message here". */
188 __HOSTLINK__
.hdr
.target2host_addr
= HL_NOADDRESS
;