Statistics
| Branch: | Revision:

root / hw / parallel.c @ 9c02f1a2

History | View | Annotate | Download (12.3 kB)

1 6508fe59 bellard
/*
2 6508fe59 bellard
 * QEMU Parallel PORT emulation
3 6508fe59 bellard
 * 
4 e57a8c0e bellard
 * Copyright (c) 2003-2005 Fabrice Bellard
5 5867c88a ths
 * Copyright (c) 2007 Marko Kohtala
6 6508fe59 bellard
 * 
7 6508fe59 bellard
 * Permission is hereby granted, free of charge, to any person obtaining a copy
8 6508fe59 bellard
 * of this software and associated documentation files (the "Software"), to deal
9 6508fe59 bellard
 * in the Software without restriction, including without limitation the rights
10 6508fe59 bellard
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11 6508fe59 bellard
 * copies of the Software, and to permit persons to whom the Software is
12 6508fe59 bellard
 * furnished to do so, subject to the following conditions:
13 6508fe59 bellard
 *
14 6508fe59 bellard
 * The above copyright notice and this permission notice shall be included in
15 6508fe59 bellard
 * all copies or substantial portions of the Software.
16 6508fe59 bellard
 *
17 6508fe59 bellard
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18 6508fe59 bellard
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19 6508fe59 bellard
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
20 6508fe59 bellard
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21 6508fe59 bellard
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22 6508fe59 bellard
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
23 6508fe59 bellard
 * THE SOFTWARE.
24 6508fe59 bellard
 */
25 6508fe59 bellard
#include "vl.h"
26 6508fe59 bellard
27 6508fe59 bellard
//#define DEBUG_PARALLEL
28 6508fe59 bellard
29 5867c88a ths
#ifdef DEBUG_PARALLEL
30 5867c88a ths
#define pdebug(fmt, arg...) printf("pp: " fmt, ##arg)
31 5867c88a ths
#else
32 5867c88a ths
#define pdebug(fmt, arg...) ((void)0)
33 5867c88a ths
#endif
34 5867c88a ths
35 5867c88a ths
#define PARA_REG_DATA 0
36 5867c88a ths
#define PARA_REG_STS 1
37 5867c88a ths
#define PARA_REG_CTR 2
38 5867c88a ths
#define PARA_REG_EPP_ADDR 3
39 5867c88a ths
#define PARA_REG_EPP_DATA 4
40 5867c88a ths
41 6508fe59 bellard
/*
42 6508fe59 bellard
 * These are the definitions for the Printer Status Register
43 6508fe59 bellard
 */
44 6508fe59 bellard
#define PARA_STS_BUSY        0x80        /* Busy complement */
45 6508fe59 bellard
#define PARA_STS_ACK        0x40        /* Acknowledge */
46 6508fe59 bellard
#define PARA_STS_PAPER        0x20        /* Out of paper */
47 6508fe59 bellard
#define PARA_STS_ONLINE        0x10        /* Online */
48 6508fe59 bellard
#define PARA_STS_ERROR        0x08        /* Error complement */
49 5867c88a ths
#define PARA_STS_TMOUT        0x01        /* EPP timeout */
50 6508fe59 bellard
51 6508fe59 bellard
/*
52 6508fe59 bellard
 * These are the definitions for the Printer Control Register
53 6508fe59 bellard
 */
54 5867c88a ths
#define PARA_CTR_DIR        0x20        /* Direction (1=read, 0=write) */
55 6508fe59 bellard
#define PARA_CTR_INTEN        0x10        /* IRQ Enable */
56 6508fe59 bellard
#define PARA_CTR_SELECT        0x08        /* Select In complement */
57 6508fe59 bellard
#define PARA_CTR_INIT        0x04        /* Initialize Printer complement */
58 6508fe59 bellard
#define PARA_CTR_AUTOLF        0x02        /* Auto linefeed complement */
59 6508fe59 bellard
#define PARA_CTR_STROBE        0x01        /* Strobe complement */
60 6508fe59 bellard
61 5867c88a ths
#define PARA_CTR_SIGNAL (PARA_CTR_SELECT|PARA_CTR_INIT|PARA_CTR_AUTOLF|PARA_CTR_STROBE)
62 5867c88a ths
63 6508fe59 bellard
struct ParallelState {
64 5867c88a ths
    uint8_t dataw;
65 5867c88a ths
    uint8_t datar;
66 5867c88a ths
    uint8_t status;
67 6508fe59 bellard
    uint8_t control;
68 d537cf6c pbrook
    qemu_irq irq;
69 6508fe59 bellard
    int irq_pending;
70 6508fe59 bellard
    CharDriverState *chr;
71 e57a8c0e bellard
    int hw_driver;
72 5867c88a ths
    int epp_timeout;
73 5867c88a ths
    uint32_t last_read_offset; /* For debugging */
74 6508fe59 bellard
};
75 6508fe59 bellard
76 6508fe59 bellard
static void parallel_update_irq(ParallelState *s)
77 6508fe59 bellard
{
78 6508fe59 bellard
    if (s->irq_pending)
79 d537cf6c pbrook
        qemu_irq_raise(s->irq);
80 6508fe59 bellard
    else
81 d537cf6c pbrook
        qemu_irq_lower(s->irq);
82 6508fe59 bellard
}
83 6508fe59 bellard
84 5867c88a ths
static void
85 5867c88a ths
parallel_ioport_write_sw(void *opaque, uint32_t addr, uint32_t val)
86 6508fe59 bellard
{
87 6508fe59 bellard
    ParallelState *s = opaque;
88 6508fe59 bellard
    
89 5867c88a ths
    pdebug("write addr=0x%02x val=0x%02x\n", addr, val);
90 5867c88a ths
91 5867c88a ths
    addr &= 7;
92 5867c88a ths
    switch(addr) {
93 5867c88a ths
    case PARA_REG_DATA:
94 5867c88a ths
        s->dataw = val;
95 5867c88a ths
        parallel_update_irq(s);
96 5867c88a ths
        break;
97 5867c88a ths
    case PARA_REG_CTR:
98 5867c88a ths
        if ((val & PARA_CTR_INIT) == 0 ) {
99 5867c88a ths
            s->status = PARA_STS_BUSY;
100 5867c88a ths
            s->status |= PARA_STS_ACK;
101 5867c88a ths
            s->status |= PARA_STS_ONLINE;
102 5867c88a ths
            s->status |= PARA_STS_ERROR;
103 5867c88a ths
        }
104 5867c88a ths
        else if (val & PARA_CTR_SELECT) {
105 5867c88a ths
            if (val & PARA_CTR_STROBE) {
106 5867c88a ths
                s->status &= ~PARA_STS_BUSY;
107 5867c88a ths
                if ((s->control & PARA_CTR_STROBE) == 0)
108 5867c88a ths
                    qemu_chr_write(s->chr, &s->dataw, 1);
109 5867c88a ths
            } else {
110 5867c88a ths
                if (s->control & PARA_CTR_INTEN) {
111 5867c88a ths
                    s->irq_pending = 1;
112 5867c88a ths
                }
113 5867c88a ths
            }
114 5867c88a ths
        }
115 5867c88a ths
        parallel_update_irq(s);
116 5867c88a ths
        s->control = val;
117 5867c88a ths
        break;
118 5867c88a ths
    }
119 5867c88a ths
}
120 5867c88a ths
121 5867c88a ths
static void parallel_ioport_write_hw(void *opaque, uint32_t addr, uint32_t val)
122 5867c88a ths
{
123 5867c88a ths
    ParallelState *s = opaque;
124 5867c88a ths
    uint8_t parm = val;
125 5867c88a ths
126 5867c88a ths
    /* Sometimes programs do several writes for timing purposes on old
127 5867c88a ths
       HW. Take care not to waste time on writes that do nothing. */
128 5867c88a ths
129 5867c88a ths
    s->last_read_offset = ~0U;
130 5867c88a ths
131 6508fe59 bellard
    addr &= 7;
132 6508fe59 bellard
    switch(addr) {
133 5867c88a ths
    case PARA_REG_DATA:
134 5867c88a ths
        if (s->dataw == val)
135 5867c88a ths
            return;
136 5867c88a ths
        pdebug("wd%02x\n", val);
137 5867c88a ths
        qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_WRITE_DATA, &parm);
138 5867c88a ths
        s->dataw = val;
139 6508fe59 bellard
        break;
140 5867c88a ths
    case PARA_REG_STS:
141 5867c88a ths
        pdebug("ws%02x\n", val);
142 5867c88a ths
        if (val & PARA_STS_TMOUT)
143 5867c88a ths
            s->epp_timeout = 0;
144 5867c88a ths
        break;
145 5867c88a ths
    case PARA_REG_CTR:
146 5867c88a ths
        val |= 0xc0;
147 5867c88a ths
        if (s->control == val)
148 5867c88a ths
            return;
149 5867c88a ths
        pdebug("wc%02x\n", val);
150 5867c88a ths
        qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_WRITE_CONTROL, &parm);
151 5867c88a ths
        s->control = val;
152 6508fe59 bellard
        break;
153 5867c88a ths
    case PARA_REG_EPP_ADDR:
154 5867c88a ths
        if ((s->control & (PARA_CTR_DIR|PARA_CTR_SIGNAL)) != PARA_CTR_INIT)
155 5867c88a ths
            /* Controls not correct for EPP address cycle, so do nothing */
156 5867c88a ths
            pdebug("wa%02x s\n", val);
157 5867c88a ths
        else {
158 5867c88a ths
            struct ParallelIOArg ioarg = { .buffer = &parm, .count = 1 };
159 5867c88a ths
            if (qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_EPP_WRITE_ADDR, &ioarg)) {
160 5867c88a ths
                s->epp_timeout = 1;
161 5867c88a ths
                pdebug("wa%02x t\n", val);
162 5867c88a ths
            }
163 5867c88a ths
            else
164 5867c88a ths
                pdebug("wa%02x\n", val);
165 5867c88a ths
        }
166 5867c88a ths
        break;
167 5867c88a ths
    case PARA_REG_EPP_DATA:
168 5867c88a ths
        if ((s->control & (PARA_CTR_DIR|PARA_CTR_SIGNAL)) != PARA_CTR_INIT)
169 5867c88a ths
            /* Controls not correct for EPP data cycle, so do nothing */
170 5867c88a ths
            pdebug("we%02x s\n", val);
171 5867c88a ths
        else {
172 5867c88a ths
            struct ParallelIOArg ioarg = { .buffer = &parm, .count = 1 };
173 5867c88a ths
            if (qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_EPP_WRITE, &ioarg)) {
174 5867c88a ths
                s->epp_timeout = 1;
175 5867c88a ths
                pdebug("we%02x t\n", val);
176 5867c88a ths
            }
177 5867c88a ths
            else
178 5867c88a ths
                pdebug("we%02x\n", val);
179 5867c88a ths
        }
180 5867c88a ths
        break;
181 5867c88a ths
    }
182 5867c88a ths
}
183 5867c88a ths
184 5867c88a ths
static void
185 5867c88a ths
parallel_ioport_eppdata_write_hw2(void *opaque, uint32_t addr, uint32_t val)
186 5867c88a ths
{
187 5867c88a ths
    ParallelState *s = opaque;
188 5867c88a ths
    uint16_t eppdata = cpu_to_le16(val);
189 5867c88a ths
    int err;
190 5867c88a ths
    struct ParallelIOArg ioarg = {
191 5867c88a ths
        .buffer = &eppdata, .count = sizeof(eppdata)
192 5867c88a ths
    };
193 5867c88a ths
    if ((s->control & (PARA_CTR_DIR|PARA_CTR_SIGNAL)) != PARA_CTR_INIT) {
194 5867c88a ths
        /* Controls not correct for EPP data cycle, so do nothing */
195 5867c88a ths
        pdebug("we%04x s\n", val);
196 5867c88a ths
        return;
197 5867c88a ths
    }
198 5867c88a ths
    err = qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_EPP_WRITE, &ioarg);
199 5867c88a ths
    if (err) {
200 5867c88a ths
        s->epp_timeout = 1;
201 5867c88a ths
        pdebug("we%04x t\n", val);
202 5867c88a ths
    }
203 5867c88a ths
    else
204 5867c88a ths
        pdebug("we%04x\n", val);
205 5867c88a ths
}
206 5867c88a ths
207 5867c88a ths
static void
208 5867c88a ths
parallel_ioport_eppdata_write_hw4(void *opaque, uint32_t addr, uint32_t val)
209 5867c88a ths
{
210 5867c88a ths
    ParallelState *s = opaque;
211 5867c88a ths
    uint32_t eppdata = cpu_to_le32(val);
212 5867c88a ths
    int err;
213 5867c88a ths
    struct ParallelIOArg ioarg = {
214 5867c88a ths
        .buffer = &eppdata, .count = sizeof(eppdata)
215 5867c88a ths
    };
216 5867c88a ths
    if ((s->control & (PARA_CTR_DIR|PARA_CTR_SIGNAL)) != PARA_CTR_INIT) {
217 5867c88a ths
        /* Controls not correct for EPP data cycle, so do nothing */
218 5867c88a ths
        pdebug("we%08x s\n", val);
219 5867c88a ths
        return;
220 5867c88a ths
    }
221 5867c88a ths
    err = qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_EPP_WRITE, &ioarg);
222 5867c88a ths
    if (err) {
223 5867c88a ths
        s->epp_timeout = 1;
224 5867c88a ths
        pdebug("we%08x t\n", val);
225 6508fe59 bellard
    }
226 5867c88a ths
    else
227 5867c88a ths
        pdebug("we%08x\n", val);
228 6508fe59 bellard
}
229 6508fe59 bellard
230 5867c88a ths
static uint32_t parallel_ioport_read_sw(void *opaque, uint32_t addr)
231 6508fe59 bellard
{
232 6508fe59 bellard
    ParallelState *s = opaque;
233 6508fe59 bellard
    uint32_t ret = 0xff;
234 6508fe59 bellard
235 6508fe59 bellard
    addr &= 7;
236 6508fe59 bellard
    switch(addr) {
237 5867c88a ths
    case PARA_REG_DATA:
238 5867c88a ths
        if (s->control & PARA_CTR_DIR)
239 5867c88a ths
            ret = s->datar;
240 5867c88a ths
        else
241 5867c88a ths
            ret = s->dataw;
242 6508fe59 bellard
        break;
243 5867c88a ths
    case PARA_REG_STS:
244 5867c88a ths
        ret = s->status;
245 5867c88a ths
        s->irq_pending = 0;
246 5867c88a ths
        if ((s->status & PARA_STS_BUSY) == 0 && (s->control & PARA_CTR_STROBE) == 0) {
247 5867c88a ths
            /* XXX Fixme: wait 5 microseconds */
248 5867c88a ths
            if (s->status & PARA_STS_ACK)
249 5867c88a ths
                s->status &= ~PARA_STS_ACK;
250 5867c88a ths
            else {
251 5867c88a ths
                /* XXX Fixme: wait 5 microseconds */
252 5867c88a ths
                s->status |= PARA_STS_ACK;
253 5867c88a ths
                s->status |= PARA_STS_BUSY;
254 5867c88a ths
            }
255 5867c88a ths
        }
256 5867c88a ths
        parallel_update_irq(s);
257 6508fe59 bellard
        break;
258 5867c88a ths
    case PARA_REG_CTR:
259 6508fe59 bellard
        ret = s->control;
260 6508fe59 bellard
        break;
261 6508fe59 bellard
    }
262 5867c88a ths
    pdebug("read addr=0x%02x val=0x%02x\n", addr, ret);
263 5867c88a ths
    return ret;
264 5867c88a ths
}
265 5867c88a ths
266 5867c88a ths
static uint32_t parallel_ioport_read_hw(void *opaque, uint32_t addr)
267 5867c88a ths
{
268 5867c88a ths
    ParallelState *s = opaque;
269 5867c88a ths
    uint8_t ret = 0xff;
270 5867c88a ths
    addr &= 7;
271 5867c88a ths
    switch(addr) {
272 5867c88a ths
    case PARA_REG_DATA:
273 5867c88a ths
        qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_READ_DATA, &ret);
274 5867c88a ths
        if (s->last_read_offset != addr || s->datar != ret)
275 5867c88a ths
            pdebug("rd%02x\n", ret);
276 5867c88a ths
        s->datar = ret;
277 5867c88a ths
        break;
278 5867c88a ths
    case PARA_REG_STS:
279 5867c88a ths
        qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_READ_STATUS, &ret);
280 5867c88a ths
        ret &= ~PARA_STS_TMOUT;
281 5867c88a ths
        if (s->epp_timeout)
282 5867c88a ths
            ret |= PARA_STS_TMOUT;
283 5867c88a ths
        if (s->last_read_offset != addr || s->status != ret)
284 5867c88a ths
            pdebug("rs%02x\n", ret);
285 5867c88a ths
        s->status = ret;
286 5867c88a ths
        break;
287 5867c88a ths
    case PARA_REG_CTR:
288 5867c88a ths
        /* s->control has some bits fixed to 1. It is zero only when
289 5867c88a ths
           it has not been yet written to.  */
290 5867c88a ths
        if (s->control == 0) {
291 5867c88a ths
            qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_READ_CONTROL, &ret);
292 5867c88a ths
            if (s->last_read_offset != addr)
293 5867c88a ths
                pdebug("rc%02x\n", ret);
294 5867c88a ths
            s->control = ret;
295 5867c88a ths
        }
296 5867c88a ths
        else {
297 5867c88a ths
            ret = s->control;
298 5867c88a ths
            if (s->last_read_offset != addr)
299 5867c88a ths
                pdebug("rc%02x\n", ret);
300 5867c88a ths
        }
301 5867c88a ths
        break;
302 5867c88a ths
    case PARA_REG_EPP_ADDR:
303 5867c88a ths
        if ((s->control & (PARA_CTR_DIR|PARA_CTR_SIGNAL)) != (PARA_CTR_DIR|PARA_CTR_INIT))
304 5867c88a ths
            /* Controls not correct for EPP addr cycle, so do nothing */
305 5867c88a ths
            pdebug("ra%02x s\n", ret);
306 5867c88a ths
        else {
307 5867c88a ths
            struct ParallelIOArg ioarg = { .buffer = &ret, .count = 1 };
308 5867c88a ths
            if (qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_EPP_READ_ADDR, &ioarg)) {
309 5867c88a ths
                s->epp_timeout = 1;
310 5867c88a ths
                pdebug("ra%02x t\n", ret);
311 5867c88a ths
            }
312 5867c88a ths
            else
313 5867c88a ths
                pdebug("ra%02x\n", ret);
314 5867c88a ths
        }
315 5867c88a ths
        break;
316 5867c88a ths
    case PARA_REG_EPP_DATA:
317 5867c88a ths
        if ((s->control & (PARA_CTR_DIR|PARA_CTR_SIGNAL)) != (PARA_CTR_DIR|PARA_CTR_INIT))
318 5867c88a ths
            /* Controls not correct for EPP data cycle, so do nothing */
319 5867c88a ths
            pdebug("re%02x s\n", ret);
320 5867c88a ths
        else {
321 5867c88a ths
            struct ParallelIOArg ioarg = { .buffer = &ret, .count = 1 };
322 5867c88a ths
            if (qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_EPP_READ, &ioarg)) {
323 5867c88a ths
                s->epp_timeout = 1;
324 5867c88a ths
                pdebug("re%02x t\n", ret);
325 5867c88a ths
            }
326 5867c88a ths
            else
327 5867c88a ths
                pdebug("re%02x\n", ret);
328 5867c88a ths
        }
329 5867c88a ths
        break;
330 5867c88a ths
    }
331 5867c88a ths
    s->last_read_offset = addr;
332 5867c88a ths
    return ret;
333 5867c88a ths
}
334 5867c88a ths
335 5867c88a ths
static uint32_t
336 5867c88a ths
parallel_ioport_eppdata_read_hw2(void *opaque, uint32_t addr)
337 5867c88a ths
{
338 5867c88a ths
    ParallelState *s = opaque;
339 5867c88a ths
    uint32_t ret;
340 5867c88a ths
    uint16_t eppdata = ~0;
341 5867c88a ths
    int err;
342 5867c88a ths
    struct ParallelIOArg ioarg = {
343 5867c88a ths
        .buffer = &eppdata, .count = sizeof(eppdata)
344 5867c88a ths
    };
345 5867c88a ths
    if ((s->control & (PARA_CTR_DIR|PARA_CTR_SIGNAL)) != (PARA_CTR_DIR|PARA_CTR_INIT)) {
346 5867c88a ths
        /* Controls not correct for EPP data cycle, so do nothing */
347 5867c88a ths
        pdebug("re%04x s\n", eppdata);
348 5867c88a ths
        return eppdata;
349 5867c88a ths
    }
350 5867c88a ths
    err = qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_EPP_READ, &ioarg);
351 5867c88a ths
    ret = le16_to_cpu(eppdata);
352 5867c88a ths
353 5867c88a ths
    if (err) {
354 5867c88a ths
        s->epp_timeout = 1;
355 5867c88a ths
        pdebug("re%04x t\n", ret);
356 5867c88a ths
    }
357 5867c88a ths
    else
358 5867c88a ths
        pdebug("re%04x\n", ret);
359 5867c88a ths
    return ret;
360 5867c88a ths
}
361 5867c88a ths
362 5867c88a ths
static uint32_t
363 5867c88a ths
parallel_ioport_eppdata_read_hw4(void *opaque, uint32_t addr)
364 5867c88a ths
{
365 5867c88a ths
    ParallelState *s = opaque;
366 5867c88a ths
    uint32_t ret;
367 5867c88a ths
    uint32_t eppdata = ~0U;
368 5867c88a ths
    int err;
369 5867c88a ths
    struct ParallelIOArg ioarg = {
370 5867c88a ths
        .buffer = &eppdata, .count = sizeof(eppdata)
371 5867c88a ths
    };
372 5867c88a ths
    if ((s->control & (PARA_CTR_DIR|PARA_CTR_SIGNAL)) != (PARA_CTR_DIR|PARA_CTR_INIT)) {
373 5867c88a ths
        /* Controls not correct for EPP data cycle, so do nothing */
374 5867c88a ths
        pdebug("re%08x s\n", eppdata);
375 5867c88a ths
        return eppdata;
376 5867c88a ths
    }
377 5867c88a ths
    err = qemu_chr_ioctl(s->chr, CHR_IOCTL_PP_EPP_READ, &ioarg);
378 5867c88a ths
    ret = le32_to_cpu(eppdata);
379 5867c88a ths
380 5867c88a ths
    if (err) {
381 5867c88a ths
        s->epp_timeout = 1;
382 5867c88a ths
        pdebug("re%08x t\n", ret);
383 5867c88a ths
    }
384 5867c88a ths
    else
385 5867c88a ths
        pdebug("re%08x\n", ret);
386 5867c88a ths
    return ret;
387 5867c88a ths
}
388 5867c88a ths
389 5867c88a ths
static void parallel_ioport_ecp_write(void *opaque, uint32_t addr, uint32_t val)
390 5867c88a ths
{
391 5867c88a ths
    addr &= 7;
392 5867c88a ths
    pdebug("wecp%d=%02x\n", addr, val);
393 5867c88a ths
}
394 5867c88a ths
395 5867c88a ths
static uint32_t parallel_ioport_ecp_read(void *opaque, uint32_t addr)
396 5867c88a ths
{
397 5867c88a ths
    uint8_t ret = 0xff;
398 5867c88a ths
    addr &= 7;
399 5867c88a ths
    pdebug("recp%d:%02x\n", addr, ret);
400 6508fe59 bellard
    return ret;
401 6508fe59 bellard
}
402 6508fe59 bellard
403 6508fe59 bellard
/* If fd is zero, it means that the parallel device uses the console */
404 d537cf6c pbrook
ParallelState *parallel_init(int base, qemu_irq irq, CharDriverState *chr)
405 6508fe59 bellard
{
406 6508fe59 bellard
    ParallelState *s;
407 e57a8c0e bellard
    uint8_t dummy;
408 6508fe59 bellard
409 6508fe59 bellard
    s = qemu_mallocz(sizeof(ParallelState));
410 6508fe59 bellard
    if (!s)
411 6508fe59 bellard
        return NULL;
412 5867c88a ths
    s->datar = ~0;
413 5867c88a ths
    s->dataw = ~0;
414 6508fe59 bellard
    s->status = PARA_STS_BUSY;
415 6508fe59 bellard
    s->status |= PARA_STS_ACK;
416 6508fe59 bellard
    s->status |= PARA_STS_ONLINE;
417 6508fe59 bellard
    s->status |= PARA_STS_ERROR;
418 6508fe59 bellard
    s->control = PARA_CTR_SELECT;
419 6508fe59 bellard
    s->control |= PARA_CTR_INIT;
420 5867c88a ths
    s->irq = irq;
421 5867c88a ths
    s->irq_pending = 0;
422 5867c88a ths
    s->chr = chr;
423 5867c88a ths
    s->hw_driver = 0;
424 5867c88a ths
    s->epp_timeout = 0;
425 5867c88a ths
    s->last_read_offset = ~0U;
426 6508fe59 bellard
427 5867c88a ths
    if (qemu_chr_ioctl(chr, CHR_IOCTL_PP_READ_STATUS, &dummy) == 0) {
428 5867c88a ths
        s->hw_driver = 1;
429 5867c88a ths
        s->status = dummy;
430 5867c88a ths
    }
431 5867c88a ths
432 5867c88a ths
    if (s->hw_driver) {
433 5867c88a ths
        register_ioport_write(base, 8, 1, parallel_ioport_write_hw, s);
434 5867c88a ths
        register_ioport_read(base, 8, 1, parallel_ioport_read_hw, s);
435 5867c88a ths
        register_ioport_write(base+4, 1, 2, parallel_ioport_eppdata_write_hw2, s);
436 5867c88a ths
        register_ioport_read(base+4, 1, 2, parallel_ioport_eppdata_read_hw2, s);
437 5867c88a ths
        register_ioport_write(base+4, 1, 4, parallel_ioport_eppdata_write_hw4, s);
438 5867c88a ths
        register_ioport_read(base+4, 1, 4, parallel_ioport_eppdata_read_hw4, s);
439 5867c88a ths
        register_ioport_write(base+0x400, 8, 1, parallel_ioport_ecp_write, s);
440 5867c88a ths
        register_ioport_read(base+0x400, 8, 1, parallel_ioport_ecp_read, s);
441 5867c88a ths
    }
442 5867c88a ths
    else {
443 5867c88a ths
        register_ioport_write(base, 8, 1, parallel_ioport_write_sw, s);
444 5867c88a ths
        register_ioport_read(base, 8, 1, parallel_ioport_read_sw, s);
445 5867c88a ths
    }
446 6508fe59 bellard
    return s;
447 6508fe59 bellard
}