?? geek hideout -- io_dll.htm
字號(hào):
80x86 assembly programming just because they want to turn on a
lamp from their computer. However, the unwillingness to learn
assembly language becomes rather trivial when faced with 9x's
big brother.
<P>Windows NT/2000/XP, being the secure operating system that
it is, does not permit port I/O operations at the application
level at all. Period. A program with inline IN and OUT
assembly instructions that runs perfectly on Windows 95/98
will fail horribly when it comes to Windows NT/2000/XP.
<P>Windows NT/2000/XP does, however, allow I/O instructions in
its kernel mode drivers. A kernel mode driver runs at the most
priviledged level of the processor and can do whatever it
pleases, including screwing up the system beyond repair, thus
writing a kernel mode driver is not for the feint of heart.
<P>If you were to take it upon yourself to wade through the
documentation of the Windows NT/2000/XP ddk and piece together
a driver that was callable by your application to do the I/O
instructions on behalf of your application, you'd probably
notice something not too pleasant--this sort of access is
painfully slow. The call from application level to system
level typically takes about one millisecond. Compare this to
the one microsecond that a normal I/O access takes. To further
the insult, you are at the whim of the operating system. If it
has tasks which it believes are of higher priority than your
lowly call to your driver, it will perform them, making
precise timing nearly impossible.
<P>Obviously, writing a driver that does acts a proxy for the
I/O calls isn't the most ideal solution. There is, however, a
solution for NT/2000/XP that allows the same convienience of
inline assembly language that 95/98 does.
<P>As mentioned, a kernel mode driver can do whatever it
wants. The implication here is that if another kernel mode
driver shut off application access to the I/O ports, it should
be possible for another kernel mode driver to turn it back on.
This is where IO.DLL enters the picture.
<P>
<H4>Licensing</H4>IO.DLL is completely free! However, you may
not:
<UL>
<LI>Charge others for it in any way. For example, you cannot
sell it as a stand alone product.
<LI>Charge for an IO.DLL wrapper, such as an OCX or Delphi
control whose purpose is just to put a fancy interface on
IO.DLL. I consider these to be "derived works" and they must
be provided free of charge.
<LI>Claim that it is your property. </LI></UL>Also, the author
(that's me) cannot be held liable due to io.dll's failure to
perform. As with most free stuff, you are on your own.
<P>
<P>
<H4>Source Code and Special Modifications</H4>The source code
is available for $1,000 US.
<P>I'm willing to work with people should they require a
special modification to IO.DLL. For example, you might have a
strict timing requirement of some sort that can only be done
in kernel mode. For a fee, I will modify IO.DLL and/or the
embedded kernel mode driver for the task at hand.
<P>
<H4>Description of IO.DLL</H4>
<P>IO.DLL provides a useful set of commands for reading and
writing to the I/O ports. These commands are consistent
between 95/98 and NT/2000/XP. Furthermore, there is no need
for the programmer to learn assembly language or muck with
kernel mode drivers. Simply link to the DLL and call the
functions. It's that easy.
<P>Windows NT/2000/XP is accomodated through the use of a
small kernel mode driver that releases the ports as needed to
the application. This driver is embedded in the DLL and is
installed if Windows NT/2000/XP is determined to be the
underlying operating system.
<P>Due to the very minor overhead involved in dynamically
linking to IO.DLL, and the optimized functions contained
within, access to I/O ports is nearly as fast as if it was
written in raw assembler and inlined in your application. This
holds true for both Windows 95/98 and Windows NT/2000/XP.
<P>Before moving on, it is probably prudent to mention that
the technique employed in IO.DLL for releasing the ports to
the application level isn't, strictly speaking, the proper way
to do things. The proper way is to have a virtual device
driver for Windows 95/98 and a kernel mode driver for Windows
NT/2000/XP. This isn't very practical for many people though,
nor is it really necessary. There are several successful
commercial products on the market that do exactly what IO.DLL
does. Let it be noted though that some of them are shady with
their explanation of how their product works, meanwhile
charging $500 or more for it.
<P>
<H4>Download</H4>
<P><A
href="http://www.geekhideout.com/downloads/io.zip">io.zip</A>
46k (Contains all the files) <BR><A
href="http://www.geekhideout.com/downloads/io.dll">io.dll</A>
46k
<P>The following two files are for C++ users. There is more
info on these in the prototypes section.<BR>
<P><A
href="http://www.geekhideout.com/downloads/io.cpp">io.cpp</A>
1k <BR><A
href="http://www.geekhideout.com/downloads/io.h">io.h</A> 1k
<H4>C/C++ Prototypes</H4><PRE>void WINAPI PortOut(short int Port, char Data);
void WINAPI PortWordOut(short int Port, short int Data);
void WINAPI PortDWordOut(short int Port, int Data);
char WINAPI PortIn(short int Port);
short int WINAPI PortWordIn(short int Port);
int WINAPI PortDWordIn(short int Port);
void WINAPI SetPortBit(short int Port, char Bit);
void WINAPI ClrPortBit(short int Port, char Bit);
void WINAPI NotPortBit(short int Port, char Bit);
short int WINAPI GetPortBit(short int Port, char Bit);
short int WINAPI RightPortShift(short int Port, short int Val);
short int WINAPI LeftPortShift(short int Port, short int Val);
short int WINAPI IsDriverInstalled();
</PRE>To use IO.DLL with Visual C++/ Borland C++, etc, you'll
need to use LoadLibrary and GetProcAddress. Yes, it's more of
a pain than using a .lib file, but because of name mangling,
it's the only reliable way of calling the functions in IO.DLL.
I've gone ahead and done the dirty work for you:
<P><A
href="http://www.geekhideout.com/downloads/io.cpp">io.cpp</A><BR><A
href="http://www.geekhideout.com/downloads/io.h">io.h</A>
<P>Just save these two files and include them in your project.
For a Visual C++, you may need to add #include "StdAfx.h" at
the top of io.cpp otherwise the compiler will whine at you.
<P>These two files take care of calling LoadLibrary and all
the neccessary calls to GetProcAddress, making your life happy
once again.
<P>The only step you are required to do is call
<B>LoadIODLL</B> somewhere at the beginning of your program.
Make sure you do this or you will find yourself faced with all
sorts of interesting crashes.
<P>Please let me know if you find any errors in the above two
files. They are new and haven't been tested all that much.
<P>
<H4>Delphi Prototypes</H4><PRE>procedure PortOut(Port : Word; Data : Byte);
procedure PortWordOut(Port : Word; Data : Word);
procedure PortDWordOut(Port : Word; Data : DWord);
function PortIn(Port : Word) : Byte;
function PortWordIn(Port : Word) : Word;
function PortDWordIn(Port : Word) : DWord;
procedure SetPortBit(Port : Word; Bit : Byte);
procedure ClrPortBit(Port : Word; Bit : Byte);
procedure NotPortBit(Port : Word; Bit : Byte);
function GetPortBit(Port : Word; Bit : Byte) : WordBool;
function RightPortShift(Port : Word; Val : WordBool) : WordBool;
function LeftPortShift(Port : Word; Val : WordBool) : WordBool;
function IsDriverInstalled : Boolean;
</PRE><B>Important!</B> To use these functions in your Delphi
program, the correct calling convention of stdcall is
required. For example:
<P><PRE>procedure PortOut(Port : Word; Data : Byte); stdcall; external 'io.dll';
</PRE>
<H4>Visual Basic Prototypes</H4><FONT
face="courier new, courier, times" size=-1>Private Declare Sub
PortOut Lib "IO.DLL" (ByVal Port As Integer, ByVal Data As
Byte)<BR>Private Declare Sub PortWordOut Lib "IO.DLL" (ByVal
Port As Integer, ByVal Data As Integer)<BR>Private Declare Sub
PortDWordOut Lib "IO.DLL" (ByVal Port As Integer, ByVal Data
As Long)<BR>Private Declare Function PortIn Lib "IO.DLL"
(ByVal Port As Integer) As Byte<BR>Private Declare Function
PortWordIn Lib "IO.DLL" (ByVal Port As Integer) As
Integer<BR>Private Declare Function PortDWordIn Lib "IO.DLL"
(ByVal Port As Integer) As Long<BR>Private Declare Sub
SetPortBit Lib "IO.DLL" (ByVal Port As Integer, ByVal Bit As
Byte)<BR>Private Declare Sub ClrPortBit Lib "IO.DLL" (ByVal
Port As Integer, ByVal Bit As Byte)<BR>Private Declare Sub
NotPortBit Lib "IO.DLL" (ByVal Port As Integer, ByVal Bit As
Byte)<BR>Private Declare Function GetPortBit Lib "IO.DLL"
(ByVal Port As Integer, ByVal Bit As Byte) As
Boolean<BR>Private Declare Function RightPortShift Lib
"IO.DLL" (ByVal Port As Integer, ByVal Val As Boolean) As
Boolean<BR>Private Declare Function LeftPortShift Lib "IO.DLL"
(ByVal Port As Integer, ByVal Val As Boolean) As
Boolean<BR>Private Declare Function IsDriverInstalled Lib
"IO.DLL" As Boolean<BR></FONT>
<H4>Function Descriptions</H4>Please refer to the prototype
for the particular language you are using.
<P><B>PortOut</B><BR>Outputs a byte to the specified port.
<P><B>PortWordOut</B><BR>Outputs a word (16-bits) to the
specified port.
<P><B>PortDWordOut</B><BR>Outputs a double word (32-bits) to
the specified port.
<P><B>PortIn</B><BR>Reads a byte from the specified port.
<P><B>PortWordIn</B><BR>Reads a word (16-bits) from the
specified port.
<P><B>PortDWordIn</B><BR>Reads a double word (32-bits) from
the specified port.
<P><B>SetPortBit</B><BR>Sets the bit of the specified port.
<P><B>ClrPortBit</B><BR>Clears the bit of the specified port.
<P><B>NotPortBit</B><BR>Nots (inverts) the bit of the
specified port.
<P><B>GetPortBit</B><BR>Returns the state of the specified
bit.
<P><B>RightPortShift</B><BR>Shifts the specified port to the
right. The LSB is returned, and the value passed becomes the
MSB.
<P><B>LeftPortShift</B><BR>Shifts the specified port to the
left. The MSB is returned, and the value passed becomes the
LSB.
<P><B>IsDriverInstalled</B><BR>Returns non-zero if io.dll is
installed and functioning. The primary purpose of this
function is to ensure that the kernel mode driver for
NT/2000/XP has been installed and is accessible.
<P>
<H4>Other Information</H4>An excellent document about the
standard parallel port can be found <A
href="http://www.timgoldstein.com/CNC/ParallelPortPrimer.htm">here</A>.
</TD></TR></TBODY></TABLE><!-- end actual content --></TD>
<TD width=11
background="Geek Hideout -- IO_DLL.files/ver-rt.gif"><IMG height=11
src="Geek Hideout -- IO_DLL.files/ver-rt.gif" width=11></TD>
<TR>
<TD width=11><IMG height=11
src="Geek Hideout -- IO_DLL.files/ll.gif" width=11></TD>
<TD align=right width="100%"
background="Geek Hideout -- IO_DLL.files/hor-bt.gif"><IMG height=11
src="Geek Hideout -- IO_DLL.files/bt.gif" width=11></TD>
<TD width=11><IMG height=11
src="Geek Hideout -- IO_DLL.files/lr.gif"
width=11></TD></TR></TBODY></TABLE><!-- end content --><!-- begin footer table -->
<TABLE cellSpacing=0 cellPadding=0 width="100%" bgColor=#1285c2
border=0><TBODY>
<TR>
<TD width=11><IMG height=11
src="Geek Hideout -- IO_DLL.files/ul.gif" width=11></TD>
<TD align=right width="100%"
background="Geek Hideout -- IO_DLL.files/hor-tp.gif"><IMG height=11
src="Geek Hideout -- IO_DLL.files/tt.gif" width=11></TD>
<TD width=11><IMG height=11
src="Geek Hideout -- IO_DLL.files/ur.gif" width=11></TD></TR>
<TR>
<TD background="Geek Hideout -- IO_DLL.files/ver-lt.gif"><IMG
height=11 src="Geek Hideout -- IO_DLL.files/ver-lt.gif" width=11></TD>
<TD>
<TABLE cellSpacing=0 cellPadding=0 width="100%" border=0>
<TBODY>
<TR>
<TD class=menu vAlign=top>© Copyright 2000-2003 Geek
Hideout<BR>System load: 2.39, 1.12, 0.47 | Current Visitors: 3
</TD>
<TD class=menu
align=right>http://www.geekhideout.com/iodll.shtml<BR>Last
modified on July 11, 2003</TD></TR></TBODY></TABLE></TD>
<TD background="Geek Hideout -- IO_DLL.files/ver-rt.gif"><IMG
height=11 src="Geek Hideout -- IO_DLL.files/ver-rt.gif" width=11></TD>
<TR>
<TD width=11><IMG height=11
src="Geek Hideout -- IO_DLL.files/ll.gif" width=11></TD>
<TD align=right width="100%"
background="Geek Hideout -- IO_DLL.files/hor-bt.gif"><IMG height=11
src="Geek Hideout -- IO_DLL.files/hor-bt.gif" width=11></TD>
<TD width=11><IMG height=11
src="Geek Hideout -- IO_DLL.files/lr.gif"
width=11></TD></TR></TBODY></TABLE><!-- end footer table --></TD></TR></TBODY></TABLE><!-- end outer table --></BODY></HTML>
?? 快捷鍵說明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號(hào)
Ctrl + =
減小字號(hào)
Ctrl + -