ReactOS  0.4.14-dev-376-gaedba84
rtctimer.c
Go to the documentation of this file.
1 /*
2  * PROJECT: ReactOS HAL
3  * LICENSE: GNU GPL - See COPYING in the top level directory
4  * FILE: hal/halx86/apic/rtctimer.c
5  * PURPOSE: HAL APIC Management and Control Code
6  * PROGRAMMERS: Timo Kreuzer (timo.kreuzer@reactos.org)
7  * REFERENCES:
8  */
9 
10 /* INCLUDES *******************************************************************/
11 
12 #include <hal.h>
13 #define NDEBUG
14 #include <debug.h>
15 
16 #if defined(ALLOC_PRAGMA) && !defined(_MINIHAL_)
17 #pragma alloc_text(INIT, HalpInitializeClock)
18 #endif
19 
20 /* GLOBALS ********************************************************************/
21 
22 const UCHAR HalpClockVector = 0xD1;
25 UCHAR HalpCurrentRate = 9; /* Initial rate 9: 128 Hz / 7.8 ms */
27 static UCHAR RtcMinimumClockRate = 6; /* Minimum rate 6: 16 Hz / 62.5 ms */
28 static UCHAR RtcMaximumClockRate = 10; /* Maximum rate 10: 256 Hz / 3.9 ms */
29 
30 
32 ULONG
34 {
35  ULONG Freqency = ((32768 << 1) >> Rate);
36  return (1000000 + (Freqency/2)) / Freqency;
37 }
38 
39 VOID
41 {
42  UCHAR RegisterA;
43 
44  /* Update the global values */
45  HalpCurrentRate = ClockRate;
47 
48  /* Acquire CMOS lock */
50 
51  // TODO: disable NMI
52 
53  /* Read value of register A */
54  RegisterA = HalpReadCmos(RTC_REGISTER_A);
55 
56  /* Change lower 4 bits to new rate */
57  RegisterA &= 0xF0;
58  RegisterA |= ClockRate;
59 
60  /* Write the new value */
61  HalpWriteCmos(RTC_REGISTER_A, RegisterA);
62 
63  /* Release CMOS lock */
65 }
66 
67 INIT_FUNCTION
68 VOID
69 NTAPI
71 {
72  ULONG_PTR EFlags;
73  UCHAR RegisterB;
74 
75  /* Save EFlags and disable interrupts */
76  EFlags = __readeflags();
77  _disable();
78 
79  // TODO: disable NMI
80 
81  /* Acquire CMOS lock */
83 
84  /* Enable the periodic interrupt in the CMOS */
85  RegisterB = HalpReadCmos(RTC_REGISTER_B);
87 
88  /* Release CMOS lock */
90 
91  /* Set initial rate */
93 
94  /* Restore interrupt state */
95  __writeeflags(EFlags);
96 
97  /* Notify the kernel about the maximum and minimum increment */
100 
101 
102  DPRINT1("Clock initialized\n");
103 }
104 
105 VOID
106 FASTCALL
108 {
109  ULONG LastIncrement;
110  KIRQL Irql;
111 
112  /* Enter trap */
113  KiEnterInterruptTrap(TrapFrame);
114 #ifdef _M_AMD64
115  /* This is for debugging */
116  TrapFrame->ErrorCode = 0xc10c4;
117 #endif
118 
119  /* Start the interrupt */
121  {
122  /* Spurious, just end the interrupt */
123  KiEoiHelper(TrapFrame);
124  }
125 
126  /* Read register C, so that the next interrupt can happen */
128 
129  /* Save increment */
130  LastIncrement = HalpCurrentTimeIncrement;
131 
132  /* Check if someone changed the time rate */
133  if (HalpClockSetMSRate)
134  {
135  /* Set new clock rate */
137 
138  /* We're done */
140  }
141 
142  /* Update the system time -- on x86 the kernel will exit this trap */
143  KeUpdateSystemTime(TrapFrame, LastIncrement, Irql);
144 }
145 
146 VOID
147 FASTCALL
149 {
150  __debugbreak();
151 }
152 
153 ULONG
154 NTAPI
156 {
157  UCHAR Rate;
158 
159  /* Lookup largest value below given Increment */
160  for (Rate = RtcMinimumClockRate; Rate <= RtcMaximumClockRate; Rate++)
161  {
162  /* Check if this is the largest rate possible */
163  if (RtcClockRateToIncrement(Rate + 1) > Increment) break;
164  }
165 
166  /* Set the rate and tell HAL we want to change it */
167  HalpNextMSRate = Rate;
169 
170  /* Return the real increment */
171  return RtcClockRateToIncrement(Rate);
172 }
#define IN
Definition: typedefs.h:38
VOID FORCEINLINE HalpWriteCmos(IN UCHAR Reg, IN UCHAR Value)
Definition: cmos.c:35
#define TRUE
Definition: types.h:120
INIT_FUNCTION VOID NTAPI HalpInitializeClock(VOID)
Definition: rtctimer.c:70
VOID FASTCALL HalpClockInterruptHandler(IN PKTRAP_FRAME TrapFrame)
Definition: rtctimer.c:107
#define RTC_REG_B_PI
Definition: halp.h:55
VOID NTAPI KeSetTimeIncrement(IN ULONG MaxIncrement, IN ULONG MinIncrement)
Definition: ntoskrnl.c:46
VOID FASTCALL KeUpdateSystemTime(IN PKTRAP_FRAME TrapFrame, IN ULONG Increment, IN KIRQL OldIrql)
Definition: time.c:64
static UCHAR RtcMaximumClockRate
Definition: rtctimer.c:28
BOOLEAN NTAPI HalBeginSystemInterrupt(IN KIRQL Irql, IN ULONG Vector, OUT PKIRQL OldIrql)
Definition: pic.c:321
#define FASTCALL
Definition: nt_native.h:50
_Out_ PKIRQL Irql
Definition: csq.h:179
BOOLEAN HalpClockSetMSRate
Definition: rtctimer.c:23
DECLSPEC_NORETURN VOID FASTCALL KiEoiHelper(IN PKTRAP_FRAME TrapFrame)
Definition: traphdlr.c:126
void __cdecl __debugbreak(void)
Definition: intrin_ppc.h:698
VOID RtcSetClockRate(UCHAR ClockRate)
Definition: rtctimer.c:40
uint32_t ULONG_PTR
Definition: typedefs.h:63
UCHAR KIRQL
Definition: env_spec_w32.h:591
#define CLOCK_LEVEL
__INTRIN_INLINE uintptr_t __readeflags(void)
Definition: intrin_x86.h:1555
NTSTATUS(* NTAPI)(IN PFILE_FULL_EA_INFORMATION EaBuffer, IN ULONG EaLength, OUT PULONG ErrorOffset)
Definition: IoEaTest.cpp:117
UCHAR HalpCurrentRate
Definition: rtctimer.c:25
VOID NTAPI HalpReleaseCmosSpinLock(VOID)
Definition: spinlock.c:244
VOID FASTCALL HalpProfileInterruptHandler(IN PKTRAP_FRAME TrapFrame)
Definition: rtctimer.c:148
unsigned char BOOLEAN
#define FORCEINLINE
Definition: ntbasedef.h:221
UCHAR FORCEINLINE HalpReadCmos(IN UCHAR Reg)
Definition: cmos.c:24
UCHAR HalpNextMSRate
Definition: rtctimer.c:24
ULONG NTAPI HalSetTimeIncrement(IN ULONG Increment)
Definition: rtctimer.c:155
const UCHAR HalpClockVector
Definition: rtctimer.c:22
VOID NTAPI HalpAcquireCmosSpinLock(VOID)
Definition: spinlock.c:227
#define RTC_REGISTER_B
Definition: halp.h:17
unsigned char UCHAR
Definition: xmlstorage.h:181
__INTRIN_INLINE void __writeeflags(uintptr_t Value)
Definition: intrin_x86.h:1550
static UCHAR RtcMinimumClockRate
Definition: rtctimer.c:27
#define RTC_REGISTER_C
Definition: halp.h:56
FORCEINLINE VOID KiEnterInterruptTrap(IN PKTRAP_FRAME TrapFrame)
Definition: trap_x.h:369
FORCEINLINE ULONG RtcClockRateToIncrement(UCHAR Rate)
Definition: rtctimer.c:33
#define RTC_REGISTER_A
Definition: xboxrtc.c:21
#define DPRINT1
Definition: precomp.h:8
ULONG HalpCurrentTimeIncrement
Definition: rtctimer.c:26
void __cdecl _disable(void)
Definition: intrin_arm.h:365
unsigned int ULONG
Definition: retypes.h:1
IN OUT PLONG IN OUT PLONG Addend IN OUT PLONG IN LONG Increment
Definition: CrNtStubs.h:42