2 Skelton for retropc emulator
4 Author : Takeda.Toshiya
12 void UPD4991A::initialize()
16 memset(regs, 0, sizeof(regs));
17 ctrl1 = ctrl2 = mode = 0;
19 get_host_time(&cur_time);
23 register_event(this, 0, 1000000.0, true, ®ister_id);
26 void UPD4991A::write_io8(uint32_t addr, uint32_t data)
30 if(mode == 0 || mode == 3) {
31 if(regs[0][addr] != data) {
35 } else if(mode == 1) {
37 } else if(mode == 2) {
38 uint8_t tmp = regs[2][addr] ^ data;
41 if(addr == 12 && (tmp & 8)) {
46 } else if(addr == 13) {
48 } else if(addr == 14) {
50 } else if(addr == 15) {
55 uint32_t UPD4991A::read_io8(uint32_t addr)
59 if(mode == 0 || mode == 3) {
61 } else if(mode == 1 || mode == 2) {
62 return regs[mode][addr];
64 } else if(addr == 14) {
70 void UPD4991A::event_callback(int event_id, int err)
73 if(cur_time.initialized) {
76 get_host_time(&cur_time); // resync
77 cur_time.initialized = true;
85 #define MODE_12H !(regs[2][12] & 8)
87 void UPD4991A::read_from_cur_time()
89 int hour = MODE_12H ? (cur_time.hour % 12) : cur_time.hour;
90 int ampm = (MODE_12H && cur_time.hour >= 12) ? 4 : 0;
92 regs[0][ 0] = TO_BCD_LO(cur_time.second);
93 regs[0][ 1] = TO_BCD_HI(cur_time.second);
94 regs[0][ 2] = TO_BCD_LO(cur_time.minute);
95 regs[0][ 3] = TO_BCD_HI(cur_time.minute);
96 regs[0][ 4] = TO_BCD_LO(hour);
97 regs[0][ 5] = TO_BCD_HI(hour) | ampm;
98 regs[0][ 6] = cur_time.day_of_week;
99 regs[0][ 7] = TO_BCD_LO(cur_time.day);
100 regs[0][ 8] = TO_BCD_HI(cur_time.day);
101 regs[0][ 9] = TO_BCD_LO(cur_time.month);
102 regs[0][10] = TO_BCD_HI(cur_time.month);
103 regs[0][11] = TO_BCD_LO(cur_time.year);
104 regs[0][12] = TO_BCD_HI(cur_time.year);
109 void UPD4991A::write_to_cur_time()
111 cur_time.second = regs[0][0] + (regs[0][1] & 7) * 10;
112 cur_time.minute = regs[0][2] + (regs[0][3] & 7) * 10;
114 cur_time.hour = regs[0][4] + (regs[0][5] & 1) * 10 + (regs[0][5] & 4 ? 12 : 0);
116 cur_time.hour = regs[0][4] + (regs[0][5] & 3) * 10;
118 // cur_time.day_of_week = regs[0][6];
119 cur_time.day = regs[0][7] + (regs[0][8] & 3) * 10;
120 cur_time.month = regs[0][9] + (regs[0][10] & 1) * 10;
121 cur_time.year = regs[0][11] + regs[0][12] * 10;
122 cur_time.update_year();
123 cur_time.update_day_of_week();
126 cancel_event(this, register_id);
127 register_event(this, 0, 1000000.0, true, ®ister_id);
130 #define STATE_VERSION 1
132 bool UPD4991A::process_state(FILEIO* state_fio, bool loading)
134 if(!state_fio->StateCheckUint32(STATE_VERSION)) {
137 if(!state_fio->StateCheckInt32(this_device_id)) {
140 if(!cur_time.process_state((void *)state_fio, loading)) {
143 state_fio->StateValue(register_id);
144 state_fio->StateArray(®s[0][0], sizeof(regs), 1);
145 state_fio->StateValue(ctrl1);
146 state_fio->StateValue(ctrl2);
147 state_fio->StateValue(mode);