第一次写东西,把前段时间在做的一个小项目整理一下吧。 做的是windows下实现IO口的操作,实现人体感应,让程序和系统能根据人体感应器来做一些动作。
首先要知道的是,主板上的gpio针脚的物理地址,这个可以看下主板说明书。
由于windows不能像linux一样直接操作底层,所以有位牛人写了一个winio库,winio库通过使用内核模式下设备驱动程序和其它一些底层编程技巧绕过windows安全保护机制,允许32位windows程序直接对I/O口进行操作。WinIo包含了3个文件:WinIo.dll、WinIo.sys、WinIo.lib和WINIO.VXD,其中WINIO.VXD驱动程序用在Win95/98系统上,WinIo.sys驱动程序用在WinNT/2000/XP系统上,WinIo.dll提供了功能函数的调用。在 WinIo.dll中有两个函数最重要:InitializeWinIo用来初始化WinIo的驱动程序,必须在调用所有其它功能函数之前调用该函数;ShutdownWinIo用来卸载WinIo的驱动程序,在中止应用函数之前或者不再需要使用WinIo时调用。在初始化完成之后就可以直接读写 I/O端口而不会出现非法操作,winio库现在更新到3.0了,去百度google一下就能找到了。
举个例子直接贴代码吧,例子是参考了他人的思路,如果侵权请联系。
比如这个例子程序实现的功能是,当有人过来的时候,系统就修改下分辨率,只是个例子啦,当然真正用的话没那么无聊。
#ifndef WINIOTEST_H
#define WINIOTEST_H
#pragma once
#include
#include
#include
#include
class CONTROL{
protected:
HWND hwndDialog;
int ReadByteFromEC(int offset, char *pdata);
int WriteByteToEC(int offset, char data);
public:
CONTROL(HINSTANCE );
~CONTROL();
};
#endif //WINIOTEST_H
#include
#include
#include "winio.h"
#include "winiotest.h"
#include
#include "stdafx.h"
using namespace std;
// Registers of the embedded controller
#define GPIO_BASE_ADDRESS 0x500
#define EC_DATAPORT 0x0e // EC data io-port
#define EC_CTRLPORT 0x0c // EC control io-port
// Embedded controller status register bits
#define EC_STAT_OBF 0x01 // Output buffer full
#define EC_STAT_IBF 0x02 // Input buffer full
#define EC_STAT_CMD 0x08 // Last write was a command write (0=data)
// Embedded controller commands
// (write to EC_CTRLPORT to initiate read/write operation)
#define EC_CTRLPORT_READ (char)0x80
#define EC_CTRLPORT_WRITE (char)0x81
#define EC_CTRLPORT_QUERY (char)0x84
int verbosity= 0; // verbosity for the logbuf (0= nothing)
char lasterrorstring[256]= "",
logbuf[8192]= "";
void GetScrnEERO(LONG i)
{
/*switch(i)
{
case 0:
cout << "**********"<
<< "修改成功"<
<< "**********"<
0) sprintf(logbuf+strlen(logbuf), "waitportstatus: tick port= %02x, status= %02x => data was %02x\n", port, bits, data); if (!done) { strcpy(lasterrorstring, "waitportstatus: GetPortValue failed"); break; } // check for desired result int flagstate= (((char)data) & bits)!=0, wantedstate= onoff!=0; if (flagstate==wantedstate) { ok= true; break; } // try again after a moment ::Sleep(tick); } if (!ok && strlen(lasterrorstring)==0) { sprintf(lasterrorstring, "waitportstatus: timeout waiting for port %02x to change to status %02x/%d", port, bits, onoff); } if (!ok) { sprintf(logbuf+strlen(logbuf), "waitportstatus returns failed: ok= %d\n", ok); } return ok; } //------------------------------------------------------------------------- // write a character to an io port through WinIO device //------------------------------------------------------------------------- int writeport(int port, char data) { strcpy(lasterrorstring, ""); // write byte via WINIO.SYS int done= SetPortVal(port, data, 1); if (!done) { sprintf(lasterrorstring, "writeport: port %02x, data %02x failed\n", port, data); } if (verbosity>1) { sprintf(logbuf+strlen(logbuf), "writeport port= %02x, data= %02x, done= %d\n", port, data, done); } return done; } //------------------------------------------------------------------------- // read a character from an io port through WinIO device //------------------------------------------------------------------------- int readport(int port, char *pdata) { DWORD data= -1; // read byte via WINIO.SYS int done= GetPortVal(port, &data, 1); if (done) { *pdata= (char)data; } else { sprintf(lasterrorstring, "readport: port %02x failed\n", port, data); } if (verbosity>1) sprintf(logbuf+strlen(logbuf), "readport port= %02x, data= %02x, done= %d\n", port, (char)data, done); return done; } void main(int offset, char *pdata) { DWORD dwPortVal; DWORD rc = 0; int port; int ok; // Call InitializeWinIo to initialize the WinIo library. //声明一个结构 DEVMODE dmScreenSettings; ; DWORD widthShao = 0,heightShao = 0; memset(&dmScreenSettings,0,sizeof(dmScreenSettings)); dmScreenSettings.dmSize = sizeof(dmScreenSettings); //显示图形设备 EnumDisplaySettings(NULL, ENUM_CURRENT_SETTINGS, &dmScreenSettings); int i = 0; BOOL bRetvol; DEVMODE demove; do { bRetvol = EnumDisplaySettings(NULL,i,&demove); i++; if(bRetvol) { if ((demove.dmPelsWidth != widthShao || demove.dmPelsHeight != heightShao) &&(demove.dmPelsWidth >= 800 &&demove.dmPelsHeight >= 600)) { widthShao = demove.dmPelsWidth; heightShao= demove.dmPelsHeight; //cout<< endl<
<<"*"<
<
在编译的时候记得把winio.lib加到项目中,不然会编译不过去。