阅读:2594回复:11
DOS下的定时中断程序如何开发?
请教各位大虾,我要用C语言编写一个定时中断服务程序,但该如何编写定时中断程序(中断频率较高,比如4096HZ)?
|
|
沙发#
发布于:2002-08-01 21:22
请教各位大虾,我要用C语言编写一个定时中断服务程序,但该如何编写定时中断程序(中断频率较高,比如4096HZ)? dos 下的这样高。。。。。。难。 |
|
|
板凳#
发布于:2002-08-01 22:09
要用C写中断程序最好用这个:
void (_interrupt _far *oldTimer)(void);//老的int8 截取int8的中断向量 void installTimer() { oldTimer=_dos_getvect(0x8); _disable(); _dos_setvect(0x8,newInt8); _enable(); } void restoreTimer() { _disable(); _dos_setvect(0x8,oldTimer); _enable(); } //新的中断程序 void _interrupt far newInt8() { ....在这里面加你的代码,注意变量最好是用near 来声明,否则数据段会在外面 .... (*oldTimer)(); } 以上是用microsoft c 6.0 TC2.0和MSC6.0的函数不大一样,但都有对应的 |
|
地板#
发布于:2002-08-01 23:33
要用C写中断程序最好用这个: 在dos下的int 8h 有这样高的频率? “中断频率较高,比如4096HZ” :( |
|
|
地下室#
发布于:2002-08-02 12:05
INT8每秒钟可以产生18.2次
不可能达到你要求的4096Hz 要达到这么高的频率,可能需要自己做一个硬件,来产生这么高频率的中断,然后再用magicx说的那样接管那个中断。 |
|
|
5楼#
发布于:2002-08-03 09:35
好像可以通过写主板上8253的寄存器(不记得地址了)来加快int8或int1c中断的发生频率,不过不知能不能这么高,以前的游戏工具如g3x就是这样来加快/减慢游戏速度的
|
|
6楼#
发布于:2002-08-03 10:19
完全可以实现。我以前曾编写过这样的采集程序,中断频率为8k。
int8 的时钟频率为1193180,系统作为时钟使用时,每秒产生18.2次中断。可以设置这个时钟的计数值来产生不同频率的中断。下面是我在BC++3.1中的部分代码。 float CTestBase::clockFrequency = 1193180.f; void CTestBase::realtimerInit(unsigned int ccounter,void interrupt (far *realtimer_int_server)(__CPPARGS)) { disable(); /* 禁止中断响应 */ outportb(0x43,0x36); /* 重新设置计数器0 */ /* 保护系统日历计数 */ pccad=(long *)MK_FP(0x0040,0x006c); counterValue=*pccad; outportb(0x40,lo(ccounter)); /* 设置实时计时单位 */ outportb(0x40,hi(ccounter)); tatick=(float)ccounter/1.193180f; cticks=0; /* TICKS 计数器初始化 */ intVector=getvect(0x1c); /* 保存并设置中断向量 */ setvect(0x1c,realtimer_int_server); enable(); /* 使能中断响应 */ } 上面程序为接管INT8的程序代码。ccounter为中断频率,realtimer_int_server为中断函数的指针,cticks为实际中断的次数,counterValue为当前系统时钟计数值。 void CTestBase::realtimerExit(void) { disable(); /* 禁止中断响应 */ outportb(0x21,0); /* 保护系统日历计数 */ counterValue+=(long)cticks*(long)tatick*18.2/1000000L; *pccad=counterValue; outportb(0x43,0x36); /* 恢复计数器0 */ outportb(0x40,0); /* 恢复系统计时单位 */ outportb(0x40,0); setvect(0x1c,intVector); enable(); /* 使能中断响应 */ } 如果有问题可以给我联系。E-MAIL:zjg1603@sina.com |
|
7楼#
发布于:2002-08-03 12:45
是的,可以设置内部计数器的值来改变INT8的中断频率,但一定要在你的新INT8中要很的处理原来INT8的中断例程,要不系统时钟就不对了!!!!!!!
|
|
8楼#
发布于:2002-08-04 20:28
非常感谢zjg1603,通过你的帮助,我已可以实现中断频率很高的定时中断程序。
但是,还不清楚其中的一些具体的实现的道理。比如:realtimerInit()中的下列语句。 outportb(0x43,0x36); /* 重新设置计数器0 */ /* 保护系统日历计数 */ pccad=(long *)MK_FP(0x0040,0x006c); counterValue=*pccad; outportb(0x40,lo(ccounter)); /* 设置实时计时单位 */ outportb(0x40,hi(ccounter)); tatick=(float)ccounter/1.193180f; cticks=0; /* TICKS 计数器初始化 */ 请问从那些书籍上可以得到这方面的知识,请指教。 |
|
9楼#
发布于:2002-08-04 21:05
实时时钟就是主板上保存BIOS信息的CMOS芯片,在286上一块MC146818芯片,其地址口为70H,数据口为71H,升级后的主板应该与之兼容,修改实时钟只需对MC146818编程即可
|
|
10楼#
发布于:2002-08-04 21:56
对不起,你上面的程序是对8253编程的,40H是中断控制器的地址,
43H是8253的地址,不过,用实时钟也能实现你的要求,在286就能实现8K的速率,你找一本286的系统原理书上有详细描述 |
|
11楼#
发布于:2002-08-04 23:54
在很多DOS编程的书上都有,你可以查一下。
非常感谢zjg1603,通过你的帮助,我已可以实现中断频率很高的定时中断程序。 |
|