home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Simtel MSDOS 1992 June
/
SIMTEL_0692.cdr
/
msdos
/
turbo_c
/
timertst.c
< prev
next >
Wrap
Internet Message Format
|
1989-04-25
|
4KB
From: osh@cbnewsh.ATT.COM (david.a.oshinsky)
Newsgroups: comp.sys.ibm.pc
Subject: Re: Turbo C timer interrupt handler
Date: 24 Apr 89 22:01:20 GMT
Keywords: turbo C interrupt handler
Summary: short Turbo C program
The following program demonstrates how to handle timer interrupts
from Turbo C.
Hope this helps,
David Oshinsky
AT&T Bell Laboratories
Holmdel, NJ
phone: (201)949-0037
uucp: att!houxs!osh
------------------------- Cut here --------------------------
/* 8253 timer test program for Turbo C 1.5/2.0. */
/* Author: David Oshinsky, 11/14/88. */
/* This program demonstrates how to use counter 0 in the */
/* 8253 chip to provide "real-time clock" functions on the */
/* IBM PC or PC/AT. */
/* SOME QUICK INFO ON PC INTERRUPTS: */
/* The interrupt lines INT2 through INT7 appear on the PC */
/* bus. INT0 and INT1 appear only on the motherboard. */
/* Interrupt line usage is as follows: */
/* INT0 is used by counter 0 of the 8253 programmable */
/* interval timer chip */
/* INT1 is used by the keyboard */
/* INT5 is used by the hard disk controller */
/* INT6 is used by the floppy disk controller */
/* The above is not completely accurate when applied to */
/* the PC/AT; however, the timer interrupt uses INT0 on */
/* both the PC and PC/AT. (This program works on both the */
/* PC and the PC/AT.) */
/* The 8259 Peripheral Interrupt Controller (PIC) chip */
/* maps the INTx line to interrupt number x+8 (this is */
/* programmable, set by MS-DOS). Hence, the timer */
/* interrupt is number 8. */
#include <dos.h>
#define ZERO_FLAG 0x040
#define CONTROL_C 3
#define MS_PER_TICK 53 /* milliseconds per IBM PC clock tick */
unsigned long count;
unsigned ticks;
void interrupt timer(), interrupt (*old_handler)();
main()
{
union REGS sreg, rreg;
/* time starts at zero */
count = 0;
ticks = 0;
/* initializations related to MS-DOS call to read keyboard */
sreg.x.dx = 0xff;
sreg.h.ah = 0x06;
printf("\nTo stop the timer test program, type CTRL-C.");
printf("\nTo display time since starting the program, hit any key.");
printf("\nThe time is accurate to roughly the nearest 1 msec.\n\n");
/* Save the address of the current timer interrupt handler */
old_handler = getvect(8);
/* Call "timer" function when timer interrupt occurs. */
setvect(8, timer);
/* Set up 8259 PIC chip to allow INT0 interrupt. */
outportb(0x21, inportb(0x21) & 0xfe);
/* issue command to 8253: counter 0, binary counter, rate generator */
/* (mode 2), load least significant byte of counter followed by */
/* most significant byte */
outportb(0x43, 0x34);
/* Timer is set for 0x4cd * 813.8 ns = 1 ms (LSB followed by MSB). */
outportb(0x40, 0xcd); /* least significant byte of timer count */
outportb(0x40, 0x04); /* most significant byte of timer count */
while (1) {
/* wait for keystroke */
while ( 1 ) {
intdos(&sreg, &rreg);
if ( ! (rreg.x.flags & ZERO_FLAG) )
break;
}
/* stop the program if ctrl-C */
if ( (rreg.x.ax & 0xff) == CONTROL_C ) {
/* NOTE: the following code MUST be executed before */
/* returning to MS-DOS in order to allow proper */
/* operation of programs which use the 8253 timer. */
/* restore 8253 to original state set during PC boot */
/* NOTE: this program leaves 8259 mask register with */
/* least significant bit clear (i.e., INT0 enabled). */
outportb(0x43, 0x34);
outportb(0x40, 0);
outportb(0x40, 0);
/* restore original interrupt vector for number 8 */
setvect(8, old_handler);
printf("Timer test program returning to MS-DOS.\n");
exit(0);
}
else
printf("TIME = %lu MSEC.\n",count);
}
}
/* timer interrupt service routine (interrupt number 8) */
void interrupt
timer()
{
count++;
/* chain to the MS-DOS timer handler approx. 18 times per second */
if (++ticks == MS_PER_TICK) {
old_handler();
ticks = 0;
}
/* issue end-of-interrupt command to 8259 PIC chip */
outportb(0x20, 0x20);
}