Author: hbelusca
Date: Sat Jan 10 00:21:33 2015
New Revision: 66022
URL:
http://svn.reactos.org/svn/reactos?rev=66022&view=rev
Log:
[FREELDR]: Commit a temporary "hackfix" for (Pc)GetTime: on VBox when booting
with PXE, for some mysterious reason, Int386(0x1A) call with AH = 0x02 (Get CMOS Time)
*never ever* returns!! (however without PXE everything works). So... is it some kind of
stack overflow or whatever that makes the Int386 function stack messy? Or something else?
So in the meantime we use direct CMOS port reads. Timo, Hervé (and others), can you please
review? And in particular why does it happen only with PXE?
Modified:
trunk/reactos/boot/freeldr/freeldr/arch/i386/pcrtc.c
Modified: trunk/reactos/boot/freeldr/freeldr/arch/i386/pcrtc.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/boot/freeldr/freeldr/arch/…
==============================================================================
--- trunk/reactos/boot/freeldr/freeldr/arch/i386/pcrtc.c [iso-8859-1] (original)
+++ trunk/reactos/boot/freeldr/freeldr/arch/i386/pcrtc.c [iso-8859-1] Sat Jan 10 00:21:33
2015
@@ -20,10 +20,50 @@
#define BCD_INT(bcd) (((bcd & 0xf0) >> 4) * 10 + (bcd &0x0f))
+#ifndef INT386_WITH_INT_1A_AH_02_04__IS__FIXED
+
+/* CMOS Registers and Ports */
+#define CMOS_CONTROL_PORT (PUCHAR)0x70
+#define CMOS_DATA_PORT (PUCHAR)0x71
+
+#define RTC_REGISTER_A 0x0A
+#define RTC_REG_A_UIP 0x80
+
+static UCHAR
+HalpReadCmos(IN UCHAR Reg)
+{
+ /* Select the register */
+ WRITE_PORT_UCHAR(CMOS_CONTROL_PORT, Reg);
+
+ /* Query the value */
+ return READ_PORT_UCHAR(CMOS_DATA_PORT);
+}
+
+#endif
+
TIMEINFO*
PcGetTime(VOID)
{
static TIMEINFO TimeInfo;
+
+#ifndef INT386_WITH_INT_1A_AH_02_04__IS__FIXED
+
+ /* Loop while update is in progress */
+ while ((HalpReadCmos(RTC_REGISTER_A)) & RTC_REG_A_UIP);
+
+ /* Set the time data */
+ TimeInfo.Second = BCD_INT(HalpReadCmos(0));
+ TimeInfo.Minute = BCD_INT(HalpReadCmos(2));
+ TimeInfo.Hour = BCD_INT(HalpReadCmos(4));
+ TimeInfo.Day = BCD_INT(HalpReadCmos(7));
+ TimeInfo.Month = BCD_INT(HalpReadCmos(8));
+ TimeInfo.Year = BCD_INT(HalpReadCmos(9));
+
+ /* Compensate for the century field */
+ TimeInfo.Year += (TimeInfo.Year > 80) ? 1900: 2000;
+
+#else
+
REGS Regs;
for (;;)
@@ -86,6 +126,9 @@
break;
}
+
+#endif
+
return &TimeInfo;
}