I thought I'd chuck some LOG statements into 6840ptm.cpp and uncomment #define VERBOSE 1


Code
void ptm6840_device::update_interrupts()
{
        int new_state = ((m_status_reg & TIMER1_IRQ) && (m_control_reg[0] & INTERRUPT_EN)) ||
                                        ((m_status_reg & TIMER2_IRQ) && (m_control_reg[1] & INTERRUPT_EN)) ||
                                        ((m_status_reg & TIMER3_IRQ) && (m_control_reg[2] & INTERRUPT_EN));

        LOG("UPDATEINTER newstate=%d time=%f %d\n",new_state, machine().time().as_double(), m_irq);

        if (new_state != m_irq)
        {
                m_irq = new_state;

                if (m_irq)
                {
                        m_status_reg |= ANY_IRQ;
                }
                else
                {
                        m_status_reg &= ~ANY_IRQ;
                }

                m_irq_cb(m_irq);

                LOG("INTERRUPTS AFTER M_IRQ_CB: m_irq_cb time=%f %d\n", machine().time().as_double(), m_irq);

        }
}

So after it loads up and starts recording there's interrupts being generated continuously,

Code

[:sl2:midi:midi_ptm] UPDATEINTER newstate=0 time=30.329903 0
[:sl2:midi:midi_ptm] 30.329903: **ptm6840 t1 output 0 **
[:sl2:midi:midi_ptm] Timer #1 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #1 reload_count: clock = 1021800.000000  count = 332
[:sl2:midi:midi_ptm] Timer #1 reload_count: output = 0.000325
[:sl2:midi:midi_ptm] **ptm6840 t2 timeout**
[:sl2:midi:midi_ptm] UPDATEINTER newstate=1 time=30.330194 0
[:sl2:midi:midi_ptm] INTERRUPTS AFTER M_IRQ_CB: m_irq_cb time=30.330194 1
[:sl2:midi:midi_ptm] 30.330194: **ptm6840 t2 output 0 **
[:sl2:midi:midi_ptm] Timer #2 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #2 reload_count: clock = 1021800.000000  count = 10624
[:sl2:midi:midi_ptm] Timer #2 reload_count: output = 0.010397
[:sl2:midi:midi_ptm] **ptm6840 t1 timeout**
[:sl2:midi:midi_ptm] UPDATEINTER[:sl2:midi:midi_ptm] Timer #1 reload_count: output = 0.000325
[:sl2:midi:midi_ptm] **ptm6840 t1 timeout** newstate=1 time=30.330228 1
[:sl2:midi:midi_ptm] 30.330228: **ptm6840 t1 output 1 **
[:sl2:midi:midi_ptm] Timer #1 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #1 reload_count: clock = 1021800.000000  count = 332
[:sl2:midi:midi_ptm] Timer #1 reload_count: output = 0.000325
[:sl2:midi:midi_ptm] ':maincpu' (25F7): Status read = 0087
[:sl2:midi:midi_ptm] Timer #2 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #2 read counter: 10574
[:sl2:midi:midi_ptm] UPDATEINTER newstate=0 time=30.330242 1
[:sl2:midi:midi_ptm] INTERRUPTS AFTER M_IRQ_CB: m_irq_cb time=30.330242 0
[:sl2:midi:midi_ptm] ':maincpu' (25FA): Counter 2 read = 0029
[:sl2:midi:midi_ptm] **ptm6840 t1 timeout**
[:sl2:midi:midi_ptm] UPDATEINTER newstate=0 time=30.330553 0
[:sl2:midi:midi_ptm] 30.330553: **ptm6840 t1 output 0 **
[:sl2:midi:midi_ptm] Timer #1 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #1 reload_count: clock = 1021800.000000  count = 332
[:sl2:midi:midi_ptm] Timer #1 reload_count: output = 0.000325
[:sl2:midi:midi_ptm] **ptm6840 t1 timeout**

and then at some point, after typing a bunch of midi keys, it will stop generating interrupts.

Code
[:sl2:midi:midi_ptm] UPDATEINTER newstate=0 time=30.350698 0
[:sl2:midi:midi_ptm] 30.350698: **ptm6840 t1 output 0 **
[:sl2:midi:midi_ptm] Timer #1 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #1 reload_count: clock = 1021800.000000  count = 332
[:sl2:midi:midi_ptm] Timer #1 reload_count: output = 0.000325
[:sl2:midi:midi_ptm] **ptm6840 t2 timeout**
[:sl2:midi:midi_ptm] UPDATEINTER newstate=1 time=30.350988 0

last interrupt gets generated here at 30.350988 and newstate seems to get stuck at 1 so it never toggles the 

[:sl2:midi:midi_ptm] INTERRUPTS AFTER M_IRQ_CB: m_irq_cb time=30.350988 1
[:sl2:midi:midi_ptm] 30.350988: **ptm6840 t2 output 0 **
[:sl2:midi:midi_ptm] Timer #2 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #2 reload_count: clock = 1021800.000000  count = 10624
[:sl2:midi:midi_ptm] Timer #2 reload_count: output = 0.010397
[:sl2:midi:midi_ptm] **ptm6840 t1 timeout**
[:sl2:midi:midi_ptm] UPDATEINTER newstate=1 time=30.351023 1
[:sl2:midi:midi_ptm] 30.351023: **ptm6840 t1 output 1 **
[:sl2:midi:midi_ptm] Timer #1 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #1 reload_count: clock = 1021800.000000  count = 332
[:sl2:midi:midi_ptm] Timer #1 reload_count: output = 0.000325
[:sl2:midi:midi_ptm] **ptm6840 t1 timeout**
[:sl2:midi:midi_ptm] UPDATEINTER newstate=1 time=30.351348 1

The last time it changes the Control registers in the log is at time=20.41 seconds, setting control reg #2 to d3 which does have interrupts enabled (bit 6).

Code
[:sl2:midi:midi_ptm] Timer #1 reload_count: output = 0.000101
[:sl2:midi:midi_ptm] Control register #2 selected
[:sl2:midi:midi_ptm] operation mode   = 010 continuous mode
[:sl2:midi:midi_ptm] value            = 00D3
[:sl2:midi:midi_ptm] t3divisor        = 1
[:sl2:midi:midi_ptm] **ptm6840 t1 timeout**
[:sl2:midi:midi_ptm] UPDATEINTER newstate=0 time=20.411291 0
[:sl2:midi:midi_ptm] 20.411291: **ptm6840 t1 output 0 **
[:sl2:midi:midi_ptm] Timer #1 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #1 reload_count: clock = 1021800.000000  count = 103
[:sl2:midi:midi_ptm] Timer #1 reload_count: output = 0.000101
[:sl2:midi:midi_ptm] **ptm6840 t1 timeout**
[:sl2:midi:midi_ptm] UPDATEINTER newstate=0 time=20.411392 0
[:sl2:midi:midi_ptm] 20.411392: **ptm6840 t1 output 1 **
[:sl2:midi:midi_ptm] Timer #1 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #1 reload_count: clock = 1021800.000000  count = 103
[:sl2:midi:midi_ptm] Timer #1 reload_count: output = 0.000101
[:sl2:midi:midi_ptm] msbbuf1 = 01
[:sl2:midi:midi_ptm] UPDATEINTER newstate=0 time=20.411446 0
[:sl2:midi:midi_ptm] ':maincpu' (23AB): Counter #1 latch = 014B
[:sl2:midi:midi_ptm] msbbuf2 = 29
[:sl2:midi:midi_ptm] UPDATEINTER newstate=0 time=20.411462 0
[:sl2:midi:midi_ptm] ':maincpu' (23B6): Counter #2 latch = 297F
[:sl2:midi:midi_ptm] Control register #1 selected
[:sl2:midi:midi_ptm] operation mode   = 010 continuous mode
[:sl2:midi:midi_ptm] value            = 0092
[:sl2:midi:midi_ptm] t3divisor        = 1
[:sl2:midi:midi_ptm] **ptm6840 t1 timeout**


Adding a line to print the status register it gets stuck at 87 and stays there:
Code
        LOG("UPDATEINTER newstate=%d time=%f %d\n",new_state, machine().time().as_double(), m_irq);
        LOG("UPDATEINTER time=%f statusreg=%x\n",machine().time().as_double(), m_status_reg);


[:sl2:midi:midi_ptm] UPDATEINTER time=23.440963 statusreg=5
[:sl2:midi:midi_ptm] 23.440963: **ptm6840 t1 output 1 **
[:sl2:midi:midi_ptm] Timer #1 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #1 reload_count: clock = 1021800.000000  count = 332
[:sl2:midi:midi_ptm] Timer #1 reload_count: output = 0.000325
[:sl2:midi:midi_ptm] **ptm6840 t2 timeout**
[:sl2:midi:midi_ptm] UPDATEINTER newstate=1 time=23.440966 0
[:sl2:midi:midi_ptm] UPDATEINTER time=23.440966 statusreg=7
[:sl2:midi:midi_ptm] INTERRUPTS AFTER M_IRQ_CB: m_irq_cb time=23.440966 1
[:sl2:midi:midi_ptm] 23.440966: **ptm6840 t2 output 0 **
[:sl2:midi:midi_ptm] Timer #2 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #2 reload_count: clock = 1021800.000000  count = 10624
[:sl2:midi:midi_ptm] Timer #2 reload_count: output = 0.010397
[:sl2:midi:midi_ptm] **ptm6840 t1 timeout**
[:sl2:midi:midi_ptm] UPDATEINTER newstate=1 time=23.441288 1
[:sl2:midi:midi_ptm] UPDATEINTER time=23.441288 statusreg=87
[:sl2:midi:midi_ptm] 23.441288: **ptm6840 t1 output 0 **
[:sl2:midi:midi_ptm] Timer #1 internal clock freq 1021800.000000 
[:sl2:midi:midi_ptm] Timer #1 reload_count: clock = 1021800.000000  count = 332
[:sl2:midi:midi_ptm] Timer #1 reload_count: output = 0.000325



edit:

and if I go into the Debug Memory View and locate the MC6840 PTM/:sl2:midi:midi_ptm/0/m_status_reg and after it gets stuck,
manually set the low nibble to 0, it gets unstuck.

I can then play a few more keys before it gets stuck again, and setting the low nibble to 0 gets it unstuck again.


Also, another way to unstick it is to set the MC6840 PTM/:sl2:midi:midi_ptm/0/m_irq to 0 (gets stuck on 1)



edit:

doing some hacky mangling of ptm6840_device:timeout() stops the freezing, but playback is erratic, going superfast at times 8-)

Code
void ptm6840_device::timeout(int idx)
{
        LOG("**ptm6840 t%d timeout**\n", idx + 1);
        LOG("TIMEOUT time=%f statusreg=%x\n",machine().time().as_double(), m_status_reg);

        // Set the interrupt flag
        m_status_reg |= (1 << idx);
        m_status_read_since_int &= ~(1 << idx);
        update_interrupts();
        m_status_reg &= ~(1 << idx);    //  if I clear the status reg bits here it seems to stop the freezing


edit:

also noticed that the routine for m_ptm_irq in src/devices/bus/a2midi.cpp had a copy paste typo:


Code
WRITE_LINE_MEMBER( a2bus_midi_device::ptm_irq_w )
{
        m_ptm_irq = state ? true : false;     // should be m_ptm_irq?  ( I suppose it doesn't make too much difference )

        if (m_acia_irq || m_ptm_irq)
        {
                raise_slot_irq();
        }
        else
        {
                lower_slot_irq();
        }
}

Last edited by Golden Child; 05/31/19 11:07 PM.