Lines Matching refs:pChan

246 static void pit_irq_timer_update(PPITCHANNEL pChan, uint64_t current_time, uint64_t now, bool in_timer);
251 static int pit_get_count(PPITCHANNEL pChan)
254 PTMTIMER pTimer = pChan->CTX_SUFF(pPit)->channels[0].CTX_SUFF(pTimer);
257 if (EFFECTIVE_MODE(pChan->mode) == 2)
259 if (pChan->u64NextTS == UINT64_MAX)
261 d = ASMMultU64ByU32DivByU32(TMTimerGet(pTimer) - pChan->count_load_time, PIT_FREQ, TMTimerGetFreq(pTimer));
262 return pChan->count - (d % pChan->count); /** @todo check this value. */
264 uint64_t Interval = pChan->u64NextTS - pChan->u64ReloadTS;
266 return pChan->count - 1; /** @todo This is WRONG! But I'm too tired to fix it properly and just want to shut up a DIV/0 trap now. */
268 d = ASMMultU64ByU32DivByU32(d - pChan->u64ReloadTS, pChan->count, Interval);
269 if (d >= pChan->count)
271 return pChan->count - d;
274 d = ASMMultU64ByU32DivByU32(TMTimerGet(pTimer) - pChan->count_load_time, PIT_FREQ, TMTimerGetFreq(pTimer));
276 switch (EFFECTIVE_MODE(pChan->mode))
282 counter = (pChan->count - d) & 0xffff;
286 counter = pChan->count - ((2 * d) % pChan->count);
289 counter = pChan->count - (d % pChan->count);
297 static int pit_get_out1(PPITCHANNEL pChan, int64_t current_time)
299 PTMTIMER pTimer = pChan->CTX_SUFF(pPit)->channels[0].CTX_SUFF(pTimer);
303 d = ASMMultU64ByU32DivByU32(current_time - pChan->count_load_time, PIT_FREQ, TMTimerGetFreq(pTimer));
304 switch (EFFECTIVE_MODE(pChan->mode))
308 out = (d >= pChan->count);
311 out = (d < pChan->count);
314 Log2(("pit_get_out1: d=%llx c=%x %x \n", d, pChan->count, (unsigned)(d % pChan->count)));
315 if ((d % pChan->count) == 0 && d != 0)
321 out = (d % pChan->count) < ((pChan->count + 1) >> 1);
325 out = (d != pChan->count);
334 PPITCHANNEL pChan = &pThis->channels[channel];
335 return pit_get_out1(pChan, current_time);
341 PPITCHANNEL pChan = &pThis->channels[channel];
342 return pChan->gate;
347 static void pit_latch_count(PPITCHANNEL pChan)
349 if (!pChan->count_latched)
351 pChan->latched_count = pit_get_count(pChan);
352 pChan->count_latched = pChan->rw_mode;
354 pChan->latched_count, ASMMultU64ByU32DivByU32(pChan->count - pChan->latched_count, 1000000000, PIT_FREQ),
355 pChan->count, pChan->mode));
364 PPITCHANNEL pChan = &pThis->channels[channel];
365 PTMTIMER pTimer = pChan->CTX_SUFF(pPit)->channels[0].CTX_SUFF(pTimer);
370 switch (EFFECTIVE_MODE(pChan->mode))
379 if (pChan->gate < val)
382 Log(("pit_set_gate: restarting mode %d\n", pChan->mode));
383 pChan->count_load_time = TMTimerGet(pTimer);
384 pit_irq_timer_update(pChan, pChan->count_load_time, pChan->count_load_time, false);
389 if (pChan->gate < val)
392 Log(("pit_set_gate: restarting mode %d\n", pChan->mode));
393 pChan->count_load_time = pChan->u64ReloadTS = TMTimerGet(pTimer);
394 pit_irq_timer_update(pChan, pChan->count_load_time, pChan->count_load_time, false);
399 pChan->gate = val;
402 static void pit_load_count(PPITCHANNEL pChan, int val)
404 PTMTIMER pTimer = pChan->CTX_SUFF(pPit)->channels[0].CTX_SUFF(pTimer);
409 pChan->count_load_time = pChan->u64ReloadTS = TMTimerGet(pTimer);
410 pChan->count = val;
411 pit_irq_timer_update(pChan, pChan->count_load_time, pChan->count_load_time, false);
414 if (pChan->pTimerR3 /* ch 0 */)
416 if (pChan->cRelLogEntries++ < 32)
418 pChan->mode, pChan->count, pChan->count, PIT_FREQ / pChan->count, (PIT_FREQ * 100 / pChan->count) % 100));
421 pChan->mode, pChan->count, pChan->count, PIT_FREQ / pChan->count, (PIT_FREQ * 100 / pChan->count) % 100));
422 TMTimerSetFrequencyHint(pChan->CTX_SUFF(pTimer), PIT_FREQ / pChan->count);
426 pChan->mode, pChan->count, pChan->count, PIT_FREQ / pChan->count, (PIT_FREQ * 100 / pChan->count) % 100,
427 pChan - &pChan->CTX_SUFF(pPit)->channels[0]));
431 static int64_t pit_get_next_transition_time(PPITCHANNEL pChan, uint64_t current_time)
433 PTMTIMER pTimer = pChan->CTX_SUFF(pPit)->channels[0].CTX_SUFF(pTimer);
437 d = ASMMultU64ByU32DivByU32(current_time - pChan->count_load_time, PIT_FREQ, TMTimerGetFreq(pTimer));
438 switch(EFFECTIVE_MODE(pChan->mode))
443 if (d < pChan->count)
444 next_time = pChan->count;
460 base = (d / pChan->count) * pChan->count;
463 next_time = base + pChan->count - 1;
466 next_time = base + pChan->count;
469 base = (d / pChan->count) * pChan->count;
470 period2 = ((pChan->count + 1) >> 1);
474 next_time = base + pChan->count;
485 if (d <= pChan->count)
486 next_time = pChan->count;
488 if (d < pChan->count)
489 next_time = pChan->count;
490 else if (d == pChan->count)
491 next_time = pChan->count + 1;
500 ASMMultU64ByU32DivByU32(next_time, TMTimerGetFreq(pTimer), PIT_FREQ), pChan->mode, pChan->count));
501 next_time = pChan->count_load_time + ASMMultU64ByU32DivByU32(next_time, TMTimerGetFreq(pTimer), PIT_FREQ);
508 * the algorithm to think that at the end of each period, it'pChan still
514 static void pit_irq_timer_update(PPITCHANNEL pChan, uint64_t current_time, uint64_t now, bool in_timer)
518 PTMTIMER pTimer = pChan->CTX_SUFF(pPit)->channels[0].CTX_SUFF(pTimer);
521 if (!pChan->CTX_SUFF(pTimer))
523 expire_time = pit_get_next_transition_time(pChan, current_time);
524 irq_level = pit_get_out1(pChan, current_time) ? PDM_IRQ_LEVEL_HIGH : PDM_IRQ_LEVEL_LOW;
529 if (!pChan->pPitR3->fDisabledByHpet)
531 PPDMDEVINS pDevIns = pChan->CTX_SUFF(pPit)->pDevIns;
533 switch (EFFECTIVE_MODE(pChan->mode))
545 PDMDevHlpISASetIrq(pDevIns, pChan->irq, PDM_IRQ_LEVEL_FLIP_FLOP);
550 PDMDevHlpISASetIrq(pDevIns, pChan->irq, irq_level);
557 pChan->u64ReloadTS = now;
558 STAM_COUNTER_INC(&pChan->CTX_SUFF(pPit)->StatPITIrq);
564 pChan->u64NextTS = expire_time;
565 TMTimerSet(pChan->CTX_SUFF(pTimer), pChan->u64NextTS);
569 LogFlow(("PIT: m=%d count=%#4x irq_level=%#x stopped\n", pChan->mode, pChan->count, irq_level));
570 TMTimerStop(pChan->CTX_SUFF(pTimer));
571 pChan->u64NextTS = UINT64_MAX;
573 pChan->next_transition_time = expire_time;
594 PPITCHANNEL pChan = &pThis->channels[Port];
598 if (pChan->status_latched)
600 pChan->status_latched = 0;
601 ret = pChan->status;
604 else if (pChan->count_latched)
606 switch (pChan->count_latched)
610 ret = pChan->latched_count & 0xff;
611 pChan->count_latched = 0;
614 ret = pChan->latched_count >> 8;
615 pChan->count_latched = 0;
618 ret = pChan->latched_count & 0xff;
619 pChan->count_latched = RW_STATE_MSB;
629 switch (pChan->read_state)
633 count = pit_get_count(pChan);
637 count = pit_get_count(pChan);
641 count = pit_get_count(pChan);
643 pChan->read_state = RW_STATE_WORD1;
646 count = pit_get_count(pChan);
648 pChan->read_state = RW_STATE_WORD0;
700 PPITCHANNEL pChan = &pThis->channels[channel];
703 pit_latch_count(pChan);
704 if (!(u32 & 0x10) && !pChan->status_latched)
708 PTMTIMER pTimer = pChan->CTX_SUFF(pPit)->channels[0].CTX_SUFF(pTimer);
709 pChan->status = (pit_get_out1(pChan, TMTimerGet(pTimer)) << 7)
710 | (pChan->rw_mode << 4)
711 | (pChan->mode << 1)
712 | pChan->bcd;
713 pChan->status_latched = 1;
721 PPITCHANNEL pChan = &pThis->channels[channel];
726 pit_latch_count(pChan);
732 pChan->rw_mode = access;
733 pChan->read_state = access;
734 pChan->write_state = access;
736 pChan->mode = (u32 >> 1) & 7;
737 pChan->bcd = u32 & 1;
753 PPITCHANNEL pChan = &pThis->channels[Port];
754 uint8_t const write_state = pChan->write_state;
756 switch (pChan->write_state)
760 pit_load_count(pChan, u32);
763 pit_load_count(pChan, u32 << 8);
766 pChan->write_latch = u32;
767 pChan->write_state = RW_STATE_WORD1;
770 pit_load_count(pChan, pChan->write_latch | (u32 << 8));
771 pChan->write_state = RW_STATE_WORD0;
798 /* bit 4 - toggled with each (DRAM?) refresh request, every 15.085 �pChan.
877 PPITCHANNEL pChan = &pThis->channels[i];
878 SSMR3PutU32(pSSM, pChan->count);
879 SSMR3PutU16(pSSM, pChan->latched_count);
880 SSMR3PutU8(pSSM, pChan->count_latched);
881 SSMR3PutU8(pSSM, pChan->status_latched);
882 SSMR3PutU8(pSSM, pChan->status);
883 SSMR3PutU8(pSSM, pChan->read_state);
884 SSMR3PutU8(pSSM, pChan->write_state);
885 SSMR3PutU8(pSSM, pChan->write_latch);
886 SSMR3PutU8(pSSM, pChan->rw_mode);
887 SSMR3PutU8(pSSM, pChan->mode);
888 SSMR3PutU8(pSSM, pChan->bcd);
889 SSMR3PutU8(pSSM, pChan->gate);
890 SSMR3PutU64(pSSM, pChan->count_load_time);
891 SSMR3PutU64(pSSM, pChan->u64NextTS);
892 SSMR3PutU64(pSSM, pChan->u64ReloadTS);
893 SSMR3PutS64(pSSM, pChan->next_transition_time);
894 if (pChan->CTX_SUFF(pTimer))
895 TMR3TimerSave(pChan->CTX_SUFF(pTimer), pSSM);
953 PPITCHANNEL pChan = &pThis->channels[i];
954 SSMR3GetU32(pSSM, &pChan->count);
955 SSMR3GetU16(pSSM, &pChan->latched_count);
956 SSMR3GetU8(pSSM, &pChan->count_latched);
957 SSMR3GetU8(pSSM, &pChan->status_latched);
958 SSMR3GetU8(pSSM, &pChan->status);
959 SSMR3GetU8(pSSM, &pChan->read_state);
960 SSMR3GetU8(pSSM, &pChan->write_state);
961 SSMR3GetU8(pSSM, &pChan->write_latch);
962 SSMR3GetU8(pSSM, &pChan->rw_mode);
963 SSMR3GetU8(pSSM, &pChan->mode);
964 SSMR3GetU8(pSSM, &pChan->bcd);
965 SSMR3GetU8(pSSM, &pChan->gate);
966 SSMR3GetU64(pSSM, &pChan->count_load_time);
967 SSMR3GetU64(pSSM, &pChan->u64NextTS);
968 SSMR3GetU64(pSSM, &pChan->u64ReloadTS);
969 SSMR3GetS64(pSSM, &pChan->next_transition_time);
970 if (pChan->CTX_SUFF(pTimer))
972 TMR3TimerLoad(pChan->CTX_SUFF(pTimer), pSSM);
974 pChan->mode, pChan->count, pChan->count, PIT_FREQ / pChan->count, (PIT_FREQ * 100 / pChan->count) % 100, i));
976 TMTimerSetFrequencyHint(pChan->CTX_SUFF(pTimer), PIT_FREQ / pChan->count);
1004 PPITCHANNEL pChan = (PPITCHANNEL)pvUser;
1005 STAM_PROFILE_ADV_START(&pChan->CTX_SUFF(pPit)->StatPITHandler, a);
1011 pit_irq_timer_update(pChan, pChan->next_transition_time, TMTimerGet(pTimer), true);
1013 STAM_PROFILE_ADV_STOP(&pChan->CTX_SUFF(pPit)->StatPITHandler, a);
1028 const PITCHANNEL *pChan = &pThis->channels[i];
1039 i, pChan->irq,
1040 pChan->count, pChan->latched_count, pChan->count_latched,
1041 pChan->status, pChan->status_latched, pChan->read_state,
1042 pChan->write_state, pChan->write_latch, pChan->rw_mode,
1043 pChan->mode, pChan->bcd, pChan->gate,
1044 pChan->count_load_time, pChan->next_transition_time,
1045 pChan->u64ReloadTS, pChan->u64NextTS);
1101 PPITCHANNEL pChan = &pThis->channels[i];
1102 if (pChan->pTimerR3)
1103 pChan->pTimerRC = TMTimerRCPtr(pChan->pTimerR3);
1123 PPITCHANNEL pChan = &pThis->channels[i];
1126 pChan->latched_count = 0;
1127 pChan->count_latched = 0;
1128 pChan->status_latched = 0;
1129 pChan->status = 0;
1130 pChan->read_state = 0;
1131 pChan->write_state = 0;
1132 pChan->write_latch = 0;
1133 pChan->rw_mode = 0;
1134 pChan->bcd = 0;
1136 pChan->u64NextTS = UINT64_MAX;
1137 pChan->cRelLogEntries = 0;
1138 pChan->mode = 3;
1139 pChan->gate = (i != 2);
1140 pit_load_count(pChan, 0);