Commit | Line | Data |
---|---|---|
1da177e4 LT |
1 | /* |
2 | * Machine dependent access functions for RTC registers. | |
3 | */ | |
4 | #ifndef _ASM_MC146818RTC_H | |
5 | #define _ASM_MC146818RTC_H | |
6 | ||
7 | #ifdef CONFIG_SH_MPC1211 | |
8 | #undef _ASM_MC146818RTC_H | |
9 | #undef RTC_IRQ | |
10 | #include <asm/mpc1211/mc146818rtc.h> | |
11 | #else | |
12 | ||
13 | #include <asm/rtc.h> | |
14 | ||
15 | #define RTC_ALWAYS_BCD 1 | |
16 | ||
17 | /* FIXME:RTC Interrupt feature is not implemented yet. */ | |
18 | #undef RTC_IRQ | |
19 | #define RTC_IRQ 0 | |
20 | ||
21 | #if defined(CONFIG_CPU_SH3) | |
22 | #define RTC_PORT(n) (R64CNT+(n)*2) | |
23 | #define CMOS_READ(addr) __CMOS_READ(addr,b) | |
24 | #define CMOS_WRITE(val,addr) __CMOS_WRITE(val,addr,b) | |
25 | ||
26 | #elif defined(CONFIG_SH_SECUREEDGE5410) | |
27 | #include <asm/snapgear/io.h> | |
28 | ||
29 | #define RTC_PORT(n) SECUREEDGE_IOPORT_ADDR | |
30 | #define CMOS_READ(addr) secureedge5410_cmos_read(addr) | |
31 | #define CMOS_WRITE(val,addr) secureedge5410_cmos_write(val,addr) | |
32 | extern unsigned char secureedge5410_cmos_read(int addr); | |
33 | extern void secureedge5410_cmos_write(unsigned char val, int addr); | |
34 | ||
35 | #elif defined(CONFIG_CPU_SH4) | |
36 | #define RTC_PORT(n) (R64CNT+(n)*4) | |
37 | #define CMOS_READ(addr) __CMOS_READ(addr,w) | |
38 | #define CMOS_WRITE(val,addr) __CMOS_WRITE(val,addr,w) | |
39 | #endif | |
40 | ||
41 | #define __CMOS_READ(addr, s) ({ \ | |
42 | unsigned char val=0, rcr1, rcr2, r64cnt, retry; \ | |
43 | switch(addr) { \ | |
44 | case RTC_SECONDS: \ | |
45 | val = ctrl_inb(RSECCNT); \ | |
46 | break; \ | |
47 | case RTC_SECONDS_ALARM: \ | |
48 | val = ctrl_inb(RSECAR); \ | |
49 | break; \ | |
50 | case RTC_MINUTES: \ | |
51 | val = ctrl_inb(RMINCNT); \ | |
52 | break; \ | |
53 | case RTC_MINUTES_ALARM: \ | |
54 | val = ctrl_inb(RMINAR); \ | |
55 | break; \ | |
56 | case RTC_HOURS: \ | |
57 | val = ctrl_inb(RHRCNT); \ | |
58 | break; \ | |
59 | case RTC_HOURS_ALARM: \ | |
60 | val = ctrl_inb(RHRAR); \ | |
61 | break; \ | |
62 | case RTC_DAY_OF_WEEK: \ | |
63 | val = ctrl_inb(RWKCNT); \ | |
64 | break; \ | |
65 | case RTC_DAY_OF_MONTH: \ | |
66 | val = ctrl_inb(RDAYCNT); \ | |
67 | break; \ | |
68 | case RTC_MONTH: \ | |
69 | val = ctrl_inb(RMONCNT); \ | |
70 | break; \ | |
71 | case RTC_YEAR: \ | |
72 | val = ctrl_in##s(RYRCNT); \ | |
73 | break; \ | |
74 | case RTC_REG_A: /* RTC_FREQ_SELECT */ \ | |
75 | rcr2 = ctrl_inb(RCR2); \ | |
76 | val = (rcr2 & RCR2_PESMASK) >> 4; \ | |
77 | rcr1 = ctrl_inb(RCR1); \ | |
78 | rcr1 = (rcr1 & (RCR1_CIE | RCR1_AIE)) | RCR1_AF;\ | |
79 | retry = 0; \ | |
80 | do { \ | |
81 | ctrl_outb(rcr1, RCR1); /* clear CF */ \ | |
82 | r64cnt = ctrl_inb(R64CNT); \ | |
83 | } while((ctrl_inb(RCR1) & RCR1_CF) && retry++ < 1000);\ | |
84 | r64cnt ^= RTC_BIT_INVERTED; \ | |
85 | if(r64cnt == 0x7f || r64cnt == 0) \ | |
86 | val |= RTC_UIP; \ | |
87 | break; \ | |
88 | case RTC_REG_B: /* RTC_CONTROL */ \ | |
89 | rcr1 = ctrl_inb(RCR1); \ | |
90 | rcr2 = ctrl_inb(RCR2); \ | |
91 | if(rcr1 & RCR1_CIE) val |= RTC_UIE; \ | |
92 | if(rcr1 & RCR1_AIE) val |= RTC_AIE; \ | |
93 | if(rcr2 & RCR2_PESMASK) val |= RTC_PIE; \ | |
94 | if(!(rcr2 & RCR2_START))val |= RTC_SET; \ | |
95 | val |= RTC_24H; \ | |
96 | break; \ | |
97 | case RTC_REG_C: /* RTC_INTR_FLAGS */ \ | |
98 | rcr1 = ctrl_inb(RCR1); \ | |
99 | rcr1 &= ~(RCR1_CF | RCR1_AF); \ | |
100 | ctrl_outb(rcr1, RCR1); \ | |
101 | rcr2 = ctrl_inb(RCR2); \ | |
102 | rcr2 &= ~RCR2_PEF; \ | |
103 | ctrl_outb(rcr2, RCR2); \ | |
104 | break; \ | |
105 | case RTC_REG_D: /* RTC_VALID */ \ | |
106 | /* Always valid ... */ \ | |
107 | val = RTC_VRT; \ | |
108 | break; \ | |
109 | default: \ | |
110 | break; \ | |
111 | } \ | |
112 | val; \ | |
113 | }) | |
114 | ||
115 | #define __CMOS_WRITE(val, addr, s) ({ \ | |
116 | unsigned char rcr1,rcr2; \ | |
117 | switch(addr) { \ | |
118 | case RTC_SECONDS: \ | |
119 | ctrl_outb(val, RSECCNT); \ | |
120 | break; \ | |
121 | case RTC_SECONDS_ALARM: \ | |
122 | ctrl_outb(val, RSECAR); \ | |
123 | break; \ | |
124 | case RTC_MINUTES: \ | |
125 | ctrl_outb(val, RMINCNT); \ | |
126 | break; \ | |
127 | case RTC_MINUTES_ALARM: \ | |
128 | ctrl_outb(val, RMINAR); \ | |
129 | break; \ | |
130 | case RTC_HOURS: \ | |
131 | ctrl_outb(val, RHRCNT); \ | |
132 | break; \ | |
133 | case RTC_HOURS_ALARM: \ | |
134 | ctrl_outb(val, RHRAR); \ | |
135 | break; \ | |
136 | case RTC_DAY_OF_WEEK: \ | |
137 | ctrl_outb(val, RWKCNT); \ | |
138 | break; \ | |
139 | case RTC_DAY_OF_MONTH: \ | |
140 | ctrl_outb(val, RDAYCNT); \ | |
141 | break; \ | |
142 | case RTC_MONTH: \ | |
143 | ctrl_outb(val, RMONCNT); \ | |
144 | break; \ | |
145 | case RTC_YEAR: \ | |
146 | ctrl_out##s((ctrl_in##s(RYRCNT) & 0xff00) | (val & 0xff), RYRCNT);\ | |
147 | break; \ | |
148 | case RTC_REG_A: /* RTC_FREQ_SELECT */ \ | |
149 | rcr2 = ctrl_inb(RCR2); \ | |
150 | if((val & RTC_DIV_CTL) == RTC_DIV_RESET2) \ | |
151 | rcr2 |= RCR2_RESET; \ | |
152 | ctrl_outb(rcr2, RCR2); \ | |
153 | break; \ | |
154 | case RTC_REG_B: /* RTC_CONTROL */ \ | |
155 | rcr1 = (ctrl_inb(RCR1) & 0x99) | RCR1_AF; \ | |
156 | if(val & RTC_AIE) rcr1 |= RCR1_AIE; \ | |
157 | else rcr1 &= ~RCR1_AIE; \ | |
158 | if(val & RTC_UIE) rcr1 |= RCR1_CIE; \ | |
159 | else rcr1 &= ~RCR1_CIE; \ | |
160 | ctrl_outb(rcr1, RCR1); \ | |
161 | rcr2 = ctrl_inb(RCR2); \ | |
162 | if(val & RTC_SET) rcr2 &= ~RCR2_START; \ | |
163 | else rcr2 |= RCR2_START; \ | |
164 | ctrl_outb(rcr2, RCR2); \ | |
165 | break; \ | |
166 | case RTC_REG_C: /* RTC_INTR_FLAGS */ \ | |
167 | break; \ | |
168 | case RTC_REG_D: /* RTC_VALID */ \ | |
169 | break; \ | |
170 | default: \ | |
171 | break; \ | |
172 | } \ | |
173 | }) | |
174 | ||
175 | #endif /* CONFIG_SH_MPC1211 */ | |
176 | #endif /* _ASM_MC146818RTC_H */ |