wince下访问io端口的经验

类别:软件工程 点击:0 评论:0 推荐:

我用了一块艾讯的sbc84500的主板(Geode的cpu),用pb定制了一个wince,该主板上有一个8路数字io口,地址为0x123,还具有看门狗的功能。
我打算在我的程序中加入对数字io口的控制,和看门狗的功能。
我首先试验了控制数字io口的功能,我采用了在vc中嵌入汇编语言的方法,代码如下:
void CIOControlDlg::OnButtonSet()
{
 // TODO: Add your control notification handler code here
 //所有的位置1
 __asm
 {
  mov dx,0x123
  mov al,0xff
  out dx,al
 }
 return;
}

void CIOControlDlg::OnButtonClr()
{
 // TODO: Add your control notification handler code here
 //所有的位清0
 __asm
 {
  mov dx,0x123
  mov al,0x0
  out dx,al
 }
 
}
经检测io口的电平,试验成功。

然后,开始试验看门狗的功能,先将主板上的看门狗跳线短接,打开看门狗功能,编写代码:
//io口输出函数
void OutPortByte(WORD addr,BYTE prnch)
{
 _asm
 {
  push ax
  push dx
  mov dx,addr
  mov al,prnch
  out dx,al
  pop dx
  pop ax
   
 }
}
//开始执行看门狗
void CWDTDlg::OnButtonEnableTimer()
{
 // TODO: Add your control notification handler code here
 
 //OUT 120H 0AH ; enter WDT function
 //OUT 120H 0BH ; enable WDT function
 OutPortByte(0x120,0xA);
 OutPortByte(0x120,0xB);
 //OUT 120 0NH ; N=1,2,3 or 4
 OutPortByte(0x120,2);
 //OUT 121 0MH ; M=0,1,2,…F
 OutPortByte(0x121,0);

}
//复位看门狗
void CWDTDlg::OnButtonResetTimer()
{
 // TODO: Add your control notification handler code here
 //OUT 121 0MH ; M=0,1,2,…F
 OutPortByte(0x121,0);
}
//停止看门狗
void CWDTDlg::OnButtonDisableTimer()
{
 // TODO: Add your control notification handler code here
 //OUT 120 00H ; Can be disable at any time
 OutPortByte(0x120,0);
}
程序运行后,发现看门狗不起作用。

我怀疑是手册部分,关于看门狗编程部分的文档有问题,到网上搜索一番,到了艾讯法国的网站上看到了一个页面http://www.axiomtek.fr/faq.php,
里面有关于看门狗的叙述
Question:  How to use DOS command \"Debug\" to trigger WatchDog function of SBC84600?
Answer:  Firstly, please set the Jumper to RESET mode of Watchdog function. And use DOS command \"Debug\" to trigger Watchdog function as below.
-o 120 0a
-o 120 0b
-o 120 02 (N=2)
-o 121 00 (M=0)
The system will reboot after 5 seconds automatically.
Please refer SBC84600 User\'s manual, it provides the detail information about the Watchdog function. 

我按照上面说的进入dos,使用debug,敲入代码,发现看门狗功能正常。

于是再次上网,到各处的wince的论坛里逛一逛,里面关于访问io端口的方法用到MmMapIoSpace,VirtualAlloc\VirtualCopy,
把io口的物理地址映射成虚拟地址,然后对虚拟地址进行操作。
于是参照该方法试一试,我用了MmMapIoSpace,发现在我的pc上,程序不能编译,加入#include <ceddk.h>,#pragma comment(lib,"ceddk.lib")
后,链接程序找不到ceddk.lib。我于是到安装pb的电脑上,找到当初我订制wince的工程目录里,搜寻一番,在" 工程目录\WINCE420\Geode\cesysgen\oak\lib"下面终于找到了ceddk.lib,
原来定制完wince后,产生的sdk好像并没有把所有的头文件和库文件都安装上。至此一切完毕,编译好程序,下载到目标机中运行,成功。
代码如下:
#include <ceddk.h>
#pragma comment(lib,"ceddk.lib")

void OutPortFun(WORD wAddr,byte bValue)
{
 PHYSICAL_ADDRESS IoAddress;
 IoAddress.LowPart = wAddr;//硬件地址
 IoAddress.HighPart = 0;
 UCHAR * gpioPtr;
 gpioPtr = ( UCHAR *)MmMapIoSpace( IoAddress,1,FALSE );
 WRITE_PORT_UCHAR(gpioPtr,bValue);
}
//开始执行看门狗
void CWDTDlg::OnButtonEnableTimer()
{
 // TODO: Add your control notification handler code here
 //OUT 120H 0AH ; enter WDT function
 //OUT 120H 0BH ; enable WDT function
 OutPortFun(0x120,0xA);
 OutPortFun(0x120,0xB);
 //OUT 120 0NH ; N=1,2,3 or 4
 OutPortFun(0x120,2);
 //OUT 121 0MH ; M=0,1,2,…F
 OutPortFun(0x121,0);

}
//停止看门狗
void CWDTDlg::OnButtonDisableTimer()
{
 // TODO: Add your control notification handler code here
 //OUT 120 00H ; Can be disable at any time
 OutPortFun(0x120,0);
}
//复位看门狗
void CWDTDlg::OnButtonResetTimer()
{
 // TODO: Add your control notification handler code here
 //OUT 121 0MH ; M=0,1,2,…F
 OutPortFun(0x121,0);
}

 

本文地址:http://com.8s8s.com/it/it32728.htm