rem: AHI_SetSound( channel, 0, pd->m_SoundLocation[ channel ], pd->m_SoundLength[ channel ], pd->m_AudioCtrl, AHISF_NONE ); }  WriteWord( address, value );
add: if( pd->m_SoundLength[ channel ] == 2 ) {  AHI_SetSound( channel, AHI_NOSOUND, 0, 0, pd->m_AudioCtrl, AHISF_NONE ); } else { AHI_SetSound( channel, 0, pd->m_SoundLocation[ channel ], pd->m_SoundLength[ channel ], pd->m_AudioCtrl, AHISF_NONE ); } }
context: PUHWrite( UWORD            reg,           UWORD            value,          BOOL*            handled,          struct PUHData*  pd,          struct ExecBase* SysBase ){  UWORD* address = (UWORD*) ( (ULONG) pd->m_Custom + reg );  switch( reg )  {    case DMACON:    {      UWORD old_dmacon;      UWORD new_dmacon;      UWORD xor_dmacon;      if( pd->m_DMACON & DMAF_MASTER )      {        old_dmacon = pd->m_DMACON;      }      else      {        old_dmacon = 0;      }      if( value & DMAF_SETCLR )      {        pd->m_DMACON |= ( value & ~DMAF_SETCLR );      }      else      {        pd->m_DMACON &= ~( value & ~DMAF_SETCLR );      }      if( pd->m_DMACON & DMAF_MASTER )      {        new_dmacon = pd->m_DMACON;      }      else      {        new_dmacon = 0;      }      xor_dmacon = old_dmacon ^ new_dmacon;      KPrintF( "DMACON: %04lx => %04lx->%04lx\n", value, old_dmacon, new_dmacon );      if( xor_dmacon & DMAF_AUD0 )      {        if( new_dmacon & DMAF_AUD0 )        {          pd->m_SoundOn[ 0 ] = TRUE;          AHI_SetSound( 0, 0,                        pd->m_SoundLocation[ 0 ],                        pd->m_SoundLength[ 0 ],                        pd->m_AudioCtrl,                        AHISF_IMM );                  }        else        {          pd->m_SoundOn[ 0 ] = FALSE;          AHI_SetSound( 0, AHI_NOSOUND, 0, 0, pd->m_AudioCtrl, AHISF_IMM );        }      }      if( xor_dmacon & DMAF_AUD1 )      {        if( new_dmacon & DMAF_AUD1 )        {          pd->m_SoundOn[ 1 ] = TRUE;          AHI_SetSound( 1, 0,                        pd->m_SoundLocation[ 1 ],                        pd->m_SoundLength[ 1 ],                        pd->m_AudioCtrl,                        AHISF_IMM );                  }        else        {          pd->m_SoundOn[ 1 ] = FALSE;          AHI_SetSound( 1, AHI_NOSOUND, 0, 0, pd->m_AudioCtrl, AHISF_IMM );        }      }      if( xor_dmacon & DMAF_AUD2 )      {        if( new_dmacon & DMAF_AUD2 )        {          pd->m_SoundOn[ 2 ] = TRUE;          AHI_SetSound( 2, 0,                        pd->m_SoundLocation[ 2 ],                        pd->m_SoundLength[ 2 ],                        pd->m_AudioCtrl,                        AHISF_IMM );                  }        else        {          pd->m_SoundOn[ 2 ] = FALSE;          AHI_SetSound( 2, AHI_NOSOUND, 0, 0, pd->m_AudioCtrl, AHISF_IMM );        }      }      if( xor_dmacon & DMAF_AUD3 )      {        if( new_dmacon & DMAF_AUD3 )        {          pd->m_SoundOn[ 3 ] = TRUE;          AHI_SetSound( 3, 0,                        pd->m_SoundLocation[ 3 ],                        pd->m_SoundLength[ 3 ],                        pd->m_AudioCtrl,                        AHISF_IMM );                  }        else        {          pd->m_SoundOn[ 3 ] = FALSE;          AHI_SetSound( 3, AHI_NOSOUND, 0, 0, pd->m_AudioCtrl, AHISF_IMM );        }      }//      WriteWord( address, value & ~DMAF_AUDIO );      WriteWord( address, value );      *handled = TRUE;      break;    }          case INTENA:      if( value & INTF_SETCLR )      {        pd->m_INTENA |= ( value & ~INTF_SETCLR );      }      else      {        pd->m_INTENA &= ~( value & ~INTF_SETCLR );      }      WriteWord( address, value & ~INTF_AUDIO );      if( ( pd->m_INTENA & INTF_INTEN ) &&          ( pd->m_INTENA & pd->m_INTREQ & INTF_AUDIO ) &&          ! pd->m_CausePending )      {        pd->m_CausePending = TRUE;        KPrintF( "Cause\n" );        Cause( &pd->m_SoftInt );      }      *handled = FALSE;      break;    case INTREQ:      if( value & INTF_SETCLR )      {        pd->m_INTREQ |= ( value & ~INTF_SETCLR );      }      else      {        pd->m_INTREQ &= ~( value & ~INTF_SETCLR );      }      KPrintF( "INTREQ: %04lx\n", value );      WriteWord( address, value & ~INTF_AUDIO );      if( ( pd->m_INTENA & INTF_INTEN ) &&          ( pd->m_INTENA & pd->m_INTREQ & INTF_AUDIO ) &&          ! pd->m_CausePending )      {        pd->m_CausePending = TRUE;        KPrintF( "Cause\n" );        Cause( &pd->m_SoftInt );      }      *handled = FALSE;      break;    case ADKCON:      WriteWord( address, value );      *handled = FALSE;      break;    case AUD0LCH:    case AUD1LCH:    case AUD2LCH:    case AUD3LCH:      pd->m_SoundLocation[ ( reg - AUD0LCH ) >> 4 ] &= 0x0000ffff;      pd->m_SoundLocation[ ( reg - AUD0LCH ) >> 4 ] |= value << 16;      WriteWord( address, value );      *handled = TRUE;      break;    case AUD0LCL:    case AUD1LCL:    case AUD2LCL:    case AUD3LCL:    {      int channel = ( reg - AUD0LCL ) >> 4;      pd->m_SoundLocation[ channel ] &= 0xffff0000;      pd->m_SoundLocation[ channel ] |= value;            if( pd->m_SoundOn[ channel ] )      {        // Queue it        AHI_SetSound( channel, 0,                      pd->m_SoundLocation[ channel ],                      pd->m_SoundLength[ channel ],                      pd->m_AudioCtrl,                      AHISF_NONE );      }      WriteWord( address, value );      *handled = TRUE;      break;    }    case AUD0LEN:    case AUD1LEN:    case AUD2LEN:    case AUD3LEN:    {      int channel = ( reg - AUD0LEN ) >> 4;            pd->m_SoundLength[ channel ] = value * 2;            if( pd->m_SoundOn[ channel ] )      {        // Queue it        AHI_SetSound( channel, 0,                      pd->m_SoundLocation[ channel ],                      pd->m_SoundLength[ channel ],                      pd->m_AudioCtrl,                      AHISF_NONE );      }      WriteWord( address, value );      *handled = TRUE;      break;    }    case AUD0PER:    case AUD1PER:    case AUD2PER:    case AUD3PER:    {      int channel = ( reg - AUD0PER ) >> 4;            AHI_SetFreq( channel,                   PALFREQ / value,                    pd->m_AudioCtrl,                   AHISF_IMM );      WriteWord( address, value );      *handled = TRUE;      break;    }    case AUD0VOL:      AHI_SetVol( 0,                  value << 10,                  0x10000,                  pd->m_AudioCtrl,                  AHISF_IMM );      WriteWord( address, value );      *handled = TRUE;      break;    case AUD1VOL:      AHI_SetVol( 1,                  value << 10,                  0x0,                  pd->m_AudioCtrl,                  AHISF_IMM );      WriteWord( address, value );      *handled = TRUE;      break;    case AUD2VOL:      AHI_SetVol( 2,                  value << 10,                  0x0,                  pd->m_AudioCtrl,                  AHISF_IMM );      WriteWord( address, value );      *handled = TRUE;      break;    case AUD3VOL:      AHI_SetVol( 3,                  value << 10,                  0x10000,                  pd->m_AudioCtrl,                  AHISF_IMM );      WriteWord( address, value );      *handled = TRUE;      break;    case AUD0DAT:      KPrintF( "AUD0DAT=%04lx; DMACON: %04lx; INTENA: %04lx\n",      value, pd->m_DMACON, pd->m_INTENA );              if( ( pd->m_DMACON & DMAF_AUD0 ) == 0 )      {        pd->m_INTREQ |= INTF_AUD0;                if( ( pd->m_INTENA & INTF_INTEN ) &&            ( pd->m_INTENA & INTF_AUD0 ) &&            ! pd->m_CausePending )        {          pd->m_CausePending = TRUE;        KPrintF( "Cause\n" );          Cause( &pd->m_SoftInt );        }      }      *handled = TRUE;      break;    case AUD1DAT:      if( ( pd->m_DMACON & DMAF_AUD1 ) == 0 )      {        pd->m_INTREQ |= INTF_AUD1;                if( ( pd->m_INTENA & INTF_INTEN ) &&            ( pd->m_INTENA & INTF_AUD1 ) &&            ! pd->m_CausePending )        {          pd->m_CausePending = TRUE;        KPrintF( "Cause\n" );          Cause( &pd->m_SoftInt );        }      }      *handled = TRUE;      break;    case AUD2DAT:      if( ( pd->m_DMACON & DMAF_AUD2 ) == 0 )      {        pd->m_INTREQ |= INTF_AUD2;                if( ( pd->m_INTENA & INTF_INTEN ) &&            ( pd->m_INTENA & INTF_AUD2 ) &&            ! pd->m_CausePending )        {          pd->m_CausePending = TRUE;        KPrintF( "Cause\n" );          Cause( &pd->m_SoftInt );        }      }      *handled = TRUE;      break;    case AUD3DAT:      if( ( pd->m_DMACON & DMAF_AUD3 ) == 0 )      {        pd->m_INTREQ |= INTF_AUD3;                if( ( pd->m_INTENA & INTF_INTEN ) &&            ( pd->m_INTENA & INTF_AUD3 ) &&            ! pd->m_CausePending )        {          pd->m_CausePending = TRUE;        KPrintF( "Cause\n" );          Cause( &pd->m_SoftInt );        }      }      *handled = TRUE;      break;    default:      // Just carry out the intercepted write operation      WriteWord( address, value );      *handled = FALSE;      break;  }}