diff options
author | Aaron Giles <aaron@aarongiles.com> | 2021-03-23 09:41:27 -0700 |
---|---|---|
committer | Aaron Giles <aaron@aarongiles.com> | 2021-03-23 09:41:27 -0700 |
commit | c632b586f7627b4f2d880e1a114baded99911d77 (patch) | |
tree | ac2fbfda036c77444d837a4de84c032488645aac | |
parent | 690272e7fd9174983cdb17631ba28854473fb4a3 (diff) |
First round of global synchronize removals.
-rw-r--r-- | src/devices/bus/hp9845_io/98046.cpp | 10 | ||||
-rw-r--r-- | src/devices/bus/hp9845_io/98046.h | 2 | ||||
-rw-r--r-- | src/devices/bus/mackbd/keyboard.cpp | 14 | ||||
-rw-r--r-- | src/devices/bus/mackbd/pluskbd.cpp | 5 | ||||
-rw-r--r-- | src/devices/bus/nes/mmc1.cpp | 4 | ||||
-rw-r--r-- | src/devices/bus/nes/mmc1.h | 1 | ||||
-rw-r--r-- | src/devices/bus/rs232/hlemouse.cpp | 6 | ||||
-rw-r--r-- | src/devices/bus/rs232/hlemouse.h | 2 | ||||
-rw-r--r-- | src/devices/bus/z29_kbd/he191_3425.cpp | 4 | ||||
-rw-r--r-- | src/devices/bus/z29_kbd/he191_3425.h | 1 | ||||
-rw-r--r-- | src/devices/bus/z29_kbd/md_kbd.cpp | 3 | ||||
-rw-r--r-- | src/devices/bus/z29_kbd/md_kbd.h | 1 | ||||
-rw-r--r-- | src/devices/cpu/m6502/m6500_1.cpp | 16 | ||||
-rw-r--r-- | src/devices/cpu/m6502/m6500_1.h | 2 | ||||
-rw-r--r-- | src/devices/cpu/mcs48/mcs48.cpp | 10 | ||||
-rw-r--r-- | src/devices/cpu/mcs48/mcs48.h | 4 | ||||
-rw-r--r-- | src/devices/cpu/tms34010/tms34010.cpp | 12 | ||||
-rw-r--r-- | src/devices/cpu/tms34010/tms34010.h | 1 | ||||
-rw-r--r-- | src/emu/attotime.h | 55 |
19 files changed, 129 insertions, 24 deletions
diff --git a/src/devices/bus/hp9845_io/98046.cpp b/src/devices/bus/hp9845_io/98046.cpp index 8b7e601f0f4..cbf2edb3b4c 100644 --- a/src/devices/bus/hp9845_io/98046.cpp +++ b/src/devices/bus/hp9845_io/98046.cpp @@ -237,6 +237,8 @@ const tiny_rom_entry *hp98046_io_card_device::device_rom_region() const void hp98046_io_card_device::device_start() { m_ram = std::make_unique<uint8_t[]>(1024); + m_sync_rx_im_w.enregister(*this, FUNC(hp98046_io_card_device::sync_rx_im_w)); + m_sync_tx_im_w.enregister(*this, FUNC(hp98046_io_card_device::sync_tx_im_w)); save_pointer(NAME(m_ram) , 1024); } @@ -495,14 +497,14 @@ WRITE_LINE_MEMBER(hp98046_io_card_device::rs232_cts_w) WRITE_LINE_MEMBER(hp98046_io_card_device::rs232_rxc_w) { if (!m_loopback) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(hp98046_io_card_device::sync_rx_im_w) , this) , state); + m_sync_rx_im_w.synchronize(state); } } WRITE_LINE_MEMBER(hp98046_io_card_device::rs232_txc_w) { if (!m_loopback) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(hp98046_io_card_device::sync_tx_im_w) , this) , state); + m_sync_tx_im_w.synchronize(state); } } @@ -636,7 +638,7 @@ WRITE_LINE_MEMBER(hp98046_io_card_device::rxc_w) m_last_rxc = bool(state); m_sio->rxca_w(m_last_rxc); if (m_loopback) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(hp98046_io_card_device::sync_tx_im_w) , this) , state); + m_sync_tx_im_w.synchronize(state); } } } @@ -649,7 +651,7 @@ WRITE_LINE_MEMBER(hp98046_io_card_device::txc_w) m_sio->txcb_w(m_last_txc); m_sio->rxcb_w(m_last_txc); if (m_loopback) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(hp98046_io_card_device::sync_rx_im_w) , this) , state); + m_sync_rx_im_w.synchronize(state); } } } diff --git a/src/devices/bus/hp9845_io/98046.h b/src/devices/bus/hp9845_io/98046.h index 90debbb8c03..b3f9791e930 100644 --- a/src/devices/bus/hp9845_io/98046.h +++ b/src/devices/bus/hp9845_io/98046.h @@ -99,7 +99,9 @@ private: DECLARE_WRITE_LINE_MEMBER(rxc_w); DECLARE_WRITE_LINE_MEMBER(txc_w); TIMER_CALLBACK_MEMBER(sync_rx_im_w); + emu_timer_cb m_sync_rx_im_w; TIMER_CALLBACK_MEMBER(sync_tx_im_w); + emu_timer_cb m_sync_tx_im_w; }; // device type definitions diff --git a/src/devices/bus/mackbd/keyboard.cpp b/src/devices/bus/mackbd/keyboard.cpp index 4f0de812c19..5857a807985 100644 --- a/src/devices/bus/mackbd/keyboard.cpp +++ b/src/devices/bus/mackbd/keyboard.cpp @@ -287,6 +287,8 @@ protected: m_host_data_in = 0x01U; m_watchdog_in = 1U; + m_update_host_data.enregister(*this, FUNC(peripheral_base::update_host_data)); + save_item(NAME(m_row_drive)); save_item(NAME(m_host_clock_out)); save_item(NAME(m_host_data_out)); @@ -296,7 +298,7 @@ protected: virtual DECLARE_WRITE_LINE_MEMBER(data_w) override { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(peripheral_base::update_host_data), this), state); + m_update_host_data.synchronize(state); } DECLARE_WRITE_LINE_MEMBER(watchdog_w) @@ -351,6 +353,7 @@ private: m_host_data_in = param ? 0x01U : 0x00U; } } + emu_timer_cb m_update_host_data; TIMER_CALLBACK_MEMBER(watchdog_timeout) { @@ -443,6 +446,9 @@ protected: { peripheral_base<3>::device_start(); + m_update_keyboard_clock.enregister(*this, FUNC(keypad_base::update_keyboard_clock)); + m_update_keyboard_data.enregister(*this, FUNC(keypad_base::update_keyboard_data)); + m_keyboard_data_out = 0x01U; m_keyboard_clock_in = 0x01U; m_keyboard_data_in = 0x01U; @@ -466,23 +472,25 @@ private: DECLARE_WRITE_LINE_MEMBER(keyboard_clock_in_w) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(keypad_base::update_keyboard_clock), this), state); + m_update_keyboard_clock.synchronize(state); } DECLARE_WRITE_LINE_MEMBER(keyboard_data_in_w) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(keypad_base::update_keyboard_data), this), state); + m_update_keyboard_data.synchronize(state); } TIMER_CALLBACK_MEMBER(update_keyboard_clock) { m_keyboard_clock_in = param ? 0x01U : 0x00U; } + emu_timer_cb m_update_keyboard_clock; TIMER_CALLBACK_MEMBER(update_keyboard_data) { m_keyboard_data_in = param ? 0x01U : 0x00U; } + emu_timer_cb m_update_keyboard_data; u8 m_keyboard_data_out = 0x01U; // data line drive to keyboard (idle high) u8 m_keyboard_clock_in = 0x01U; // clock line driver from keyboard (idle high) diff --git a/src/devices/bus/mackbd/pluskbd.cpp b/src/devices/bus/mackbd/pluskbd.cpp index 6cc707607f4..520c509c3fc 100644 --- a/src/devices/bus/mackbd/pluskbd.cpp +++ b/src/devices/bus/mackbd/pluskbd.cpp @@ -144,6 +144,8 @@ protected: m_host_data_out = 1U; m_host_data_in = 0x01U; + m_update_host_data.enregister(*this, FUNC(keyboard_base::update_host_data)); + save_item(NAME(m_row_drive)); save_item(NAME(m_host_clock_out)); save_item(NAME(m_host_data_out)); @@ -152,7 +154,7 @@ protected: virtual DECLARE_WRITE_LINE_MEMBER(data_w) override { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(keyboard_base::update_host_data), this), state); + m_update_host_data.synchronize(state); } private: @@ -207,6 +209,7 @@ private: m_host_data_in = param ? 0x01U : 0x00U; } } + emu_timer_cb m_update_host_data; required_device<mcs48_cpu_device> m_mpu; required_ioport_array<10> m_rows; diff --git a/src/devices/bus/nes/mmc1.cpp b/src/devices/bus/nes/mmc1.cpp index 9a27c601b4c..9f7e695dd3b 100644 --- a/src/devices/bus/nes/mmc1.cpp +++ b/src/devices/bus/nes/mmc1.cpp @@ -73,6 +73,8 @@ void nes_sxrom_device::device_start() save_item(NAME(m_count)); save_item(NAME(m_reg)); save_item(NAME(m_reg_write_enable)); + + m_resync_callback.enregister(*this, FUNC(nes_sxrom_device::resync_callback)); } void nes_sxrom_device::pcb_reset() @@ -235,7 +237,7 @@ void nes_sxrom_device::write_h(offs_t offset, uint8_t data) else { m_reg_write_enable = 0; - machine().scheduler().synchronize(timer_expired_delegate(FUNC(nes_sxrom_device::resync_callback),this)); + m_resync_callback.synchronize(); } if (data & 0x80) diff --git a/src/devices/bus/nes/mmc1.h b/src/devices/bus/nes/mmc1.h index c8ccb835d76..368c757beba 100644 --- a/src/devices/bus/nes/mmc1.h +++ b/src/devices/bus/nes/mmc1.h @@ -29,6 +29,7 @@ protected: virtual void device_start() override; TIMER_CALLBACK_MEMBER(resync_callback); + emu_timer_cb m_resync_callback; virtual void update_regs(int reg); // this is needed to simplify NES-EVENT pcb implementation, which handle differently some regs! virtual void set_prg(); diff --git a/src/devices/bus/rs232/hlemouse.cpp b/src/devices/bus/rs232/hlemouse.cpp index 599e0d77d14..1cd01b9384d 100644 --- a/src/devices/bus/rs232/hlemouse.cpp +++ b/src/devices/bus/rs232/hlemouse.cpp @@ -236,7 +236,8 @@ void hle_msmouse_device_base::device_start() m_btn_val = m_btn_sent = 0x00U; m_enable = 0U; - machine().scheduler().synchronize(timer_expired_delegate(FUNC(hle_msmouse_device_base::start_mouse), this)); + m_start_mouse.enregister(*this, FUNC(hle_msmouse_device_base::start_mouse)); + m_start_mouse.synchronize(); } WRITE_LINE_MEMBER(hle_msmouse_device_base::input_dtr) @@ -463,7 +464,8 @@ void hle_msystems_device_base::device_start() m_phase = 0U; - machine().scheduler().synchronize(timer_expired_delegate(FUNC(hle_msystems_device_base::start_mouse), this)); + m_start_mouse.enregister(*this, FUNC(hle_msystems_device_base::start_mouse)); + m_start_mouse.synchronize(); } void hle_msystems_device_base::tra_callback() diff --git a/src/devices/bus/rs232/hlemouse.h b/src/devices/bus/rs232/hlemouse.h index d2fae5bd4d1..a24d5396f18 100644 --- a/src/devices/bus/rs232/hlemouse.h +++ b/src/devices/bus/rs232/hlemouse.h @@ -44,6 +44,7 @@ protected: private: TIMER_CALLBACK_MEMBER(start_mouse); + emu_timer_cb m_start_mouse; void check_enable(); void check_inputs(); @@ -138,6 +139,7 @@ protected: private: TIMER_CALLBACK_MEMBER(start_mouse); + emu_timer_cb m_start_mouse; virtual bool read_inputs() = 0; virtual uint8_t report_buttons() = 0; diff --git a/src/devices/bus/z29_kbd/he191_3425.cpp b/src/devices/bus/z29_kbd/he191_3425.cpp index 5a52f363590..555509a8a76 100644 --- a/src/devices/bus/z29_kbd/he191_3425.cpp +++ b/src/devices/bus/z29_kbd/he191_3425.cpp @@ -42,13 +42,15 @@ void he191_3425_device::device_start() { m_leds[0] = 1; // L1: Power + m_receive_data_synced.enregister(*this, FUNC(he191_3425_device::receive_data_synced)); + save_item(NAME(m_select)); save_item(NAME(m_recv_data)); } void he191_3425_device::receive_data(bool state) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(he191_3425_device::receive_data_synced), this), state); + m_receive_data_synced.synchronize(state); } TIMER_CALLBACK_MEMBER(he191_3425_device::receive_data_synced) diff --git a/src/devices/bus/z29_kbd/he191_3425.h b/src/devices/bus/z29_kbd/he191_3425.h index cf0129936fb..f7630fca636 100644 --- a/src/devices/bus/z29_kbd/he191_3425.h +++ b/src/devices/bus/z29_kbd/he191_3425.h @@ -39,6 +39,7 @@ private: // misc. helpers TIMER_CALLBACK_MEMBER(receive_data_synced); + emu_timer_cb m_receive_data_synced; // object finders required_device<cpu_device> m_mcu; diff --git a/src/devices/bus/z29_kbd/md_kbd.cpp b/src/devices/bus/z29_kbd/md_kbd.cpp index 1a313af10ce..a1f67753da6 100644 --- a/src/devices/bus/z29_kbd/md_kbd.cpp +++ b/src/devices/bus/z29_kbd/md_kbd.cpp @@ -49,6 +49,7 @@ void md_keyboard_device::device_resolve_objects() void md_keyboard_device::device_start() { + m_receive_data_synced.enregister(*this, FUNC(md_keyboard_device::receive_data_synced)); save_item(NAME(m_14515b_select)); save_item(NAME(m_ls175_clock)); save_item(NAME(m_recv_data)); @@ -61,7 +62,7 @@ void md_keyboard_device::device_reset() void md_keyboard_device::receive_data(bool state) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(md_keyboard_device::receive_data_synced), this), state); + m_receive_data_synced.synchronize(state); } TIMER_CALLBACK_MEMBER(md_keyboard_device::receive_data_synced) diff --git a/src/devices/bus/z29_kbd/md_kbd.h b/src/devices/bus/z29_kbd/md_kbd.h index 8a81b9a461d..e99ba88a537 100644 --- a/src/devices/bus/z29_kbd/md_kbd.h +++ b/src/devices/bus/z29_kbd/md_kbd.h @@ -37,6 +37,7 @@ private: // misc. helpers TIMER_CALLBACK_MEMBER(receive_data_synced); + emu_timer_cb m_receive_data_synced; void ls175_w(u8 data); // address maps diff --git a/src/devices/cpu/m6502/m6500_1.cpp b/src/devices/cpu/m6502/m6500_1.cpp index aaede8b2bff..dd0578210b1 100644 --- a/src/devices/cpu/m6502/m6500_1.cpp +++ b/src/devices/cpu/m6502/m6500_1.cpp @@ -105,28 +105,28 @@ m6500_1_device::m6500_1_device(machine_config const &mconfig, char const *tag, d void m6500_1_device::pa_w(uint8_t data) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(m6500_1_device::set_port_in<0>), this), unsigned(data)); + m_set_port_in[0].synchronize(data); } void m6500_1_device::pb_w(u8 data) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(m6500_1_device::set_port_in<1>), this), unsigned(data)); + m_set_port_in[1].synchronize(data); } void m6500_1_device::pc_w(u8 data) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(m6500_1_device::set_port_in<2>), this), unsigned(data)); + m_set_port_in[2].synchronize(data); } void m6500_1_device::pd_w(u8 data) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(m6500_1_device::set_port_in<3>), this), unsigned(data)); + m_set_port_in[3].synchronize(data); } WRITE_LINE_MEMBER(m6500_1_device::cntr_w) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(m6500_1_device::set_cntr_in), this), state); + m_set_cntr_in.synchronize(state); } @@ -145,6 +145,12 @@ void m6500_1_device::device_start() m_counter_base = 0U; + m_set_port_in[0].enregister(*this, FUNC(m6500_1_device::set_port_in<0>)); + m_set_port_in[1].enregister(*this, FUNC(m6500_1_device::set_port_in<1>)); + m_set_port_in[2].enregister(*this, FUNC(m6500_1_device::set_port_in<2>)); + m_set_port_in[3].enregister(*this, FUNC(m6500_1_device::set_port_in<3>)); + m_set_cntr_in.enregister(*this, FUNC(m6500_1_device::set_cntr_in)); + state_add(M6500_1_CR, "CR", m_cr).callimport().callexport(); state_add(M6500_1_UL, "UL", m_ul).callimport().callexport(); state_add(M6500_1_LL, "LL", m_ll).callimport().callexport(); diff --git a/src/devices/cpu/m6502/m6500_1.h b/src/devices/cpu/m6502/m6500_1.h index 0a4a07a6ff9..c756da0cf2c 100644 --- a/src/devices/cpu/m6502/m6500_1.h +++ b/src/devices/cpu/m6502/m6500_1.h @@ -98,6 +98,7 @@ protected: void write_port(offs_t offset, u8 data); void clear_edge(offs_t offset, u8 data); template <unsigned Port> TIMER_CALLBACK_MEMBER(set_port_in); + emu_timer_cb m_set_port_in[4]; u8 read_upper_count(); u8 read_lower_count(); @@ -108,6 +109,7 @@ protected: bool pulse_generator_mode() const; bool event_counter_mode() const; TIMER_CALLBACK_MEMBER(set_cntr_in); + emu_timer_cb m_set_cntr_in; void toggle_cntr(); void memory_map(address_map &map); diff --git a/src/devices/cpu/mcs48/mcs48.cpp b/src/devices/cpu/mcs48/mcs48.cpp index 34d89693bf2..fbda4a76657 100644 --- a/src/devices/cpu/mcs48/mcs48.cpp +++ b/src/devices/cpu/mcs48/mcs48.cpp @@ -1418,9 +1418,17 @@ TIMER_CALLBACK_MEMBER( upi41_cpu_device::master_callback ) void upi41_cpu_device::upi41_master_w(offs_t offset, uint8_t data) { - machine().scheduler().synchronize(timer_expired_delegate(FUNC(upi41_cpu_device::master_callback), this), (offset << 8) | data); + m_master_callback.synchronize((offset << 8) | data); } +void upi41_cpu_device::device_start() +{ + mcs48_cpu_device::device_start(); + + m_master_callback.enregister(*this, FUNC(upi41_cpu_device::master_callback)); +} + + /*************************************************************************** GENERAL CONTEXT ACCESS diff --git a/src/devices/cpu/mcs48/mcs48.h b/src/devices/cpu/mcs48/mcs48.h index fa73d33e5b6..939bbc1b497 100644 --- a/src/devices/cpu/mcs48/mcs48.h +++ b/src/devices/cpu/mcs48/mcs48.h @@ -631,7 +631,11 @@ protected: // construction/destruction upi41_cpu_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, int rom_size, int ram_size); + // overrides + virtual void device_start() override; + TIMER_CALLBACK_MEMBER( master_callback ); + emu_timer_cb m_master_callback; }; class i8041a_device : public upi41_cpu_device diff --git a/src/devices/cpu/tms34010/tms34010.cpp b/src/devices/cpu/tms34010/tms34010.cpp index 6eaf63b96ae..8d4f78c2cb2 100644 --- a/src/devices/cpu/tms34010/tms34010.cpp +++ b/src/devices/cpu/tms34010/tms34010.cpp @@ -741,8 +741,10 @@ void tms340x0_device::device_start() } } + m_internal_interrupt_callback.enregister(*this, FUNC(tms340x0_device::internal_interrupt_callback)); + /* allocate a scanline timer and set it to go off at the start */ - m_scantimer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(tms340x0_device::scanline_callback), this)); + m_scantimer = timer_alloc(*this, FUNC(tms340x0_device::scanline_callback)); m_scantimer->adjust(attotime::zero); save_item(NAME(m_pc)); @@ -1286,7 +1288,7 @@ void tms34010_device::io_register_w(offs_t offset, u16 data, u16 mem_mask) /* NMI issued? */ if (data & 0x0100) - machine().scheduler().synchronize(timer_expired_delegate(FUNC(tms340x0_device::internal_interrupt_callback), this), 0); + m_internal_interrupt_callback.synchronize(0); } break; @@ -1324,7 +1326,7 @@ void tms34010_device::io_register_w(offs_t offset, u16 data, u16 mem_mask) /* input interrupt? (should really be state-based, but the functions don't exist!) */ if (!(oldreg & 0x0008) && (newreg & 0x0008)) - machine().scheduler().synchronize(timer_expired_delegate(FUNC(tms340x0_device::internal_interrupt_callback), this), TMS34010_HI); + m_internal_interrupt_callback.synchronize(TMS34010_HI); else if ((oldreg & 0x0008) && !(newreg & 0x0008)) IOREG(REG_INTPEND) &= ~TMS34010_HI; } @@ -1441,7 +1443,7 @@ void tms34020_device::io_register_w(offs_t offset, u16 data, u16 mem_mask) /* NMI issued? */ if (data & 0x0100) - machine().scheduler().synchronize(timer_expired_delegate(FUNC(tms340x0_device::internal_interrupt_callback), this), 0); + m_internal_interrupt_callback.synchronize(0); break; case REG020_HSTCTLL: @@ -1476,7 +1478,7 @@ void tms34020_device::io_register_w(offs_t offset, u16 data, u16 mem_mask) /* input interrupt? (should really be state-based, but the functions don't exist!) */ if (!(oldreg & 0x0008) && (newreg & 0x0008)) - machine().scheduler().synchronize(timer_expired_delegate(FUNC(tms340x0_device::internal_interrupt_callback), this), TMS34010_HI); + m_internal_interrupt_callback.synchronize(TMS34010_HI); else if ((oldreg & 0x0008) && !(newreg & 0x0008)) IOREG(REG020_INTPEND) &= ~TMS34010_HI; break; diff --git a/src/devices/cpu/tms34010/tms34010.h b/src/devices/cpu/tms34010/tms34010.h index c3d639e3506..84499220929 100644 --- a/src/devices/cpu/tms34010/tms34010.h +++ b/src/devices/cpu/tms34010/tms34010.h @@ -177,6 +177,7 @@ public: u16 host_r(offs_t offset); TIMER_CALLBACK_MEMBER(internal_interrupt_callback); + emu_timer_cb m_internal_interrupt_callback; TIMER_CALLBACK_MEMBER(scanline_callback); protected: diff --git a/src/emu/attotime.h b/src/emu/attotime.h index 7b31362d7dc..ba801392b75 100644 --- a/src/emu/attotime.h +++ b/src/emu/attotime.h @@ -195,6 +195,61 @@ private: /** @} */ +class precise_clock +{ +public: + precise_clock(u32 rate = 1, u32 divider = 1) : + m_rate(rate), + m_divider(1), + m_period((rate == 0) ? ATTOSECONDS_PER_SECOND : ((ATTOSECONDS_PER_SECOND + rate - 1) / rate)), + m_base(attotime::zero), + m_tick_base(0) + { + } + + void reset_tick_base() { m_tick_base = 0; } + + void set_rate(attotime const &base, u32 rate, u32 divider = 0) + { + // remember the ticks at the old rate at the base time before setting it + m_tick_base = tick(base); + m_base = base; + + // configure the new rate + m_rate = rate; + if (divider != 0) + m_divider = divider; + m_period = (rate == 0) ? ATTOSECONDS_PER_SECOND : ((ATTOSECONDS_PER_SECOND + rate - 1) / rate); + } + + u64 tick(attotime const &time) + { + attotime delta = time - m_base; + u64 count = delta.seconds() * m_rate + delta.attoseconds() / m_period; + return m_tick_base + ((m_divider == 1) ? count : (count / m_divider)); + } + + attotime tick_time(u64 ticknum) + { + // can't get time of ticks prior to the last rate switch + if (ticknum < m_tick_base) + return attotime::zero; + ticknum = (ticknum - m_tick_base) * m_divider; + + u64 seconds = ticknum / m_rate; + attotime delta(seconds, (ticknum - seconds * m_rate) * m_period); + return delta + m_base; + } + +private: + u32 m_rate; // integral rate in Hz + u32 m_divider; // clock divider (or 1 if no divider) + attoseconds_t m_period; // period, measured in attoseconds + attotime m_base; // time of last rate change + u64 m_tick_base; // ticks at last rate change +}; + + //************************************************************************** // INLINE FUNCTIONS //************************************************************************** |