阅读:2050回复:14
wince中断问题
我现在遇到的问题是不知道如何编写硬件触发中断处理程序
环境为wince.net x86,代码如下希望您给予关注 //Öжϴ¦Àí²¿?Ö HANDLE g_hevInterrupt;; HANDLE g_htIST; DWORD g_dwSysInt; DWORD SetupInterrupt ( void ); DWORD WINAPI ThreadIST ( LPVOID lpvParam ); DWORD SetupInterrupt( void ) { BOOL fRetVal; DWORD dwIrq = 7(这是硬件设置的中断号) DWORD dwThreadID; // Create an event // g_hevInterrupt = CreateEvent(NULL, FALSE, FALSE, NULL); if(!g_hevInterrupt) return 10; // Have the OAL Translate the IRQ to a system irq // fRetVal = KernelIoControl( IOCTL_HAL_TRANSLATE_IRQ, &dwIrq, sizeof( dwIrq ), &g_dwSysInt, sizeof( g_dwSysInt ), NULL ); if( !fRetVal )return 11; // Create a thread that waits for signaling // g_htIST = CreateThread(NULL,// CE Has No Security 0, // No Stack Size ThreadIST,// Interrupt Thread NULL,// No Parameters CREATE_SUSPENDED,// Create Suspended until we are done &dwThreadID // Thread Id ); if( !g_htIST )return 12; // Set the thread priority to real time // int m_nISTPriority = 7; if(!CeSetThreadPriority( g_htIST, m_nISTPriority)) return 13; // Initialize the interrupt // if ( !InterruptInitialize(g_dwSysInt,g_hevInterrupt,NULL,0) )return 14; ResumeThread( g_htIST ); return 0; } DWORD WINAPI ThreadIST( LPVOID lpvParam ) { DWORD dwStatus; // Always chec the running flag // BOOL g_fRun = TRUE; while( g_fRun ) { dwStatus = WaitForSingleObject(g_hevInterrupt, INFINITE); // Make sure we have the object // if( dwStatus == WAIT_OBJECT_0 ) { // Handle Interrupt Here // ::MessageBox (NULL, _T("²âÊÔ!"), _T("¾¯¸æÌáʾ"), MB_ICONQUESTION); // Finish the interrupt // InterruptDone( g_dwSysInt ); } } return 0; } 不知道为什么不能触发 |
|
论坛版主
|
沙发#
发布于:2004-12-31 15:41
你的7(硬件号)号中断的isr里面要返回你申请的sysintr才行
|
|
板凳#
发布于:2004-12-31 16:13
你的7(硬件号)号中断的isr里面要返回你申请的sysintr才行 我是刚刚入行 ,很感谢你的回帖,你的意思我不太懂?请明示 |
|
地板#
发布于:2004-12-31 16:38
dellgao兄弟,怎么没有看到你的中断处理程序isr?是你自己写的吗?只有在你的isr中返回你前面定义的g_dwSysInt值,你的WaitForSingleObject函数才会被释放。
|
|
|
地下室#
发布于:2004-12-31 16:50
dellgao兄弟,怎么没有看到你的中断处理程序isr?是你自己写的吗?只有在你的isr中返回你前面定义的g_dwSysInt值,你的WaitForSingleObject函数才会被释放。 你说的中断服务程序,DWORD WINAPI ThreadIST ( LPVOID lpvParam );这个函数不是吗?你写过给一段源码好吗我参考一下,多谢了 |
|
5楼#
发布于:2005-01-01 01:06
ISR跟IST不是一回事,ISR负责获取硬件中断,再返回系统中断号给IST以触发WaitForSingleObject,ISR源码直接在帮助里找到,改改就行了。
|
|
6楼#
发布于:2005-01-02 10:00
给你讲讲关于硬件中断转换为系统中断的流程你可能就清楚了:(因为我使用的是arm所以抗smdk2410为例。你可以根据你自己的平台来调整)
1。要使用中断必须先注册中断。具体位置在: D:\WINCE420\PLATFORM\SMDK2410\INC\oalintr.h参照wince自带的中断注册即可。 2。将硬件中断变为系统中断 D:\WINCE420\PLATFORM\SMDK2410\KERNEL\HAL\ARM\armint.c 其中函数OEMInterruptHandler是实现硬件中断转换为系统中断的函数。可以参展别的中断产生的方法写你自己的中断。 3。中断与事件的绑定(以串口的为例,你要根据自己的需要写自己的东西。但是使用的函数是一样的): com_init() { PHW_INDEP_INFO pSerialHead = NULL; pSerialHead->hserialevent = CreateEvent (0.FALSE,FALSE,NULL); InterruptInitialize (pSerialhead->pHWObj->dwIntID,//系统中断号 pSerialHead->hserialevent ,NULL,0); )//此函数为中断与事件绑定 pSerialHead->pDispatchThread = CreateThread(NULL,0,IST,pSerialHead,0,NULL);//开一个处理线程 return(pSerialHead); } static DWORD WINAPI IST ( PVOID pContext) { PHW_INDEP_INFO pSerialHead = (PHW_INDEP_INFO )pContext; ULONG WaitReturn; while (!Done()) { WaitReturn = WaitForSingleObject (pSerialHead->hserialevent ,INFINITE); SerialEventHandler(pSerialHead); InterruptDone(pSerialhead->pHWObj->dwIntID); } return(0) } 在这里SerialEventHandler是自己要写的。 4。以上就是是中断处理的具体流程。你可以参考使用。如果有不对的地方请大家补充; |
|
7楼#
发布于:2005-01-04 10:28
To dellgao: 不要着急,其实你离成功只差那么一小步了:)))
我仔细看了一下你给出的代码,还差那么一点点。就是没有把你的硬件中断(7号)和你的ISR相关联。你想想,对于你给出的代码,即使你的硬件已经产生了中断,系统也无法通知你的线程,因为系统怎么会知道你的IST和7号中断有关?所以你还需要做的就是把7号中断与一个ISR相关联,当产生7号中断时,系统会调用这个ISR。这个ISR由你自己来写,一般情况下,ISR只是完成简单的处理工作,主要工作还是由IST来完成。ISR的主要任务: (1)判断这个中断(对于共享中断)是不是由你的硬件产生,如果 不是则直接返回SYSINTR_CHAIN; (2)如果是由你的硬件产生,但不需要再由你的IST做进一步处理,那么返回SYSINTR_NOP就可以了; (3)如果是由你的硬件产生,而且还需要由你的IST做进一步处理,那么要返回g_dwSysInt (这个值是你前面在SetupInterrupt( void )中得到的),返回g_dwSysInt之后,内核会激活与g_dwSysInt关联的事件,这样你的IST中的wait函数就会被释放了。 总结一下: (1)你需要自己的写这个中断的处理函数即ISR,ISR的代码可以参照前面给出的主要任务来写,也可以参考pb里面的例子; (2)在你的SetupInterrupt函数中调用LoadIntChainHandler函数把你的硬件中断(7号)同你写的ISR关联起来。 这样,就可以了,你试试吧,Good Luck. :P :P :P |
|
|
8楼#
发布于:2005-01-04 10:47
给你讲讲关于硬件中断转换为系统中断的流程你可能就清楚了:(因为我使用的是arm所以抗smdk2410为例。你可以根据你自己的平台来调整) "D:WINCE420PLATFORMSMDK2410INCoalintr.h参照wince自带的中断注册即可。 "我找了半天没有找到,请指教?谢谢我是新手 |
|
9楼#
发布于:2005-01-04 11:24
其实,arm和x86架构的平台,中断处理的实现方法的有一定的差别。在WINCE420\\PUBLIC\\COMMON\\OAK\\CSP\\I486\\INC的oalintr.h中定义了OEM所使用的用于irq和sysintr转换的函数,不过这些函数只能用于OAL层。在\\WINCE420\\PUBLIC\\COMMON\\OAK\\INC中的nkintr.h中有sysintr的定义,你可以看看。
其实,你可以按照我前面的方法试试,可以解决你的问题。你只需写一个isr并把这个isr和你的硬件中断相关联即可。 |
|
|
10楼#
发布于:2005-01-04 12:09
PB中提供了许多驱动的源代码,你的isr可以参考GIISR.dll来写,它的源代码位于WINCE420\\PUBLIC\\COMMON\\OAK\\DRIVERS\\GIISR。
|
|
|
11楼#
发布于:2005-01-07 15:59
PB中提供了许多驱动的源代码,你的isr可以参考GIISR.dll来写,它的源代码位于WINCE420\PUBLIC\COMMON\OAK\DRIVERS\GIISR。 这几天忙乎了一大阵子,还是迷茫,我是在EVC环境开发,不是在PB里面做,而且我是对计数器板开发,厂家没有提供驱动, 我的程序要实现的目的如下: 1、硬件环境是一个基于x86的PC104三寸嵌入式板卡 2、pc104的IO卡带有3个计数器 软件要实现的功能就是: 对计数器进行编程,每当计数器完毕时候就触发一个中断 以上就是所要罗嗦的,希望您能给个建议,谢谢! |
|
12楼#
发布于:2005-01-07 16:22
兄弟,如果我没说错的话,你的驱动是用来进行数据采集的?
其实,这个驱动的框架已经出来了(就是你最初写的那些),现在关键的问题是isr,你可以看看我前面给你建议,按照那个做肯定可以的。 |
|
|
13楼#
发布于:2005-01-07 16:50
兄弟,如果我没说错的话,你的驱动是用来进行数据采集的? 我不是做采集的是分频用的,我看了你说的例程,有些迷糊 |
|
14楼#
发布于:2005-01-10 08:40
不管是分频还是数据采集,你的驱动肯定是用来响应外部(定时)中断的。现在的问题是,在你的驱动中,由谁来响应你的外部中断呢?肯定不是ist,因为ist只是用来对中断进行进一步的处理,它是不能和硬件中断直接联系在一起的。直接相应硬件中断的是isr,你需要写这个中断服务例程,并把这个例程(isr)同你的硬件中断关联起来,这样当中断产生的时候,系统就会先调用你的isr,进而执行你的ist线程。如果你还是不太清楚,你就看看pb下面关于installable isr方面的文档吧。
|
|
|