Statistics
| Branch: | Revision:

root / hw / slavio_misc.c @ 1ea879e5

History | View | Annotate | Download (12.7 kB)

1 3475187d bellard
/*
2 3475187d bellard
 * QEMU Sparc SLAVIO aux io port emulation
3 5fafdf24 ths
 *
4 3475187d bellard
 * Copyright (c) 2005 Fabrice Bellard
5 5fafdf24 ths
 *
6 3475187d bellard
 * Permission is hereby granted, free of charge, to any person obtaining a copy
7 3475187d bellard
 * of this software and associated documentation files (the "Software"), to deal
8 3475187d bellard
 * in the Software without restriction, including without limitation the rights
9 3475187d bellard
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10 3475187d bellard
 * copies of the Software, and to permit persons to whom the Software is
11 3475187d bellard
 * furnished to do so, subject to the following conditions:
12 3475187d bellard
 *
13 3475187d bellard
 * The above copyright notice and this permission notice shall be included in
14 3475187d bellard
 * all copies or substantial portions of the Software.
15 3475187d bellard
 *
16 3475187d bellard
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 3475187d bellard
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 3475187d bellard
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19 3475187d bellard
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 3475187d bellard
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 3475187d bellard
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22 3475187d bellard
 * THE SOFTWARE.
23 3475187d bellard
 */
24 87ecb68b pbrook
#include "hw.h"
25 87ecb68b pbrook
#include "sun4m.h"
26 87ecb68b pbrook
#include "sysemu.h"
27 87ecb68b pbrook
28 3475187d bellard
/* debug misc */
29 3475187d bellard
//#define DEBUG_MISC
30 3475187d bellard
31 3475187d bellard
/*
32 3475187d bellard
 * This is the auxio port, chip control and system control part of
33 3475187d bellard
 * chip STP2001 (Slave I/O), also produced as NCR89C105. See
34 3475187d bellard
 * http://www.ibiblio.org/pub/historic-linux/early-ports/Sparc/NCR/NCR89C105.txt
35 3475187d bellard
 *
36 3475187d bellard
 * This also includes the PMC CPU idle controller.
37 3475187d bellard
 */
38 3475187d bellard
39 3475187d bellard
#ifdef DEBUG_MISC
40 3475187d bellard
#define MISC_DPRINTF(fmt, args...) \
41 3475187d bellard
do { printf("MISC: " fmt , ##args); } while (0)
42 3475187d bellard
#else
43 3475187d bellard
#define MISC_DPRINTF(fmt, args...)
44 3475187d bellard
#endif
45 3475187d bellard
46 3475187d bellard
typedef struct MiscState {
47 d537cf6c pbrook
    qemu_irq irq;
48 3475187d bellard
    uint8_t config;
49 3475187d bellard
    uint8_t aux1, aux2;
50 bfa30a38 blueswir1
    uint8_t diag, mctrl;
51 bfa30a38 blueswir1
    uint32_t sysctrl;
52 6a3b9cc9 blueswir1
    uint16_t leds;
53 6d0c293d blueswir1
    qemu_irq cpu_halt;
54 2be17ebd blueswir1
    qemu_irq fdc_tc;
55 3475187d bellard
} MiscState;
56 3475187d bellard
57 5aca8c3b blueswir1
#define MISC_SIZE 1
58 a8f48dcc blueswir1
#define SYSCTRL_SIZE 4
59 d5296cb5 blueswir1
#define LED_MAXADDR 1
60 6a3b9cc9 blueswir1
#define LED_SIZE (LED_MAXADDR + 1)
61 3475187d bellard
62 7debeb82 blueswir1
#define MISC_MASK 0x0fff0000
63 7debeb82 blueswir1
#define MISC_LEDS 0x01600000
64 7debeb82 blueswir1
#define MISC_CFG  0x01800000
65 7debeb82 blueswir1
#define MISC_DIAG 0x01a00000
66 7debeb82 blueswir1
#define MISC_MDM  0x01b00000
67 7debeb82 blueswir1
#define MISC_SYS  0x01f00000
68 7debeb82 blueswir1
69 2be17ebd blueswir1
#define AUX1_TC        0x02
70 2be17ebd blueswir1
71 7debeb82 blueswir1
#define AUX2_PWROFF    0x01
72 7debeb82 blueswir1
#define AUX2_PWRINTCLR 0x02
73 7debeb82 blueswir1
#define AUX2_PWRFAIL   0x20
74 7debeb82 blueswir1
75 7debeb82 blueswir1
#define CFG_PWRINTEN   0x08
76 7debeb82 blueswir1
77 7debeb82 blueswir1
#define SYS_RESET      0x01
78 7debeb82 blueswir1
#define SYS_RESETSTAT  0x02
79 7debeb82 blueswir1
80 3475187d bellard
static void slavio_misc_update_irq(void *opaque)
81 3475187d bellard
{
82 3475187d bellard
    MiscState *s = opaque;
83 3475187d bellard
84 7debeb82 blueswir1
    if ((s->aux2 & AUX2_PWRFAIL) && (s->config & CFG_PWRINTEN)) {
85 d537cf6c pbrook
        MISC_DPRINTF("Raise IRQ\n");
86 d537cf6c pbrook
        qemu_irq_raise(s->irq);
87 3475187d bellard
    } else {
88 d537cf6c pbrook
        MISC_DPRINTF("Lower IRQ\n");
89 d537cf6c pbrook
        qemu_irq_lower(s->irq);
90 3475187d bellard
    }
91 3475187d bellard
}
92 3475187d bellard
93 3475187d bellard
static void slavio_misc_reset(void *opaque)
94 3475187d bellard
{
95 3475187d bellard
    MiscState *s = opaque;
96 3475187d bellard
97 4e3b1ea1 bellard
    // Diagnostic and system control registers not cleared in reset
98 3475187d bellard
    s->config = s->aux1 = s->aux2 = s->mctrl = 0;
99 3475187d bellard
}
100 3475187d bellard
101 3475187d bellard
void slavio_set_power_fail(void *opaque, int power_failing)
102 3475187d bellard
{
103 3475187d bellard
    MiscState *s = opaque;
104 3475187d bellard
105 3475187d bellard
    MISC_DPRINTF("Power fail: %d, config: %d\n", power_failing, s->config);
106 7debeb82 blueswir1
    if (power_failing && (s->config & CFG_PWRINTEN)) {
107 7debeb82 blueswir1
        s->aux2 |= AUX2_PWRFAIL;
108 3475187d bellard
    } else {
109 7debeb82 blueswir1
        s->aux2 &= ~AUX2_PWRFAIL;
110 3475187d bellard
    }
111 3475187d bellard
    slavio_misc_update_irq(s);
112 3475187d bellard
}
113 3475187d bellard
114 a8f48dcc blueswir1
static void slavio_cfg_mem_writeb(void *opaque, target_phys_addr_t addr,
115 a8f48dcc blueswir1
                                  uint32_t val)
116 a8f48dcc blueswir1
{
117 a8f48dcc blueswir1
    MiscState *s = opaque;
118 a8f48dcc blueswir1
119 a8f48dcc blueswir1
    MISC_DPRINTF("Write config %2.2x\n", val & 0xff);
120 a8f48dcc blueswir1
    s->config = val & 0xff;
121 a8f48dcc blueswir1
    slavio_misc_update_irq(s);
122 a8f48dcc blueswir1
}
123 a8f48dcc blueswir1
124 a8f48dcc blueswir1
static uint32_t slavio_cfg_mem_readb(void *opaque, target_phys_addr_t addr)
125 a8f48dcc blueswir1
{
126 a8f48dcc blueswir1
    MiscState *s = opaque;
127 a8f48dcc blueswir1
    uint32_t ret = 0;
128 a8f48dcc blueswir1
129 a8f48dcc blueswir1
    ret = s->config;
130 a8f48dcc blueswir1
    MISC_DPRINTF("Read config %2.2x\n", ret);
131 a8f48dcc blueswir1
    return ret;
132 a8f48dcc blueswir1
}
133 a8f48dcc blueswir1
134 a8f48dcc blueswir1
static CPUReadMemoryFunc *slavio_cfg_mem_read[3] = {
135 a8f48dcc blueswir1
    slavio_cfg_mem_readb,
136 a8f48dcc blueswir1
    NULL,
137 a8f48dcc blueswir1
    NULL,
138 a8f48dcc blueswir1
};
139 a8f48dcc blueswir1
140 a8f48dcc blueswir1
static CPUWriteMemoryFunc *slavio_cfg_mem_write[3] = {
141 a8f48dcc blueswir1
    slavio_cfg_mem_writeb,
142 a8f48dcc blueswir1
    NULL,
143 a8f48dcc blueswir1
    NULL,
144 a8f48dcc blueswir1
};
145 a8f48dcc blueswir1
146 a8f48dcc blueswir1
static void slavio_diag_mem_writeb(void *opaque, target_phys_addr_t addr,
147 bfa30a38 blueswir1
                                   uint32_t val)
148 3475187d bellard
{
149 3475187d bellard
    MiscState *s = opaque;
150 3475187d bellard
151 a8f48dcc blueswir1
    MISC_DPRINTF("Write diag %2.2x\n", val & 0xff);
152 a8f48dcc blueswir1
    s->diag = val & 0xff;
153 3475187d bellard
}
154 3475187d bellard
155 a8f48dcc blueswir1
static uint32_t slavio_diag_mem_readb(void *opaque, target_phys_addr_t addr)
156 3475187d bellard
{
157 3475187d bellard
    MiscState *s = opaque;
158 3475187d bellard
    uint32_t ret = 0;
159 3475187d bellard
160 a8f48dcc blueswir1
    ret = s->diag;
161 a8f48dcc blueswir1
    MISC_DPRINTF("Read diag %2.2x\n", ret);
162 a8f48dcc blueswir1
    return ret;
163 a8f48dcc blueswir1
}
164 a8f48dcc blueswir1
165 a8f48dcc blueswir1
static CPUReadMemoryFunc *slavio_diag_mem_read[3] = {
166 a8f48dcc blueswir1
    slavio_diag_mem_readb,
167 a8f48dcc blueswir1
    NULL,
168 a8f48dcc blueswir1
    NULL,
169 a8f48dcc blueswir1
};
170 a8f48dcc blueswir1
171 a8f48dcc blueswir1
static CPUWriteMemoryFunc *slavio_diag_mem_write[3] = {
172 a8f48dcc blueswir1
    slavio_diag_mem_writeb,
173 a8f48dcc blueswir1
    NULL,
174 a8f48dcc blueswir1
    NULL,
175 a8f48dcc blueswir1
};
176 a8f48dcc blueswir1
177 a8f48dcc blueswir1
static void slavio_mdm_mem_writeb(void *opaque, target_phys_addr_t addr,
178 a8f48dcc blueswir1
                                  uint32_t val)
179 a8f48dcc blueswir1
{
180 a8f48dcc blueswir1
    MiscState *s = opaque;
181 a8f48dcc blueswir1
182 a8f48dcc blueswir1
    MISC_DPRINTF("Write modem control %2.2x\n", val & 0xff);
183 a8f48dcc blueswir1
    s->mctrl = val & 0xff;
184 a8f48dcc blueswir1
}
185 a8f48dcc blueswir1
186 a8f48dcc blueswir1
static uint32_t slavio_mdm_mem_readb(void *opaque, target_phys_addr_t addr)
187 a8f48dcc blueswir1
{
188 a8f48dcc blueswir1
    MiscState *s = opaque;
189 a8f48dcc blueswir1
    uint32_t ret = 0;
190 a8f48dcc blueswir1
191 a8f48dcc blueswir1
    ret = s->mctrl;
192 a8f48dcc blueswir1
    MISC_DPRINTF("Read modem control %2.2x\n", ret);
193 3475187d bellard
    return ret;
194 3475187d bellard
}
195 3475187d bellard
196 a8f48dcc blueswir1
static CPUReadMemoryFunc *slavio_mdm_mem_read[3] = {
197 a8f48dcc blueswir1
    slavio_mdm_mem_readb,
198 7c560456 blueswir1
    NULL,
199 7c560456 blueswir1
    NULL,
200 3475187d bellard
};
201 3475187d bellard
202 a8f48dcc blueswir1
static CPUWriteMemoryFunc *slavio_mdm_mem_write[3] = {
203 a8f48dcc blueswir1
    slavio_mdm_mem_writeb,
204 7c560456 blueswir1
    NULL,
205 7c560456 blueswir1
    NULL,
206 3475187d bellard
};
207 3475187d bellard
208 0019ad53 blueswir1
static void slavio_aux1_mem_writeb(void *opaque, target_phys_addr_t addr,
209 0019ad53 blueswir1
                                   uint32_t val)
210 0019ad53 blueswir1
{
211 0019ad53 blueswir1
    MiscState *s = opaque;
212 0019ad53 blueswir1
213 0019ad53 blueswir1
    MISC_DPRINTF("Write aux1 %2.2x\n", val & 0xff);
214 2be17ebd blueswir1
    if (val & AUX1_TC) {
215 2be17ebd blueswir1
        // Send a pulse to floppy terminal count line
216 2be17ebd blueswir1
        if (s->fdc_tc) {
217 2be17ebd blueswir1
            qemu_irq_raise(s->fdc_tc);
218 2be17ebd blueswir1
            qemu_irq_lower(s->fdc_tc);
219 2be17ebd blueswir1
        }
220 2be17ebd blueswir1
        val &= ~AUX1_TC;
221 2be17ebd blueswir1
    }
222 0019ad53 blueswir1
    s->aux1 = val & 0xff;
223 0019ad53 blueswir1
}
224 0019ad53 blueswir1
225 0019ad53 blueswir1
static uint32_t slavio_aux1_mem_readb(void *opaque, target_phys_addr_t addr)
226 0019ad53 blueswir1
{
227 0019ad53 blueswir1
    MiscState *s = opaque;
228 0019ad53 blueswir1
    uint32_t ret = 0;
229 0019ad53 blueswir1
230 0019ad53 blueswir1
    ret = s->aux1;
231 0019ad53 blueswir1
    MISC_DPRINTF("Read aux1 %2.2x\n", ret);
232 0019ad53 blueswir1
233 0019ad53 blueswir1
    return ret;
234 0019ad53 blueswir1
}
235 0019ad53 blueswir1
236 0019ad53 blueswir1
static CPUReadMemoryFunc *slavio_aux1_mem_read[3] = {
237 0019ad53 blueswir1
    slavio_aux1_mem_readb,
238 0019ad53 blueswir1
    NULL,
239 0019ad53 blueswir1
    NULL,
240 0019ad53 blueswir1
};
241 0019ad53 blueswir1
242 0019ad53 blueswir1
static CPUWriteMemoryFunc *slavio_aux1_mem_write[3] = {
243 0019ad53 blueswir1
    slavio_aux1_mem_writeb,
244 0019ad53 blueswir1
    NULL,
245 0019ad53 blueswir1
    NULL,
246 0019ad53 blueswir1
};
247 0019ad53 blueswir1
248 0019ad53 blueswir1
static void slavio_aux2_mem_writeb(void *opaque, target_phys_addr_t addr,
249 0019ad53 blueswir1
                                   uint32_t val)
250 0019ad53 blueswir1
{
251 0019ad53 blueswir1
    MiscState *s = opaque;
252 0019ad53 blueswir1
253 0019ad53 blueswir1
    val &= AUX2_PWRINTCLR | AUX2_PWROFF;
254 0019ad53 blueswir1
    MISC_DPRINTF("Write aux2 %2.2x\n", val);
255 0019ad53 blueswir1
    val |= s->aux2 & AUX2_PWRFAIL;
256 0019ad53 blueswir1
    if (val & AUX2_PWRINTCLR) // Clear Power Fail int
257 0019ad53 blueswir1
        val &= AUX2_PWROFF;
258 0019ad53 blueswir1
    s->aux2 = val;
259 0019ad53 blueswir1
    if (val & AUX2_PWROFF)
260 0019ad53 blueswir1
        qemu_system_shutdown_request();
261 0019ad53 blueswir1
    slavio_misc_update_irq(s);
262 0019ad53 blueswir1
}
263 0019ad53 blueswir1
264 0019ad53 blueswir1
static uint32_t slavio_aux2_mem_readb(void *opaque, target_phys_addr_t addr)
265 0019ad53 blueswir1
{
266 0019ad53 blueswir1
    MiscState *s = opaque;
267 0019ad53 blueswir1
    uint32_t ret = 0;
268 0019ad53 blueswir1
269 0019ad53 blueswir1
    ret = s->aux2;
270 0019ad53 blueswir1
    MISC_DPRINTF("Read aux2 %2.2x\n", ret);
271 0019ad53 blueswir1
272 0019ad53 blueswir1
    return ret;
273 0019ad53 blueswir1
}
274 0019ad53 blueswir1
275 0019ad53 blueswir1
static CPUReadMemoryFunc *slavio_aux2_mem_read[3] = {
276 0019ad53 blueswir1
    slavio_aux2_mem_readb,
277 0019ad53 blueswir1
    NULL,
278 0019ad53 blueswir1
    NULL,
279 0019ad53 blueswir1
};
280 0019ad53 blueswir1
281 0019ad53 blueswir1
static CPUWriteMemoryFunc *slavio_aux2_mem_write[3] = {
282 0019ad53 blueswir1
    slavio_aux2_mem_writeb,
283 0019ad53 blueswir1
    NULL,
284 0019ad53 blueswir1
    NULL,
285 0019ad53 blueswir1
};
286 0019ad53 blueswir1
287 0019ad53 blueswir1
static void apc_mem_writeb(void *opaque, target_phys_addr_t addr, uint32_t val)
288 0019ad53 blueswir1
{
289 0019ad53 blueswir1
    MiscState *s = opaque;
290 0019ad53 blueswir1
291 0019ad53 blueswir1
    MISC_DPRINTF("Write power management %2.2x\n", val & 0xff);
292 6d0c293d blueswir1
    qemu_irq_raise(s->cpu_halt);
293 0019ad53 blueswir1
}
294 0019ad53 blueswir1
295 0019ad53 blueswir1
static uint32_t apc_mem_readb(void *opaque, target_phys_addr_t addr)
296 0019ad53 blueswir1
{
297 0019ad53 blueswir1
    uint32_t ret = 0;
298 0019ad53 blueswir1
299 0019ad53 blueswir1
    MISC_DPRINTF("Read power management %2.2x\n", ret);
300 0019ad53 blueswir1
    return ret;
301 0019ad53 blueswir1
}
302 0019ad53 blueswir1
303 0019ad53 blueswir1
static CPUReadMemoryFunc *apc_mem_read[3] = {
304 0019ad53 blueswir1
    apc_mem_readb,
305 0019ad53 blueswir1
    NULL,
306 0019ad53 blueswir1
    NULL,
307 0019ad53 blueswir1
};
308 0019ad53 blueswir1
309 0019ad53 blueswir1
static CPUWriteMemoryFunc *apc_mem_write[3] = {
310 0019ad53 blueswir1
    apc_mem_writeb,
311 0019ad53 blueswir1
    NULL,
312 0019ad53 blueswir1
    NULL,
313 0019ad53 blueswir1
};
314 0019ad53 blueswir1
315 bfa30a38 blueswir1
static uint32_t slavio_sysctrl_mem_readl(void *opaque, target_phys_addr_t addr)
316 bfa30a38 blueswir1
{
317 bfa30a38 blueswir1
    MiscState *s = opaque;
318 a8f48dcc blueswir1
    uint32_t ret = 0;
319 bfa30a38 blueswir1
320 a8f48dcc blueswir1
    switch (addr) {
321 bfa30a38 blueswir1
    case 0:
322 bfa30a38 blueswir1
        ret = s->sysctrl;
323 bfa30a38 blueswir1
        break;
324 bfa30a38 blueswir1
    default:
325 bfa30a38 blueswir1
        break;
326 bfa30a38 blueswir1
    }
327 bfa30a38 blueswir1
    MISC_DPRINTF("Read system control reg 0x" TARGET_FMT_plx " = %x\n", addr,
328 bfa30a38 blueswir1
                 ret);
329 bfa30a38 blueswir1
    return ret;
330 bfa30a38 blueswir1
}
331 bfa30a38 blueswir1
332 bfa30a38 blueswir1
static void slavio_sysctrl_mem_writel(void *opaque, target_phys_addr_t addr,
333 bfa30a38 blueswir1
                                      uint32_t val)
334 bfa30a38 blueswir1
{
335 bfa30a38 blueswir1
    MiscState *s = opaque;
336 bfa30a38 blueswir1
337 bfa30a38 blueswir1
    MISC_DPRINTF("Write system control reg 0x" TARGET_FMT_plx " =  %x\n", addr,
338 bfa30a38 blueswir1
                 val);
339 a8f48dcc blueswir1
    switch (addr) {
340 bfa30a38 blueswir1
    case 0:
341 7debeb82 blueswir1
        if (val & SYS_RESET) {
342 7debeb82 blueswir1
            s->sysctrl = SYS_RESETSTAT;
343 bfa30a38 blueswir1
            qemu_system_reset_request();
344 bfa30a38 blueswir1
        }
345 bfa30a38 blueswir1
        break;
346 bfa30a38 blueswir1
    default:
347 bfa30a38 blueswir1
        break;
348 bfa30a38 blueswir1
    }
349 bfa30a38 blueswir1
}
350 bfa30a38 blueswir1
351 bfa30a38 blueswir1
static CPUReadMemoryFunc *slavio_sysctrl_mem_read[3] = {
352 7c560456 blueswir1
    NULL,
353 7c560456 blueswir1
    NULL,
354 bfa30a38 blueswir1
    slavio_sysctrl_mem_readl,
355 bfa30a38 blueswir1
};
356 bfa30a38 blueswir1
357 bfa30a38 blueswir1
static CPUWriteMemoryFunc *slavio_sysctrl_mem_write[3] = {
358 7c560456 blueswir1
    NULL,
359 7c560456 blueswir1
    NULL,
360 bfa30a38 blueswir1
    slavio_sysctrl_mem_writel,
361 bfa30a38 blueswir1
};
362 bfa30a38 blueswir1
363 7c560456 blueswir1
static uint32_t slavio_led_mem_readw(void *opaque, target_phys_addr_t addr)
364 6a3b9cc9 blueswir1
{
365 6a3b9cc9 blueswir1
    MiscState *s = opaque;
366 a8f48dcc blueswir1
    uint32_t ret = 0;
367 6a3b9cc9 blueswir1
368 a8f48dcc blueswir1
    switch (addr) {
369 6a3b9cc9 blueswir1
    case 0:
370 6a3b9cc9 blueswir1
        ret = s->leds;
371 6a3b9cc9 blueswir1
        break;
372 6a3b9cc9 blueswir1
    default:
373 6a3b9cc9 blueswir1
        break;
374 6a3b9cc9 blueswir1
    }
375 6a3b9cc9 blueswir1
    MISC_DPRINTF("Read diagnostic LED reg 0x" TARGET_FMT_plx " = %x\n", addr,
376 6a3b9cc9 blueswir1
                 ret);
377 6a3b9cc9 blueswir1
    return ret;
378 6a3b9cc9 blueswir1
}
379 6a3b9cc9 blueswir1
380 7c560456 blueswir1
static void slavio_led_mem_writew(void *opaque, target_phys_addr_t addr,
381 6a3b9cc9 blueswir1
                                  uint32_t val)
382 6a3b9cc9 blueswir1
{
383 6a3b9cc9 blueswir1
    MiscState *s = opaque;
384 6a3b9cc9 blueswir1
385 6a3b9cc9 blueswir1
    MISC_DPRINTF("Write diagnostic LED reg 0x" TARGET_FMT_plx " =  %x\n", addr,
386 6a3b9cc9 blueswir1
                 val);
387 a8f48dcc blueswir1
    switch (addr) {
388 6a3b9cc9 blueswir1
    case 0:
389 d5296cb5 blueswir1
        s->leds = val;
390 6a3b9cc9 blueswir1
        break;
391 6a3b9cc9 blueswir1
    default:
392 6a3b9cc9 blueswir1
        break;
393 6a3b9cc9 blueswir1
    }
394 6a3b9cc9 blueswir1
}
395 6a3b9cc9 blueswir1
396 6a3b9cc9 blueswir1
static CPUReadMemoryFunc *slavio_led_mem_read[3] = {
397 7c560456 blueswir1
    NULL,
398 7c560456 blueswir1
    slavio_led_mem_readw,
399 7c560456 blueswir1
    NULL,
400 6a3b9cc9 blueswir1
};
401 6a3b9cc9 blueswir1
402 6a3b9cc9 blueswir1
static CPUWriteMemoryFunc *slavio_led_mem_write[3] = {
403 7c560456 blueswir1
    NULL,
404 7c560456 blueswir1
    slavio_led_mem_writew,
405 7c560456 blueswir1
    NULL,
406 6a3b9cc9 blueswir1
};
407 6a3b9cc9 blueswir1
408 3475187d bellard
static void slavio_misc_save(QEMUFile *f, void *opaque)
409 3475187d bellard
{
410 3475187d bellard
    MiscState *s = opaque;
411 22548760 blueswir1
    uint32_t tmp = 0;
412 bfa30a38 blueswir1
    uint8_t tmp8;
413 3475187d bellard
414 d537cf6c pbrook
    qemu_put_be32s(f, &tmp); /* ignored, was IRQ.  */
415 3475187d bellard
    qemu_put_8s(f, &s->config);
416 3475187d bellard
    qemu_put_8s(f, &s->aux1);
417 3475187d bellard
    qemu_put_8s(f, &s->aux2);
418 3475187d bellard
    qemu_put_8s(f, &s->diag);
419 3475187d bellard
    qemu_put_8s(f, &s->mctrl);
420 bfa30a38 blueswir1
    tmp8 = s->sysctrl & 0xff;
421 bfa30a38 blueswir1
    qemu_put_8s(f, &tmp8);
422 3475187d bellard
}
423 3475187d bellard
424 3475187d bellard
static int slavio_misc_load(QEMUFile *f, void *opaque, int version_id)
425 3475187d bellard
{
426 3475187d bellard
    MiscState *s = opaque;
427 22548760 blueswir1
    uint32_t tmp;
428 bfa30a38 blueswir1
    uint8_t tmp8;
429 3475187d bellard
430 3475187d bellard
    if (version_id != 1)
431 3475187d bellard
        return -EINVAL;
432 3475187d bellard
433 d537cf6c pbrook
    qemu_get_be32s(f, &tmp);
434 3475187d bellard
    qemu_get_8s(f, &s->config);
435 3475187d bellard
    qemu_get_8s(f, &s->aux1);
436 3475187d bellard
    qemu_get_8s(f, &s->aux2);
437 3475187d bellard
    qemu_get_8s(f, &s->diag);
438 3475187d bellard
    qemu_get_8s(f, &s->mctrl);
439 bfa30a38 blueswir1
    qemu_get_8s(f, &tmp8);
440 bfa30a38 blueswir1
    s->sysctrl = (uint32_t)tmp8;
441 3475187d bellard
    return 0;
442 3475187d bellard
}
443 3475187d bellard
444 5dcb6b91 blueswir1
void *slavio_misc_init(target_phys_addr_t base, target_phys_addr_t power_base,
445 0019ad53 blueswir1
                       target_phys_addr_t aux1_base,
446 0019ad53 blueswir1
                       target_phys_addr_t aux2_base, qemu_irq irq,
447 6d0c293d blueswir1
                       qemu_irq cpu_halt, qemu_irq **fdc_tc)
448 3475187d bellard
{
449 0019ad53 blueswir1
    int io;
450 3475187d bellard
    MiscState *s;
451 3475187d bellard
452 3475187d bellard
    s = qemu_mallocz(sizeof(MiscState));
453 3475187d bellard
    if (!s)
454 3475187d bellard
        return NULL;
455 3475187d bellard
456 0019ad53 blueswir1
    if (base) {
457 0019ad53 blueswir1
        /* 8 bit registers */
458 a8f48dcc blueswir1
459 0019ad53 blueswir1
        // Slavio control
460 a8f48dcc blueswir1
        io = cpu_register_io_memory(0, slavio_cfg_mem_read,
461 a8f48dcc blueswir1
                                    slavio_cfg_mem_write, s);
462 a8f48dcc blueswir1
        cpu_register_physical_memory(base + MISC_CFG, MISC_SIZE, io);
463 a8f48dcc blueswir1
464 0019ad53 blueswir1
        // Diagnostics
465 a8f48dcc blueswir1
        io = cpu_register_io_memory(0, slavio_diag_mem_read,
466 a8f48dcc blueswir1
                                    slavio_diag_mem_write, s);
467 a8f48dcc blueswir1
        cpu_register_physical_memory(base + MISC_DIAG, MISC_SIZE, io);
468 a8f48dcc blueswir1
469 0019ad53 blueswir1
        // Modem control
470 a8f48dcc blueswir1
        io = cpu_register_io_memory(0, slavio_mdm_mem_read,
471 a8f48dcc blueswir1
                                    slavio_mdm_mem_write, s);
472 a8f48dcc blueswir1
        cpu_register_physical_memory(base + MISC_MDM, MISC_SIZE, io);
473 0019ad53 blueswir1
474 0019ad53 blueswir1
        /* 16 bit registers */
475 0019ad53 blueswir1
        io = cpu_register_io_memory(0, slavio_led_mem_read,
476 0019ad53 blueswir1
                                    slavio_led_mem_write, s);
477 0019ad53 blueswir1
        /* ss600mp diag LEDs */
478 0019ad53 blueswir1
        cpu_register_physical_memory(base + MISC_LEDS, MISC_SIZE, io);
479 0019ad53 blueswir1
480 0019ad53 blueswir1
        /* 32 bit registers */
481 0019ad53 blueswir1
        io = cpu_register_io_memory(0, slavio_sysctrl_mem_read,
482 0019ad53 blueswir1
                                    slavio_sysctrl_mem_write, s);
483 0019ad53 blueswir1
        // System control
484 0019ad53 blueswir1
        cpu_register_physical_memory(base + MISC_SYS, SYSCTRL_SIZE, io);
485 0019ad53 blueswir1
    }
486 0019ad53 blueswir1
487 0019ad53 blueswir1
    // AUX 1 (Misc System Functions)
488 0019ad53 blueswir1
    if (aux1_base) {
489 0019ad53 blueswir1
        io = cpu_register_io_memory(0, slavio_aux1_mem_read,
490 0019ad53 blueswir1
                                    slavio_aux1_mem_write, s);
491 0019ad53 blueswir1
        cpu_register_physical_memory(aux1_base, MISC_SIZE, io);
492 0019ad53 blueswir1
    }
493 0019ad53 blueswir1
494 0019ad53 blueswir1
    // AUX 2 (Software Powerdown Control)
495 0019ad53 blueswir1
    if (aux2_base) {
496 0019ad53 blueswir1
        io = cpu_register_io_memory(0, slavio_aux2_mem_read,
497 0019ad53 blueswir1
                                    slavio_aux2_mem_write, s);
498 0019ad53 blueswir1
        cpu_register_physical_memory(aux2_base, MISC_SIZE, io);
499 0019ad53 blueswir1
    }
500 0019ad53 blueswir1
501 0019ad53 blueswir1
    // Power management (APC) XXX: not a Slavio device
502 0019ad53 blueswir1
    if (power_base) {
503 0019ad53 blueswir1
        io = cpu_register_io_memory(0, apc_mem_read, apc_mem_write, s);
504 0019ad53 blueswir1
        cpu_register_physical_memory(power_base, MISC_SIZE, io);
505 0019ad53 blueswir1
    }
506 bfa30a38 blueswir1
507 3475187d bellard
    s->irq = irq;
508 6d0c293d blueswir1
    s->cpu_halt = cpu_halt;
509 2be17ebd blueswir1
    *fdc_tc = &s->fdc_tc;
510 3475187d bellard
511 bfa30a38 blueswir1
    register_savevm("slavio_misc", base, 1, slavio_misc_save, slavio_misc_load,
512 bfa30a38 blueswir1
                    s);
513 3475187d bellard
    qemu_register_reset(slavio_misc_reset, s);
514 3475187d bellard
    slavio_misc_reset(s);
515 0019ad53 blueswir1
516 3475187d bellard
    return s;
517 3475187d bellard
}