xref: /openbmc/qemu/hw/misc/macio/mac_dbdma.c (revision 500eb6db)
1 /*
2  * PowerMac descriptor-based DMA emulation
3  *
4  * Copyright (c) 2005-2007 Fabrice Bellard
5  * Copyright (c) 2007 Jocelyn Mayer
6  * Copyright (c) 2009 Laurent Vivier
7  *
8  * some parts from linux-2.6.28, arch/powerpc/include/asm/dbdma.h
9  *
10  *   Definitions for using the Apple Descriptor-Based DMA controller
11  *   in Power Macintosh computers.
12  *
13  *   Copyright (C) 1996 Paul Mackerras.
14  *
15  * some parts from mol 0.9.71
16  *
17  *   Descriptor based DMA emulation
18  *
19  *   Copyright (C) 1998-2004 Samuel Rydh (samuel@ibrium.se)
20  *
21  * Permission is hereby granted, free of charge, to any person obtaining a copy
22  * of this software and associated documentation files (the "Software"), to deal
23  * in the Software without restriction, including without limitation the rights
24  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
25  * copies of the Software, and to permit persons to whom the Software is
26  * furnished to do so, subject to the following conditions:
27  *
28  * The above copyright notice and this permission notice shall be included in
29  * all copies or substantial portions of the Software.
30  *
31  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
32  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
33  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
34  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
35  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
36  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
37  * THE SOFTWARE.
38  */
39 
40 #include "qemu/osdep.h"
41 #include "hw/hw.h"
42 #include "hw/ppc/mac_dbdma.h"
43 #include "qemu/main-loop.h"
44 #include "qemu/module.h"
45 #include "qemu/log.h"
46 #include "sysemu/dma.h"
47 
48 /* debug DBDMA */
49 #define DEBUG_DBDMA 0
50 #define DEBUG_DBDMA_CHANMASK ((1ull << DBDMA_CHANNELS) - 1)
51 
52 #define DBDMA_DPRINTF(fmt, ...) do { \
53     if (DEBUG_DBDMA) { \
54         printf("DBDMA: " fmt , ## __VA_ARGS__); \
55     } \
56 } while (0)
57 
58 #define DBDMA_DPRINTFCH(ch, fmt, ...) do { \
59     if (DEBUG_DBDMA) { \
60         if ((1ul << (ch)->channel) & DEBUG_DBDMA_CHANMASK) { \
61             printf("DBDMA[%02x]: " fmt , (ch)->channel, ## __VA_ARGS__); \
62         } \
63     } \
64 } while (0)
65 
66 /*
67  */
68 
69 static DBDMAState *dbdma_from_ch(DBDMA_channel *ch)
70 {
71     return container_of(ch, DBDMAState, channels[ch->channel]);
72 }
73 
74 #if DEBUG_DBDMA
75 static void dump_dbdma_cmd(DBDMA_channel *ch, dbdma_cmd *cmd)
76 {
77     DBDMA_DPRINTFCH(ch, "dbdma_cmd %p\n", cmd);
78     DBDMA_DPRINTFCH(ch, "    req_count 0x%04x\n", le16_to_cpu(cmd->req_count));
79     DBDMA_DPRINTFCH(ch, "    command 0x%04x\n", le16_to_cpu(cmd->command));
80     DBDMA_DPRINTFCH(ch, "    phy_addr 0x%08x\n", le32_to_cpu(cmd->phy_addr));
81     DBDMA_DPRINTFCH(ch, "    cmd_dep 0x%08x\n", le32_to_cpu(cmd->cmd_dep));
82     DBDMA_DPRINTFCH(ch, "    res_count 0x%04x\n", le16_to_cpu(cmd->res_count));
83     DBDMA_DPRINTFCH(ch, "    xfer_status 0x%04x\n",
84                     le16_to_cpu(cmd->xfer_status));
85 }
86 #else
87 static void dump_dbdma_cmd(DBDMA_channel *ch, dbdma_cmd *cmd)
88 {
89 }
90 #endif
91 static void dbdma_cmdptr_load(DBDMA_channel *ch)
92 {
93     DBDMA_DPRINTFCH(ch, "dbdma_cmdptr_load 0x%08x\n",
94                     ch->regs[DBDMA_CMDPTR_LO]);
95     dma_memory_read(&address_space_memory, ch->regs[DBDMA_CMDPTR_LO],
96                     &ch->current, sizeof(dbdma_cmd));
97 }
98 
99 static void dbdma_cmdptr_save(DBDMA_channel *ch)
100 {
101     DBDMA_DPRINTFCH(ch, "-> update 0x%08x stat=0x%08x, res=0x%04x\n",
102                     ch->regs[DBDMA_CMDPTR_LO],
103                     le16_to_cpu(ch->current.xfer_status),
104                     le16_to_cpu(ch->current.res_count));
105     dma_memory_write(&address_space_memory, ch->regs[DBDMA_CMDPTR_LO],
106                      &ch->current, sizeof(dbdma_cmd));
107 }
108 
109 static void kill_channel(DBDMA_channel *ch)
110 {
111     DBDMA_DPRINTFCH(ch, "kill_channel\n");
112 
113     ch->regs[DBDMA_STATUS] |= DEAD;
114     ch->regs[DBDMA_STATUS] &= ~ACTIVE;
115 
116     qemu_irq_raise(ch->irq);
117 }
118 
119 static void conditional_interrupt(DBDMA_channel *ch)
120 {
121     dbdma_cmd *current = &ch->current;
122     uint16_t intr;
123     uint16_t sel_mask, sel_value;
124     uint32_t status;
125     int cond;
126 
127     DBDMA_DPRINTFCH(ch, "%s\n", __func__);
128 
129     intr = le16_to_cpu(current->command) & INTR_MASK;
130 
131     switch(intr) {
132     case INTR_NEVER:  /* don't interrupt */
133         return;
134     case INTR_ALWAYS: /* always interrupt */
135         qemu_irq_raise(ch->irq);
136         DBDMA_DPRINTFCH(ch, "%s: raise\n", __func__);
137         return;
138     }
139 
140     status = ch->regs[DBDMA_STATUS] & DEVSTAT;
141 
142     sel_mask = (ch->regs[DBDMA_INTR_SEL] >> 16) & 0x0f;
143     sel_value = ch->regs[DBDMA_INTR_SEL] & 0x0f;
144 
145     cond = (status & sel_mask) == (sel_value & sel_mask);
146 
147     switch(intr) {
148     case INTR_IFSET:  /* intr if condition bit is 1 */
149         if (cond) {
150             qemu_irq_raise(ch->irq);
151             DBDMA_DPRINTFCH(ch, "%s: raise\n", __func__);
152         }
153         return;
154     case INTR_IFCLR:  /* intr if condition bit is 0 */
155         if (!cond) {
156             qemu_irq_raise(ch->irq);
157             DBDMA_DPRINTFCH(ch, "%s: raise\n", __func__);
158         }
159         return;
160     }
161 }
162 
163 static int conditional_wait(DBDMA_channel *ch)
164 {
165     dbdma_cmd *current = &ch->current;
166     uint16_t wait;
167     uint16_t sel_mask, sel_value;
168     uint32_t status;
169     int cond;
170     int res = 0;
171 
172     wait = le16_to_cpu(current->command) & WAIT_MASK;
173     switch(wait) {
174     case WAIT_NEVER:  /* don't wait */
175         return 0;
176     case WAIT_ALWAYS: /* always wait */
177         DBDMA_DPRINTFCH(ch, "  [WAIT_ALWAYS]\n");
178         return 1;
179     }
180 
181     status = ch->regs[DBDMA_STATUS] & DEVSTAT;
182 
183     sel_mask = (ch->regs[DBDMA_WAIT_SEL] >> 16) & 0x0f;
184     sel_value = ch->regs[DBDMA_WAIT_SEL] & 0x0f;
185 
186     cond = (status & sel_mask) == (sel_value & sel_mask);
187 
188     switch(wait) {
189     case WAIT_IFSET:  /* wait if condition bit is 1 */
190         if (cond) {
191             res = 1;
192         }
193         DBDMA_DPRINTFCH(ch, "  [WAIT_IFSET=%d]\n", res);
194         break;
195     case WAIT_IFCLR:  /* wait if condition bit is 0 */
196         if (!cond) {
197             res = 1;
198         }
199         DBDMA_DPRINTFCH(ch, "  [WAIT_IFCLR=%d]\n", res);
200         break;
201     }
202     return res;
203 }
204 
205 static void next(DBDMA_channel *ch)
206 {
207     uint32_t cp;
208 
209     ch->regs[DBDMA_STATUS] &= ~BT;
210 
211     cp = ch->regs[DBDMA_CMDPTR_LO];
212     ch->regs[DBDMA_CMDPTR_LO] = cp + sizeof(dbdma_cmd);
213     dbdma_cmdptr_load(ch);
214 }
215 
216 static void branch(DBDMA_channel *ch)
217 {
218     dbdma_cmd *current = &ch->current;
219 
220     ch->regs[DBDMA_CMDPTR_LO] = le32_to_cpu(current->cmd_dep);
221     ch->regs[DBDMA_STATUS] |= BT;
222     dbdma_cmdptr_load(ch);
223 }
224 
225 static void conditional_branch(DBDMA_channel *ch)
226 {
227     dbdma_cmd *current = &ch->current;
228     uint16_t br;
229     uint16_t sel_mask, sel_value;
230     uint32_t status;
231     int cond;
232 
233     /* check if we must branch */
234 
235     br = le16_to_cpu(current->command) & BR_MASK;
236 
237     switch(br) {
238     case BR_NEVER:  /* don't branch */
239         next(ch);
240         return;
241     case BR_ALWAYS: /* always branch */
242         DBDMA_DPRINTFCH(ch, "  [BR_ALWAYS]\n");
243         branch(ch);
244         return;
245     }
246 
247     status = ch->regs[DBDMA_STATUS] & DEVSTAT;
248 
249     sel_mask = (ch->regs[DBDMA_BRANCH_SEL] >> 16) & 0x0f;
250     sel_value = ch->regs[DBDMA_BRANCH_SEL] & 0x0f;
251 
252     cond = (status & sel_mask) == (sel_value & sel_mask);
253 
254     switch(br) {
255     case BR_IFSET:  /* branch if condition bit is 1 */
256         if (cond) {
257             DBDMA_DPRINTFCH(ch, "  [BR_IFSET = 1]\n");
258             branch(ch);
259         } else {
260             DBDMA_DPRINTFCH(ch, "  [BR_IFSET = 0]\n");
261             next(ch);
262         }
263         return;
264     case BR_IFCLR:  /* branch if condition bit is 0 */
265         if (!cond) {
266             DBDMA_DPRINTFCH(ch, "  [BR_IFCLR = 1]\n");
267             branch(ch);
268         } else {
269             DBDMA_DPRINTFCH(ch, "  [BR_IFCLR = 0]\n");
270             next(ch);
271         }
272         return;
273     }
274 }
275 
276 static void channel_run(DBDMA_channel *ch);
277 
278 static void dbdma_end(DBDMA_io *io)
279 {
280     DBDMA_channel *ch = io->channel;
281     dbdma_cmd *current = &ch->current;
282 
283     DBDMA_DPRINTFCH(ch, "%s\n", __func__);
284 
285     if (conditional_wait(ch))
286         goto wait;
287 
288     current->xfer_status = cpu_to_le16(ch->regs[DBDMA_STATUS]);
289     current->res_count = cpu_to_le16(io->len);
290     dbdma_cmdptr_save(ch);
291     if (io->is_last)
292         ch->regs[DBDMA_STATUS] &= ~FLUSH;
293 
294     conditional_interrupt(ch);
295     conditional_branch(ch);
296 
297 wait:
298     /* Indicate that we're ready for a new DMA round */
299     ch->io.processing = false;
300 
301     if ((ch->regs[DBDMA_STATUS] & RUN) &&
302         (ch->regs[DBDMA_STATUS] & ACTIVE))
303         channel_run(ch);
304 }
305 
306 static void start_output(DBDMA_channel *ch, int key, uint32_t addr,
307                         uint16_t req_count, int is_last)
308 {
309     DBDMA_DPRINTFCH(ch, "start_output\n");
310 
311     /* KEY_REGS, KEY_DEVICE and KEY_STREAM
312      * are not implemented in the mac-io chip
313      */
314 
315     DBDMA_DPRINTFCH(ch, "addr 0x%x key 0x%x\n", addr, key);
316     if (!addr || key > KEY_STREAM3) {
317         kill_channel(ch);
318         return;
319     }
320 
321     ch->io.addr = addr;
322     ch->io.len = req_count;
323     ch->io.is_last = is_last;
324     ch->io.dma_end = dbdma_end;
325     ch->io.is_dma_out = 1;
326     ch->io.processing = true;
327     if (ch->rw) {
328         ch->rw(&ch->io);
329     }
330 }
331 
332 static void start_input(DBDMA_channel *ch, int key, uint32_t addr,
333                        uint16_t req_count, int is_last)
334 {
335     DBDMA_DPRINTFCH(ch, "start_input\n");
336 
337     /* KEY_REGS, KEY_DEVICE and KEY_STREAM
338      * are not implemented in the mac-io chip
339      */
340 
341     DBDMA_DPRINTFCH(ch, "addr 0x%x key 0x%x\n", addr, key);
342     if (!addr || key > KEY_STREAM3) {
343         kill_channel(ch);
344         return;
345     }
346 
347     ch->io.addr = addr;
348     ch->io.len = req_count;
349     ch->io.is_last = is_last;
350     ch->io.dma_end = dbdma_end;
351     ch->io.is_dma_out = 0;
352     ch->io.processing = true;
353     if (ch->rw) {
354         ch->rw(&ch->io);
355     }
356 }
357 
358 static void load_word(DBDMA_channel *ch, int key, uint32_t addr,
359                      uint16_t len)
360 {
361     dbdma_cmd *current = &ch->current;
362 
363     DBDMA_DPRINTFCH(ch, "load_word %d bytes, addr=%08x\n", len, addr);
364 
365     /* only implements KEY_SYSTEM */
366 
367     if (key != KEY_SYSTEM) {
368         printf("DBDMA: LOAD_WORD, unimplemented key %x\n", key);
369         kill_channel(ch);
370         return;
371     }
372 
373     dma_memory_read(&address_space_memory, addr, &current->cmd_dep, len);
374 
375     if (conditional_wait(ch))
376         goto wait;
377 
378     current->xfer_status = cpu_to_le16(ch->regs[DBDMA_STATUS]);
379     dbdma_cmdptr_save(ch);
380     ch->regs[DBDMA_STATUS] &= ~FLUSH;
381 
382     conditional_interrupt(ch);
383     next(ch);
384 
385 wait:
386     DBDMA_kick(dbdma_from_ch(ch));
387 }
388 
389 static void store_word(DBDMA_channel *ch, int key, uint32_t addr,
390                       uint16_t len)
391 {
392     dbdma_cmd *current = &ch->current;
393 
394     DBDMA_DPRINTFCH(ch, "store_word %d bytes, addr=%08x pa=%x\n",
395                     len, addr, le32_to_cpu(current->cmd_dep));
396 
397     /* only implements KEY_SYSTEM */
398 
399     if (key != KEY_SYSTEM) {
400         printf("DBDMA: STORE_WORD, unimplemented key %x\n", key);
401         kill_channel(ch);
402         return;
403     }
404 
405     dma_memory_write(&address_space_memory, addr, &current->cmd_dep, len);
406 
407     if (conditional_wait(ch))
408         goto wait;
409 
410     current->xfer_status = cpu_to_le16(ch->regs[DBDMA_STATUS]);
411     dbdma_cmdptr_save(ch);
412     ch->regs[DBDMA_STATUS] &= ~FLUSH;
413 
414     conditional_interrupt(ch);
415     next(ch);
416 
417 wait:
418     DBDMA_kick(dbdma_from_ch(ch));
419 }
420 
421 static void nop(DBDMA_channel *ch)
422 {
423     dbdma_cmd *current = &ch->current;
424 
425     if (conditional_wait(ch))
426         goto wait;
427 
428     current->xfer_status = cpu_to_le16(ch->regs[DBDMA_STATUS]);
429     dbdma_cmdptr_save(ch);
430 
431     conditional_interrupt(ch);
432     conditional_branch(ch);
433 
434 wait:
435     DBDMA_kick(dbdma_from_ch(ch));
436 }
437 
438 static void stop(DBDMA_channel *ch)
439 {
440     ch->regs[DBDMA_STATUS] &= ~(ACTIVE);
441 
442     /* the stop command does not increment command pointer */
443 }
444 
445 static void channel_run(DBDMA_channel *ch)
446 {
447     dbdma_cmd *current = &ch->current;
448     uint16_t cmd, key;
449     uint16_t req_count;
450     uint32_t phy_addr;
451 
452     DBDMA_DPRINTFCH(ch, "channel_run\n");
453     dump_dbdma_cmd(ch, current);
454 
455     /* clear WAKE flag at command fetch */
456 
457     ch->regs[DBDMA_STATUS] &= ~WAKE;
458 
459     cmd = le16_to_cpu(current->command) & COMMAND_MASK;
460 
461     switch (cmd) {
462     case DBDMA_NOP:
463         nop(ch);
464         return;
465 
466     case DBDMA_STOP:
467         stop(ch);
468         return;
469     }
470 
471     key = le16_to_cpu(current->command) & 0x0700;
472     req_count = le16_to_cpu(current->req_count);
473     phy_addr = le32_to_cpu(current->phy_addr);
474 
475     if (key == KEY_STREAM4) {
476         printf("command %x, invalid key 4\n", cmd);
477         kill_channel(ch);
478         return;
479     }
480 
481     switch (cmd) {
482     case OUTPUT_MORE:
483         DBDMA_DPRINTFCH(ch, "* OUTPUT_MORE *\n");
484         start_output(ch, key, phy_addr, req_count, 0);
485         return;
486 
487     case OUTPUT_LAST:
488         DBDMA_DPRINTFCH(ch, "* OUTPUT_LAST *\n");
489         start_output(ch, key, phy_addr, req_count, 1);
490         return;
491 
492     case INPUT_MORE:
493         DBDMA_DPRINTFCH(ch, "* INPUT_MORE *\n");
494         start_input(ch, key, phy_addr, req_count, 0);
495         return;
496 
497     case INPUT_LAST:
498         DBDMA_DPRINTFCH(ch, "* INPUT_LAST *\n");
499         start_input(ch, key, phy_addr, req_count, 1);
500         return;
501     }
502 
503     if (key < KEY_REGS) {
504         printf("command %x, invalid key %x\n", cmd, key);
505         key = KEY_SYSTEM;
506     }
507 
508     /* for LOAD_WORD and STORE_WORD, req_count is on 3 bits
509      * and BRANCH is invalid
510      */
511 
512     req_count = req_count & 0x0007;
513     if (req_count & 0x4) {
514         req_count = 4;
515         phy_addr &= ~3;
516     } else if (req_count & 0x2) {
517         req_count = 2;
518         phy_addr &= ~1;
519     } else
520         req_count = 1;
521 
522     switch (cmd) {
523     case LOAD_WORD:
524         DBDMA_DPRINTFCH(ch, "* LOAD_WORD *\n");
525         load_word(ch, key, phy_addr, req_count);
526         return;
527 
528     case STORE_WORD:
529         DBDMA_DPRINTFCH(ch, "* STORE_WORD *\n");
530         store_word(ch, key, phy_addr, req_count);
531         return;
532     }
533 }
534 
535 static void DBDMA_run(DBDMAState *s)
536 {
537     int channel;
538 
539     for (channel = 0; channel < DBDMA_CHANNELS; channel++) {
540         DBDMA_channel *ch = &s->channels[channel];
541         uint32_t status = ch->regs[DBDMA_STATUS];
542         if (!ch->io.processing && (status & RUN) && (status & ACTIVE)) {
543             channel_run(ch);
544         }
545     }
546 }
547 
548 static void DBDMA_run_bh(void *opaque)
549 {
550     DBDMAState *s = opaque;
551 
552     DBDMA_DPRINTF("-> DBDMA_run_bh\n");
553     DBDMA_run(s);
554     DBDMA_DPRINTF("<- DBDMA_run_bh\n");
555 }
556 
557 void DBDMA_kick(DBDMAState *dbdma)
558 {
559     qemu_bh_schedule(dbdma->bh);
560 }
561 
562 void DBDMA_register_channel(void *dbdma, int nchan, qemu_irq irq,
563                             DBDMA_rw rw, DBDMA_flush flush,
564                             void *opaque)
565 {
566     DBDMAState *s = dbdma;
567     DBDMA_channel *ch = &s->channels[nchan];
568 
569     DBDMA_DPRINTFCH(ch, "DBDMA_register_channel 0x%x\n", nchan);
570 
571     assert(rw);
572     assert(flush);
573 
574     ch->irq = irq;
575     ch->rw = rw;
576     ch->flush = flush;
577     ch->io.opaque = opaque;
578 }
579 
580 static void dbdma_control_write(DBDMA_channel *ch)
581 {
582     uint16_t mask, value;
583     uint32_t status;
584     bool do_flush = false;
585 
586     mask = (ch->regs[DBDMA_CONTROL] >> 16) & 0xffff;
587     value = ch->regs[DBDMA_CONTROL] & 0xffff;
588 
589     /* This is the status register which we'll update
590      * appropriately and store back
591      */
592     status = ch->regs[DBDMA_STATUS];
593 
594     /* RUN and PAUSE are bits under SW control only
595      * FLUSH and WAKE are set by SW and cleared by HW
596      * DEAD, ACTIVE and BT are only under HW control
597      *
598      * We handle ACTIVE separately at the end of the
599      * logic to ensure all cases are covered.
600      */
601 
602     /* Setting RUN will tentatively activate the channel
603      */
604     if ((mask & RUN) && (value & RUN)) {
605         status |= RUN;
606         DBDMA_DPRINTFCH(ch, " Setting RUN !\n");
607     }
608 
609     /* Clearing RUN 1->0 will stop the channel */
610     if ((mask & RUN) && !(value & RUN)) {
611         /* This has the side effect of clearing the DEAD bit */
612         status &= ~(DEAD | RUN);
613         DBDMA_DPRINTFCH(ch, " Clearing RUN !\n");
614     }
615 
616     /* Setting WAKE wakes up an idle channel if it's running
617      *
618      * Note: The doc doesn't say so but assume that only works
619      * on a channel whose RUN bit is set.
620      *
621      * We set WAKE in status, it's not terribly useful as it will
622      * be cleared on the next command fetch but it seems to mimmic
623      * the HW behaviour and is useful for the way we handle
624      * ACTIVE further down.
625      */
626     if ((mask & WAKE) && (value & WAKE) && (status & RUN)) {
627         status |= WAKE;
628         DBDMA_DPRINTFCH(ch, " Setting WAKE !\n");
629     }
630 
631     /* PAUSE being set will deactivate (or prevent activation)
632      * of the channel. We just copy it over for now, ACTIVE will
633      * be re-evaluated later.
634      */
635     if (mask & PAUSE) {
636         status = (status & ~PAUSE) | (value & PAUSE);
637         DBDMA_DPRINTFCH(ch, " %sing PAUSE !\n",
638                         (value & PAUSE) ? "sett" : "clear");
639     }
640 
641     /* FLUSH is its own thing */
642     if ((mask & FLUSH) && (value & FLUSH))  {
643         DBDMA_DPRINTFCH(ch, " Setting FLUSH !\n");
644         /* We set flush directly in the status register, we do *NOT*
645          * set it in "status" so that it gets naturally cleared when
646          * we update the status register further down. That way it
647          * will be set only during the HW flush operation so it is
648          * visible to any completions happening during that time.
649          */
650         ch->regs[DBDMA_STATUS] |= FLUSH;
651         do_flush = true;
652     }
653 
654     /* If either RUN or PAUSE is clear, so should ACTIVE be,
655      * otherwise, ACTIVE will be set if we modified RUN, PAUSE or
656      * set WAKE. That means that PAUSE was just cleared, RUN was
657      * just set or WAKE was just set.
658      */
659     if ((status & PAUSE) || !(status & RUN)) {
660         status &= ~ACTIVE;
661         DBDMA_DPRINTFCH(ch, "  -> ACTIVE down !\n");
662 
663         /* We stopped processing, we want the underlying HW command
664          * to complete *before* we clear the ACTIVE bit. Otherwise
665          * we can get into a situation where the command status will
666          * have RUN or ACTIVE not set which is going to confuse the
667          * MacOS driver.
668          */
669         do_flush = true;
670     } else if (mask & (RUN | PAUSE)) {
671         status |= ACTIVE;
672         DBDMA_DPRINTFCH(ch, " -> ACTIVE up !\n");
673     } else if ((mask & WAKE) && (value & WAKE)) {
674         status |= ACTIVE;
675         DBDMA_DPRINTFCH(ch, " -> ACTIVE up !\n");
676     }
677 
678     DBDMA_DPRINTFCH(ch, " new status=0x%08x\n", status);
679 
680     /* If we need to flush the underlying HW, do it now, this happens
681      * both on FLUSH commands and when stopping the channel for safety.
682      */
683     if (do_flush && ch->flush) {
684         ch->flush(&ch->io);
685     }
686 
687     /* Finally update the status register image */
688     ch->regs[DBDMA_STATUS] = status;
689 
690     /* If active, make sure the BH gets to run */
691     if (status & ACTIVE) {
692         DBDMA_kick(dbdma_from_ch(ch));
693     }
694 }
695 
696 static void dbdma_write(void *opaque, hwaddr addr,
697                         uint64_t value, unsigned size)
698 {
699     int channel = addr >> DBDMA_CHANNEL_SHIFT;
700     DBDMAState *s = opaque;
701     DBDMA_channel *ch = &s->channels[channel];
702     int reg = (addr - (channel << DBDMA_CHANNEL_SHIFT)) >> 2;
703 
704     DBDMA_DPRINTFCH(ch, "writel 0x" TARGET_FMT_plx " <= 0x%08"PRIx64"\n",
705                     addr, value);
706     DBDMA_DPRINTFCH(ch, "channel 0x%x reg 0x%x\n",
707                     (uint32_t)addr >> DBDMA_CHANNEL_SHIFT, reg);
708 
709     /* cmdptr cannot be modified if channel is ACTIVE */
710 
711     if (reg == DBDMA_CMDPTR_LO && (ch->regs[DBDMA_STATUS] & ACTIVE)) {
712         return;
713     }
714 
715     ch->regs[reg] = value;
716 
717     switch(reg) {
718     case DBDMA_CONTROL:
719         dbdma_control_write(ch);
720         break;
721     case DBDMA_CMDPTR_LO:
722         /* 16-byte aligned */
723         ch->regs[DBDMA_CMDPTR_LO] &= ~0xf;
724         dbdma_cmdptr_load(ch);
725         break;
726     case DBDMA_STATUS:
727     case DBDMA_INTR_SEL:
728     case DBDMA_BRANCH_SEL:
729     case DBDMA_WAIT_SEL:
730         /* nothing to do */
731         break;
732     case DBDMA_XFER_MODE:
733     case DBDMA_CMDPTR_HI:
734     case DBDMA_DATA2PTR_HI:
735     case DBDMA_DATA2PTR_LO:
736     case DBDMA_ADDRESS_HI:
737     case DBDMA_BRANCH_ADDR_HI:
738     case DBDMA_RES1:
739     case DBDMA_RES2:
740     case DBDMA_RES3:
741     case DBDMA_RES4:
742         /* unused */
743         break;
744     }
745 }
746 
747 static uint64_t dbdma_read(void *opaque, hwaddr addr,
748                            unsigned size)
749 {
750     uint32_t value;
751     int channel = addr >> DBDMA_CHANNEL_SHIFT;
752     DBDMAState *s = opaque;
753     DBDMA_channel *ch = &s->channels[channel];
754     int reg = (addr - (channel << DBDMA_CHANNEL_SHIFT)) >> 2;
755 
756     value = ch->regs[reg];
757 
758     switch(reg) {
759     case DBDMA_CONTROL:
760         value = ch->regs[DBDMA_STATUS];
761         break;
762     case DBDMA_STATUS:
763     case DBDMA_CMDPTR_LO:
764     case DBDMA_INTR_SEL:
765     case DBDMA_BRANCH_SEL:
766     case DBDMA_WAIT_SEL:
767         /* nothing to do */
768         break;
769     case DBDMA_XFER_MODE:
770     case DBDMA_CMDPTR_HI:
771     case DBDMA_DATA2PTR_HI:
772     case DBDMA_DATA2PTR_LO:
773     case DBDMA_ADDRESS_HI:
774     case DBDMA_BRANCH_ADDR_HI:
775         /* unused */
776         value = 0;
777         break;
778     case DBDMA_RES1:
779     case DBDMA_RES2:
780     case DBDMA_RES3:
781     case DBDMA_RES4:
782         /* reserved */
783         break;
784     }
785 
786     DBDMA_DPRINTFCH(ch, "readl 0x" TARGET_FMT_plx " => 0x%08x\n", addr, value);
787     DBDMA_DPRINTFCH(ch, "channel 0x%x reg 0x%x\n",
788                     (uint32_t)addr >> DBDMA_CHANNEL_SHIFT, reg);
789 
790     return value;
791 }
792 
793 static const MemoryRegionOps dbdma_ops = {
794     .read = dbdma_read,
795     .write = dbdma_write,
796     .endianness = DEVICE_LITTLE_ENDIAN,
797     .valid = {
798         .min_access_size = 4,
799         .max_access_size = 4,
800     },
801 };
802 
803 static const VMStateDescription vmstate_dbdma_io = {
804     .name = "dbdma_io",
805     .version_id = 0,
806     .minimum_version_id = 0,
807     .fields = (VMStateField[]) {
808         VMSTATE_UINT64(addr, struct DBDMA_io),
809         VMSTATE_INT32(len, struct DBDMA_io),
810         VMSTATE_INT32(is_last, struct DBDMA_io),
811         VMSTATE_INT32(is_dma_out, struct DBDMA_io),
812         VMSTATE_BOOL(processing, struct DBDMA_io),
813         VMSTATE_END_OF_LIST()
814     }
815 };
816 
817 static const VMStateDescription vmstate_dbdma_cmd = {
818     .name = "dbdma_cmd",
819     .version_id = 0,
820     .minimum_version_id = 0,
821     .fields = (VMStateField[]) {
822         VMSTATE_UINT16(req_count, dbdma_cmd),
823         VMSTATE_UINT16(command, dbdma_cmd),
824         VMSTATE_UINT32(phy_addr, dbdma_cmd),
825         VMSTATE_UINT32(cmd_dep, dbdma_cmd),
826         VMSTATE_UINT16(res_count, dbdma_cmd),
827         VMSTATE_UINT16(xfer_status, dbdma_cmd),
828         VMSTATE_END_OF_LIST()
829     }
830 };
831 
832 static const VMStateDescription vmstate_dbdma_channel = {
833     .name = "dbdma_channel",
834     .version_id = 1,
835     .minimum_version_id = 1,
836     .fields = (VMStateField[]) {
837         VMSTATE_UINT32_ARRAY(regs, struct DBDMA_channel, DBDMA_REGS),
838         VMSTATE_STRUCT(io, struct DBDMA_channel, 0, vmstate_dbdma_io, DBDMA_io),
839         VMSTATE_STRUCT(current, struct DBDMA_channel, 0, vmstate_dbdma_cmd,
840                        dbdma_cmd),
841         VMSTATE_END_OF_LIST()
842     }
843 };
844 
845 static const VMStateDescription vmstate_dbdma = {
846     .name = "dbdma",
847     .version_id = 3,
848     .minimum_version_id = 3,
849     .fields = (VMStateField[]) {
850         VMSTATE_STRUCT_ARRAY(channels, DBDMAState, DBDMA_CHANNELS, 1,
851                              vmstate_dbdma_channel, DBDMA_channel),
852         VMSTATE_END_OF_LIST()
853     }
854 };
855 
856 static void mac_dbdma_reset(DeviceState *d)
857 {
858     DBDMAState *s = MAC_DBDMA(d);
859     int i;
860 
861     for (i = 0; i < DBDMA_CHANNELS; i++) {
862         memset(s->channels[i].regs, 0, DBDMA_SIZE);
863     }
864 }
865 
866 static void dbdma_unassigned_rw(DBDMA_io *io)
867 {
868     DBDMA_channel *ch = io->channel;
869     dbdma_cmd *current = &ch->current;
870     uint16_t cmd;
871     qemu_log_mask(LOG_GUEST_ERROR, "%s: use of unassigned channel %d\n",
872                   __func__, ch->channel);
873     ch->io.processing = false;
874 
875     cmd = le16_to_cpu(current->command) & COMMAND_MASK;
876     if (cmd == OUTPUT_MORE || cmd == OUTPUT_LAST ||
877         cmd == INPUT_MORE || cmd == INPUT_LAST) {
878         current->xfer_status = cpu_to_le16(ch->regs[DBDMA_STATUS]);
879         current->res_count = cpu_to_le16(io->len);
880         dbdma_cmdptr_save(ch);
881     }
882 }
883 
884 static void dbdma_unassigned_flush(DBDMA_io *io)
885 {
886     DBDMA_channel *ch = io->channel;
887     qemu_log_mask(LOG_GUEST_ERROR, "%s: use of unassigned channel %d\n",
888                   __func__, ch->channel);
889 }
890 
891 static void mac_dbdma_init(Object *obj)
892 {
893     SysBusDevice *sbd = SYS_BUS_DEVICE(obj);
894     DBDMAState *s = MAC_DBDMA(obj);
895     int i;
896 
897     for (i = 0; i < DBDMA_CHANNELS; i++) {
898         DBDMA_channel *ch = &s->channels[i];
899 
900         ch->rw = dbdma_unassigned_rw;
901         ch->flush = dbdma_unassigned_flush;
902         ch->channel = i;
903         ch->io.channel = ch;
904     }
905 
906     memory_region_init_io(&s->mem, obj, &dbdma_ops, s, "dbdma", 0x1000);
907     sysbus_init_mmio(sbd, &s->mem);
908 }
909 
910 static void mac_dbdma_realize(DeviceState *dev, Error **errp)
911 {
912     DBDMAState *s = MAC_DBDMA(dev);
913 
914     s->bh = qemu_bh_new(DBDMA_run_bh, s);
915 }
916 
917 static void mac_dbdma_class_init(ObjectClass *oc, void *data)
918 {
919     DeviceClass *dc = DEVICE_CLASS(oc);
920 
921     dc->realize = mac_dbdma_realize;
922     dc->reset = mac_dbdma_reset;
923     dc->vmsd = &vmstate_dbdma;
924 }
925 
926 static const TypeInfo mac_dbdma_type_info = {
927     .name = TYPE_MAC_DBDMA,
928     .parent = TYPE_SYS_BUS_DEVICE,
929     .instance_size = sizeof(DBDMAState),
930     .instance_init = mac_dbdma_init,
931     .class_init = mac_dbdma_class_init
932 };
933 
934 static void mac_dbdma_register_types(void)
935 {
936     type_register_static(&mac_dbdma_type_info);
937 }
938 
939 type_init(mac_dbdma_register_types)
940