@@ -705,89 +705,18 @@ static void update_MI_intr_mask_reg()
705705 );
706706}
707707
708-
709- void update_SP ()
708+ static void do_SP_task ()
710709{
711- if (sp_register .w_sp_status_reg & 0x1 )
712- sp_register .halt = 0 ;
713- if (sp_register .w_sp_status_reg & 0x2 )
714- sp_register .halt = 1 ;
715- if (sp_register .w_sp_status_reg & 0x4 )
716- sp_register .broke = 0 ;
717- if (sp_register .w_sp_status_reg & 0x8 )
718- {
719- MI_register .mi_intr_reg &= 0xFFFFFFFE ;
720- check_interupt ();
721- }
722- if (sp_register .w_sp_status_reg & 0x10 )
723- {
724- MI_register .mi_intr_reg |= 1 ;
725- check_interupt ();
726- }
727- if (sp_register .w_sp_status_reg & 0x20 )
728- sp_register .single_step = 0 ;
729- if (sp_register .w_sp_status_reg & 0x40 )
730- sp_register .single_step = 1 ;
731- if (sp_register .w_sp_status_reg & 0x80 )
732- sp_register .intr_break = 0 ;
733- if (sp_register .w_sp_status_reg & 0x100 )
734- sp_register .intr_break = 1 ;
735- if (sp_register .w_sp_status_reg & 0x200 )
736- sp_register .signal0 = 0 ;
737- if (sp_register .w_sp_status_reg & 0x400 )
738- sp_register .signal0 = 1 ;
739- if (sp_register .w_sp_status_reg & 0x800 )
740- sp_register .signal1 = 0 ;
741- if (sp_register .w_sp_status_reg & 0x1000 )
742- sp_register .signal1 = 1 ;
743- if (sp_register .w_sp_status_reg & 0x2000 )
744- sp_register .signal2 = 0 ;
745- if (sp_register .w_sp_status_reg & 0x4000 )
746- sp_register .signal2 = 1 ;
747- if (sp_register .w_sp_status_reg & 0x8000 )
748- sp_register .signal3 = 0 ;
749- if (sp_register .w_sp_status_reg & 0x10000 )
750- sp_register .signal3 = 1 ;
751- if (sp_register .w_sp_status_reg & 0x20000 )
752- sp_register .signal4 = 0 ;
753- if (sp_register .w_sp_status_reg & 0x40000 )
754- sp_register .signal4 = 1 ;
755- if (sp_register .w_sp_status_reg & 0x80000 )
756- sp_register .signal5 = 0 ;
757- if (sp_register .w_sp_status_reg & 0x100000 )
758- sp_register .signal5 = 1 ;
759- if (sp_register .w_sp_status_reg & 0x200000 )
760- sp_register .signal6 = 0 ;
761- if (sp_register .w_sp_status_reg & 0x400000 )
762- sp_register .signal6 = 1 ;
763- if (sp_register .w_sp_status_reg & 0x800000 )
764- sp_register .signal7 = 0 ;
765- if (sp_register .w_sp_status_reg & 0x1000000 )
766- sp_register .signal7 = 1 ;
767- sp_register .sp_status_reg = ((sp_register .halt ) |
768- (sp_register .broke << 1 ) |
769- (sp_register .dma_busy << 2 ) |
770- (sp_register .dma_full << 3 ) |
771- (sp_register .io_full << 4 ) |
772- (sp_register .single_step << 5 ) |
773- (sp_register .intr_break << 6 ) |
774- (sp_register .signal0 << 7 ) |
775- (sp_register .signal1 << 8 ) |
776- (sp_register .signal2 << 9 ) |
777- (sp_register .signal3 << 10 ) |
778- (sp_register .signal4 << 11 ) |
779- (sp_register .signal5 << 12 ) |
780- (sp_register .signal6 << 13 ) |
781- (sp_register .signal7 << 14 )
782- );
783- //if (get_event(SP_INT)) return;
784- if (!(sp_register .w_sp_status_reg & 0x1 ) &&
785- !(sp_register .w_sp_status_reg & 0x4 )) return ;
786- if (!sp_register .halt && !sp_register .broke )
787- {
788710 int save_pc = rsp_register .rsp_pc & ~0xFFF ;
789711 if (SP_DMEM [0xFC0 /4 ] == 1 )
790712 {
713+ if (dpc_register .freeze ) // DP frozen (DK64, BC)
714+ {
715+ // don't do the task now
716+ // the task will be done when DP is unfreezed (see update_DPC)
717+ return ;
718+ }
719+
791720 // unprotecting old frame buffers
792721 if (fBGetFrameBufferInfo && fBRead && fBWrite &&
793722 frameBufferInfos [0 ].addr )
@@ -821,11 +750,13 @@ void update_SP()
821750 rsp_register .rsp_pc |= save_pc ;
822751 new_frame ();
823752
753+ update_count ();
754+ if (MI_register .mi_intr_reg & 0x1 )
755+ add_interupt_event (SP_INT , 100 );
756+ if (MI_register .mi_intr_reg & 0x20 )
757+ add_interupt_event (DP_INT , 0 );
824758 MI_register .mi_intr_reg &= ~0x21 ;
825759 sp_register .sp_status_reg &= ~0x303 ;
826- update_count ();
827- add_interupt_event (SP_INT , 1000 );
828- add_interupt_event (DP_INT , 1000 );
829760
830761 // protecting new frame buffers
831762 if (fBGetFrameBufferInfo && fBRead && fBWrite ) fBGetFrameBufferInfo (frameBufferInfos );
@@ -878,29 +809,105 @@ void update_SP()
878809 end_section (AUDIO_SECTION );
879810 rsp_register .rsp_pc |= save_pc ;
880811
812+ update_count ();
813+ if (MI_register .mi_intr_reg & 0x1 )
814+ add_interupt_event (SP_INT , 100 );
881815 MI_register .mi_intr_reg &= ~0x1 ;
882816 sp_register .sp_status_reg &= ~0x303 ;
883- update_count ();
884- //add_interupt_event(SP_INT, 500);
885- add_interupt_event (SP_INT , 4000 );
886817 }
887818 else
888819 {
889- //printf("other task\n");
890820 rsp_register .rsp_pc &= 0xFFF ;
891821 doRspCycles (100 );
892822 rsp_register .rsp_pc |= save_pc ;
893823
824+ update_count ();
825+ if (MI_register .mi_intr_reg & 0x1 )
826+ add_interupt_event (SP_INT , 100 );
894827 MI_register .mi_intr_reg &= ~0x1 ;
895828 sp_register .sp_status_reg &= ~0x203 ;
896- update_count ();
897- add_interupt_event (SP_INT , 0 /*100*/ );
898829 }
899- //printf("unknown task type\n");
900- /*if (hle) execute_dlist();
901- //if (hle) processDList();
902- else sp_register.halt = 0;*/
830+ }
831+
832+ void update_SP ()
833+ {
834+ if (sp_register .w_sp_status_reg & 0x1 )
835+ sp_register .halt = 0 ;
836+ if (sp_register .w_sp_status_reg & 0x2 )
837+ sp_register .halt = 1 ;
838+ if (sp_register .w_sp_status_reg & 0x4 )
839+ sp_register .broke = 0 ;
840+ if (sp_register .w_sp_status_reg & 0x8 )
841+ {
842+ MI_register .mi_intr_reg &= 0xFFFFFFFE ;
843+ check_interupt ();
844+ }
845+ if (sp_register .w_sp_status_reg & 0x10 )
846+ {
847+ MI_register .mi_intr_reg |= 1 ;
848+ check_interupt ();
903849 }
850+ if (sp_register .w_sp_status_reg & 0x20 )
851+ sp_register .single_step = 0 ;
852+ if (sp_register .w_sp_status_reg & 0x40 )
853+ sp_register .single_step = 1 ;
854+ if (sp_register .w_sp_status_reg & 0x80 )
855+ sp_register .intr_break = 0 ;
856+ if (sp_register .w_sp_status_reg & 0x100 )
857+ sp_register .intr_break = 1 ;
858+ if (sp_register .w_sp_status_reg & 0x200 )
859+ sp_register .signal0 = 0 ;
860+ if (sp_register .w_sp_status_reg & 0x400 )
861+ sp_register .signal0 = 1 ;
862+ if (sp_register .w_sp_status_reg & 0x800 )
863+ sp_register .signal1 = 0 ;
864+ if (sp_register .w_sp_status_reg & 0x1000 )
865+ sp_register .signal1 = 1 ;
866+ if (sp_register .w_sp_status_reg & 0x2000 )
867+ sp_register .signal2 = 0 ;
868+ if (sp_register .w_sp_status_reg & 0x4000 )
869+ sp_register .signal2 = 1 ;
870+ if (sp_register .w_sp_status_reg & 0x8000 )
871+ sp_register .signal3 = 0 ;
872+ if (sp_register .w_sp_status_reg & 0x10000 )
873+ sp_register .signal3 = 1 ;
874+ if (sp_register .w_sp_status_reg & 0x20000 )
875+ sp_register .signal4 = 0 ;
876+ if (sp_register .w_sp_status_reg & 0x40000 )
877+ sp_register .signal4 = 1 ;
878+ if (sp_register .w_sp_status_reg & 0x80000 )
879+ sp_register .signal5 = 0 ;
880+ if (sp_register .w_sp_status_reg & 0x100000 )
881+ sp_register .signal5 = 1 ;
882+ if (sp_register .w_sp_status_reg & 0x200000 )
883+ sp_register .signal6 = 0 ;
884+ if (sp_register .w_sp_status_reg & 0x400000 )
885+ sp_register .signal6 = 1 ;
886+ if (sp_register .w_sp_status_reg & 0x800000 )
887+ sp_register .signal7 = 0 ;
888+ if (sp_register .w_sp_status_reg & 0x1000000 )
889+ sp_register .signal7 = 1 ;
890+ sp_register .sp_status_reg = ((sp_register .halt ) |
891+ (sp_register .broke << 1 ) |
892+ (sp_register .dma_busy << 2 ) |
893+ (sp_register .dma_full << 3 ) |
894+ (sp_register .io_full << 4 ) |
895+ (sp_register .single_step << 5 ) |
896+ (sp_register .intr_break << 6 ) |
897+ (sp_register .signal0 << 7 ) |
898+ (sp_register .signal1 << 8 ) |
899+ (sp_register .signal2 << 9 ) |
900+ (sp_register .signal3 << 10 ) |
901+ (sp_register .signal4 << 11 ) |
902+ (sp_register .signal5 << 12 ) |
903+ (sp_register .signal6 << 13 ) |
904+ (sp_register .signal7 << 14 )
905+ );
906+ //if (get_event(SP_INT)) return;
907+ if (!(sp_register .w_sp_status_reg & 0x1 ) &&
908+ !(sp_register .w_sp_status_reg & 0x4 )) return ;
909+ if (!sp_register .halt && !sp_register .broke )
910+ do_SP_task ();
904911}
905912
906913void update_DPC ()
@@ -910,7 +917,12 @@ void update_DPC()
910917 if (dpc_register .w_dpc_status & 0x2 )
911918 dpc_register .xbus_dmem_dma = 1 ;
912919 if (dpc_register .w_dpc_status & 0x4 )
913- dpc_register .freeze = 0 ;
920+ {
921+ dpc_register .freeze = 0 ;
922+ // see do_SP_task for more info
923+ if (!sp_register .halt && !sp_register .broke )
924+ do_SP_task ();
925+ }
914926 if (dpc_register .w_dpc_status & 0x8 )
915927 dpc_register .freeze = 1 ;
916928 if (dpc_register .w_dpc_status & 0x10 )
0 commit comments