| 1603 | // IPU Commands (exec on worker thread only) |
| 1604 | |
| 1605 | __fi static bool ipuVDEC(u32 val) |
| 1606 | { |
| 1607 | static int count = 0; |
| 1608 | if (count++ > 5) { |
| 1609 | if (!FMVstarted) { |
| 1610 | EnableFMV = true; |
| 1611 | FMVstarted = true; |
| 1612 | } |
| 1613 | count = 0; |
| 1614 | } |
| 1615 | eecount_on_last_vdec = cpuRegs.cycle; |
| 1616 | |
| 1617 | switch (ipu_cmd.pos[0]) |
| 1618 | { |
| 1619 | case 0: |
| 1620 | if (!BitstreamInit()) return false; |
| 1621 | |
| 1622 | switch ((val >> 26) & 3) |
| 1623 | { |
| 1624 | case 0://Macroblock Address Increment |
| 1625 | decoder.mpeg1 = ipuRegs.ctrl.MP1; |
| 1626 | ipuRegs.cmd.DATA = get_macroblock_address_increment(); |
| 1627 | break; |
| 1628 | |
| 1629 | case 1://Macroblock Type |
| 1630 | decoder.frame_pred_frame_dct = 1; |
| 1631 | decoder.coding_type = ipuRegs.ctrl.PCT > 0 ? ipuRegs.ctrl.PCT : 1; // Kaiketsu Zorro Mezase doesn't set a Picture type, seems happy with I |
| 1632 | ipuRegs.cmd.DATA = GetMacroblockModes(); |
| 1633 | break; |
| 1634 | |
| 1635 | case 2://Motion Code |
| 1636 | { |
| 1637 | const u16 code = UBITS(16); |
| 1638 | if ((code & 0x8000)) |
| 1639 | { |
| 1640 | DUMPBITS(1); |
| 1641 | ipuRegs.cmd.DATA = 0x00010000; |
| 1642 | } |
| 1643 | else |
| 1644 | { |
| 1645 | const MVtab* tab; |
| 1646 | if ((code & 0xf000) || ((code & 0xfc00) == 0x0c00)) |
| 1647 | tab = MV_4 + UBITS(4); |
| 1648 | else |
| 1649 | tab = MV_10 + UBITS(10); |
| 1650 | |
| 1651 | const int delta = tab->delta + 1; |
| 1652 | DUMPBITS(tab->len); |
| 1653 | |
| 1654 | const int sign = SBITS(1); |
| 1655 | DUMPBITS(1); |
| 1656 | |
| 1657 | ipuRegs.cmd.DATA = (((delta ^ sign) - sign) | (tab->len << 16)); |
| 1658 | } |
| 1659 | } |
| 1660 | break; |
| 1661 | |
| 1662 | case 3://DMVector |
no test coverage detected