Talk:CMOS

From OSDev Wiki
Jump to: navigation, search

Usage of GCC inline assembler instead of VC?

Technically the code could be converted to code that would compile in GCC, Considering a majority of code examples here are in Assembly or C in a syntax compatible with GCC. --Brynet-Inc 17:17, 14 January 2007 (CST)

The goal is to get the point across. To that extent intel assembly is easier to read than AT&T syntax. Besides, this is 16-bit stuff which fits in neither GCC nor MSVC. - Combuster 17:13, 15 January 2007 (CST)

Reading and sanitizing the RTC

I use the following code to read and sanitize the RTC:

char time[10];
void out_byte(int port, int value);
int in_byte(int port);
enum {
	cmos_address = 0x70,
	cmos_data    = 0x71
};
int cmos_ready() {
	out_byte(cmos_address, 10);
	return (in_byte(cmos_data) & 0x80);
}

void read_rtc() {
	while (cmos_ready());
	out_byte(cmos_address, 0x00);	time[0] = in_byte(cmos_data);
	out_byte(cmos_address, 0x02);	time[1] = in_byte(cmos_data);
	out_byte(cmos_address, 0x04);	time[2] = in_byte(cmos_data);
	out_byte(cmos_address, 0x06);	time[3] = in_byte(cmos_data);
	out_byte(cmos_address, 0x07);	time[4] = in_byte(cmos_data);
	out_byte(cmos_address, 0x08);	time[5] = in_byte(cmos_data) - 1;
	out_byte(cmos_address, 0x09);	time[6] = in_byte(cmos_data);
	out_byte(cmos_address, 0x32);	time[7] = in_byte(cmos_data);
	out_byte(cmos_address, 0x0a);	time[8] = in_byte(cmos_data);
	out_byte(cmos_address, 0x0b);	time[9] = in_byte(cmos_data);
	// 12 hour clock
	if (!(time[9] & 2) && (time[2] & 0x80)) {
		time[2] = ((time[2] & 0x80) + 12) % 24;
	}
	// decimal stuff
	if (!(time[9] & 4)) {
		time[0] = (time[0] & 0xf) + ((time[0] / 16) * 10);
		time[1] = (time[1] & 0xf) + ((time[1] / 16) * 10);
		time[2] = (time[2] & 0xf) + ((time[2] / 16) * 10);
		time[5] = (time[5] & 0xf) + ((time[5] / 16) * 10);
	}
	time[3] = (time[3] + 5)	% 7;
}

This produces a much saner version of the CMOS bytes for the RTC; weeks start on Mondays (international standard, used pretty much everywhere but the US) with Monday = 0, Sunday = 6. January = 0 (not 1), December = 11, hour is always [0..23] and minutes/seconds is always [0..59] (no hexing). Naturally, I can't say that the "century" is a correct representation of the century.

The code assumes that interrupts are disabled before calling it.

I hope this is helpful. (Posted 2011-12-13 by Clearer, edited by Solar.)

Personal tools
Namespaces
Variants
Actions
Navigation
About
Toolbox