/* * RTC.CPP - Contains Real Time Clock functions. * Copyright (C) 1998, 1999 Prashant TR * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * See the file COPYING.TR for more details. */ // ID for this file. #define _RTC_CC_ #include "rtc.h" int errflag = 0; FILE *fp; char cmdline[20]; // Write any string to the file and check for successfulness. void writestring(const char *string) { if (fprintf(fp, "%s", string) == EOF) { errflag = 2; checkerrors(); } } int sysinfo() { char output[256]; unsigned char rtcdata[256]; int f, flags; union REGS regs; struct SREGS segs; // Create output file. if ((fp = fopen("rtc.txt", "w")) == NULL) { errflag = 1; checkerrors(); } writestring("\nRTC INFORMATION :\n\n"); // Check if RTC is installed. // Get ROM table. regs.h.ah = 0xc0; int86x(0x15, ®s, ®s, &segs); // Check directly if not found (not perfect although). if (regs.x.flags & 1) { char rtctime; outportb(0x70, 0); rtctime = inportb(0x71); delay(2000); outportb(0x70, 0); if (inportb(0x71) == rtctime) { writestring("\tReal Time Clock not Installed.\n"); fclose(fp); return 0; } } else { // Check from ROM table. if (peek(segs.es, regs.x.bx) >= 3) { // Entry exists in ROM table. if ((!(peekb(segs.es, regs.x.bx + 4) & 0x20)) && (regs.h.ah)) { writestring("\tReal Time Clock not Installed.\n"); fclose(fp); return 0; } } } // RTC is installed. writestring("\tReal Time Clock Installed : Yes\n"); // Get RTC information. for(f = 0; f <= 256; f++) { outportb(0x70, f); rtcdata[f] = inportb(0x71); } // Check if battery is dead. if ((!(rtcdata[0xd] & 0x80)) || (rtcdata[0xe] & 0x80)) { writestring("\tPower Condition : Battery is dead\n"); fclose(fp); return 0; } // Write information. writestring("\tPower Condition : Good\n"); if (!(rtcdata[0xb] & 4)) { // Convert to binary mode if BCD. for(f = 0; f <= 9; f++) { flags = rtcdata[f]; rtcdata[f] = (flags / 0x10) * 10 + flags % 0x10; } } // Write time. sprintf(output, "\tRTC Time : %02u:%02u:%02u\n", rtcdata[4], rtcdata[2], rtcdata[0]); writestring(output); sprintf(output, "\tRTC Alarm time last set : %02u:%02u:%02u\n", rtcdata[5], rtcdata[3], rtcdata[1]); writestring(output); // Write date. sprintf(output, "\tRTC Date : %02u/%02u/%02u\n", rtcdata[7], rtcdata[8], rtcdata[9]); writestring(output); // Write other information. flags = rtcdata[0xa] & 0xf; sprintf(output, "\tRTC Rate Selection bits : %s\n", (!flags) ? "None" : (flags == 3) ? "122 Microseconds" : (flags == 15) ? "500 Milliseconds" : (flags == 6) ? "976.562 Microseconds (Default)" : "(Unknown)"); writestring(output); sprintf(output, "\tDaylight Savings Enabled : %s\n", (rtcdata[0xb] & 1) ? "Yes" : "No"); writestring(output); sprintf(output, "\tHour Selection : %s\n", (rtcdata[0xb] & 2) ? "24-Hour" : "12-Hour"); writestring(output); sprintf(output, "\tData Mode : %s\n", (rtcdata[0xb] & 4) ? "Binary" : "BCD"); writestring(output); sprintf(output, "\tSquare Wave Output : %s\n", (rtcdata[0xb] & 8) ? "Enabled" : "Disabled"); writestring(output); sprintf(output, "\tRTC Alarm Enabled : %s\n", (rtcdata[0xb] & 16) ? "Yes" : "No"); writestring(output); sprintf(output, "\tPeriodic Interrupts : %s\n", (rtcdata[0xb] & 64) ? "Enabled" : "Disabled"); writestring(output); fclose(fp); return 0; } void open_stderr() { fclose(stdout); fclose(&_streams[2]); if (fopen("nul", "wb") == NULL) exit(0x7f); if (fopen("nul", "wb") == NULL) exit(0x7f); if ((stderr = fopen("errors.$$$", "ab")) == NULL) exit(0x7f); } void get_cmdline() { if ((fp = fopen("cmdline.$$$", "rb")) == NULL) exit (0x7f); if (fscanf(fp, "%s", cmdline) != 1) { fclose(fp); exit (0x7f); } fclose(fp); unlink("cmdline.$$$"); } #pragma argsused // The main function. int main(int argc, char **argv) { open_stderr(); get_cmdline(); if (!strcmp(cmdline, "sysinfo")) return (sysinfo()); return 0; }