📄 portio.pas
字号:
//*** TDLPortIO: DriverLINX Port IO Driver wrapper component *****************
//** **
//** File: PortIO.pas **
//** **
//** Copyright (c) 1999 John Pappas (DiskDude). All rights reserved. **
//** This software is FreeWare. **
//** **
//** Please notify me if you make any changes to this file. **
//** Email: diskdude@poboxes.com **
//** **
//** **
//** The following resources helped in developing the install, start, stop **
//** and remove code for dynamically opening/closing the DriverLINX WinNT **
//** kernel mode driver. **
//** **
//** "Dynamically Loading Drivers in Windows NT" by Paula Tomlinson **
//** from "Windows Developer's Journal", Volume 6, Issue 5. (C code) **
//** ftp://ftp.mfi.com/pub/windev/1995/may95.zip **
//** **
//** "Hardware I/O Port Programming with Delphi and NT" by Graham Wideman **
//** http://www.wideman-one.com/tech/Delphi/IOPM/index.htm **
//** **
//** **
//** Special thanks to Peter Holm <comtext3@post4.tele.dk> for his **
//** algorithm and code for detecting the number and addresses of the **
//** installed printer ports, on which the detection code below is based. **
//** **
//*** http://diskdude.cjb.net/ ***********************************************
unit PortIO;
interface
uses
Windows, Messages, SysUtils, Classes, WinSvc;
//---------------------------------------------------------------------------
// DLL Import Types
// Pointer to functions, to dynamically link into the DLL
//---------------------------------------------------------------------------
type
Longword = Cardinal; // Delphi 3.0 only
type
PByte = ^Byte;
PWord = ^Word;
PLongword = ^Longword;
type
TDlPortReadPortUchar = function(Port : Word) : Byte; stdcall;
TDlPortReadPortUshort = function(Port : Word) : Word; stdcall;
TDlPortReadPortUlong = function(Port : Word) : Longword; stdcall;
TDlPortWritePortUchar = procedure(Port : Word; Value : Byte); stdcall;
TDlPortWritePortUshort = procedure(Port : Word; Value : Word); stdcall;
TDlPortWritePortUlong = procedure(Port : Word; Value : Longword); stdcall;
TDlPortReadPortBufferUchar = procedure(Port : Word; Buffer : PByte; Count : Longword); stdcall;
TDlPortReadPortBufferUshort = procedure(Port : Word; Buffer : PWord; Count : Longword); stdcall;
TDlPortReadPortBufferUlong = procedure(Port : Word; Buffer : PLongword; Count : Longword); stdcall;
TDlPortWritePortBufferUchar = procedure(Port : Word; Buffer : PByte; Count : Longword); stdcall;
TDlPortWritePortBufferUshort = procedure(Port : Word; Buffer : PWord; Count : Longword); stdcall;
TDlPortWritePortBufferUlong = procedure(Port : Word; Buffer : PLongword; Count : Longword); stdcall;
//---------------------------------------------------------------------------
// Data Types
//---------------------------------------------------------------------------
// Specifies the type of read or write in a TPortCommand
type
TMode = (tmReadByte, tmReadWord, tmReadDWord,
tmWriteByte, tmWriteWord, tmWriteDWord);
// Specifies the data required to do a block
// read/write of an array of port records.
// Extends the model TVicHW32/TVicPort uses
type
TPortCommand = record
PortAddr : Word; // The address of the port to read/write
PortData : Longword; // The data to read/write
// If a byte, only lower 8bits are used, or 16bits
// if reading/writing a word
PortMode : TMode; // The mode of reading/writing
end;
// Standard TVicHW32/TVicPort PortRec for compatibility
type
TPortRec = record
PortAddr : Word; // Address
PortData : Byte; // Data (for writing or after reading)
fWrite : Boolean; // TRUE if you want to write this port
// and FALSE if to read.
end;
//---------------------------------------------------------------------------
// TDLPortIO class
// This is supposed to be compatible with TVicPort
//---------------------------------------------------------------------------
type
TDLPortIO = class(TComponent)
private
FActiveHW : Boolean; // Is the DLL loaded?
FHardAccess : Boolean; // Not used: for compatibility only
FRunningWinNT : Boolean; // True when we're running Windows NT
FDLLInst : THandle; // For use with DLL
hSCMan : SC_HANDLE; // For use with WinNT Service Control Manager
FDriverPath : AnsiString; // Full path of WinNT driver
FDLLPath : AnsiString; // Full path of DriverLINX DLL
FLastError : AnsiString; // Last error which occurred in Open/CloseDriver()
// Used for the Windows NT version only
FDrvPrevInst : Boolean; // DriverLINX driver already installed?
FDrvPrevStart : Boolean; // DriverLINX driver already running?
// Pointers to the functions within the DLL
DlReadByte : TDlPortReadPortUchar;
DlReadWord : TDlPortReadPortUshort;
DlReadDWord : TDlPortReadPortUlong;
DlWriteByte : TDlPortWritePortUchar;
DlWriteWord : TDlPortWritePortUshort;
DlWriteDWord : TDlPortWritePortUlong;
DlReadBufferByte : TDlPortReadPortBufferUchar;
DlReadBufferWord : TDlPortReadPortBufferUshort;
DlReadBufferDWord : TDlPortReadPortBufferUlong;
DlWriteBufferByte : TDlPortWritePortBufferUchar;
DlWriteBufferWord : TDlPortWritePortBufferUshort;
DlWriteBufferDWord : TDlPortWritePortBufferUlong;
// Connects and disconnects to the WinNT Service Control Manager
function ConnectSCM : Boolean;
procedure DisconnectSCM;
// Installs, starts, stops and removes the WinNT kernel mode driver
function DriverInstall : Boolean;
function DriverStart : Boolean;
function DriverStop : Boolean;
function DriverRemove : Boolean;
protected
// returns true if the DLL/Driver is loaded
function IsLoaded : Boolean;
// Wrappers for the properties below
function GetPortByte(Address : Word) : Byte;
procedure SetPortByte(Address : Word; Data : Byte);
function GetPortWord(Address : Word) : Word;
procedure SetPortWord(Address : Word; Data : Word);
function GetPortDWord(Address : Word) : Longword;
procedure SetPortDWord(Address : Word; Data : Longword);
public
constructor Create(Owner : TComponent); override;
destructor Destroy; override;
// These open and close the DLL/Driver
procedure OpenDriver;
procedure CloseDriver;
// Allows write/read array of ports.
procedure PortControl(Ports : array of TPortRec; NumPorts : Word);
procedure PortCommand(Ports : array of TPortCommand; NumPorts : Word);
// Allows read/write array of bytes from single port.
procedure ReadPortFIFO(PortAddr : Word; NumPorts : Word; var Buffer);
procedure WritePortFIFO(PortAddr : Word; NumPorts : Word; var Buffer);
// Extended block read/write routines for WORD and DWORD
procedure ReadWPortFIFO(PortAddr : Word; NumPorts : Word; var Buffer);
procedure WriteWPortFIFO(PortAddr : Word; NumPorts : Word; var Buffer);
procedure ReadLPortFIFO(PortAddr : Word; NumPorts : Word; var Buffer);
procedure WriteLPortFIFO(PortAddr : Word; NumPorts : Word; var Buffer);
// Access any port as you like, similar to the old pascal way of doing things
property Port[Address : Word] : Byte read GetPortByte write SetPortByte;
property PortW[Address : Word] : Word read GetPortWord write SetPortWord;
property PortL[Address : Word] : Longword read GetPortDWord write SetPortDWord;
published
// Sets the path (no ending \, nor any filename) of the DLPortIO.SYS file
// Assumed to be <windows system directory>\DRIVERS if not specified
property DriverPath : AnsiString read FDriverPath write FDriverPath;
// Sets the path (no ending \, nor any filename) of the DLPortIO.DLL file
// Assumed to be "" if not specified, meaning it will search the program
// path, windows directory and computer's path for the DLL
property DLLPath : AnsiString read FDLLPath write FDLLPath;
// True when the DLL/Driver has been loaded successfully after OpenDriver()
property ActiveHW : Boolean read FActiveHW;
// This doesn't really do anything; provided for compatibility only
property HardAccess : Boolean read FHardAccess write FHardAccess default true;
// Returns the last error which occurred in Open/CloseDriver()
property LastError : AnsiString read FLastError;
end;
//---------------------------------------------------------------------------
// Types for the TDLPrinterPortIO class
//---------------------------------------------------------------------------
type
TPinNumber = 1..25;
//---------------------------------------------------------------------------
// TDLPrinterPortIO class
// This is supposed to be compatible with TVicLPT
//---------------------------------------------------------------------------
const
// Maximum number of printer ports
// that would be installed on a system
MAX_LPT_PORTS = 8;
type
TDLPrinterPortIO = class(TDLPortIO)
private
FLPTNumber : Byte; // Current number of the printer port, default=1
FLPTBase : Word; // The address of the current printer port (faster)
FLPTCount : Integer; // Number of LPT ports on the system
// List of port addresses installed on the system
FLPTAddress : array[0..MAX_LPT_PORTS] of Word;
// Detects the printer ports using the registry
procedure DetectPorts;
procedure DetectPorts9x; // Win9x version
procedure DetectPortsNT; // WinNT version
protected
function GetLPTNumPorts : Byte;
function GetLPTBasePort : Word;
procedure SetLPTNumber(Number : Byte);
function GetPin(Index : TPinNumber) : Boolean;
procedure SetPin(Index : TPinNumber; State : Boolean);
function GetLPTAckwl : Boolean;
function GetLPTBusy : Boolean;
function GetLPTPaperEnd : Boolean;
function GetLPTSlct : Boolean;
function GetLPTError : Boolean;
public
constructor Create(Owner : TComponent); override;
// Sends STROBE signal to the printer
procedure LPTStrobe;
// Sends AUTOFD (auto line feed) signal to the printer
procedure LPTAutofd(Flag : Boolean);
// Resets printer by sending INIT signal
procedure LPTInit;
// Sends SLCTIN signal to the printer
procedure LPTSlctIn;
// Sends a character to the printer.
// Returns true on success. Repeat as neccessary.
function LPTPrintChar(Ch : Char) : Boolean;
// Index valid is in the range 1-25 only (other values return false)
// Reading the pin returns true when it is 5V, or false when it at 0V.
// Writing true sets the pin to 5V, or 0V when false.
property Pin[Index : TPinNumber] : Boolean read GetPin write SetPin;
// Returns ACKWL state from the printer
property LPTAckwl : Boolean read GetLPTAckwl;
// Returns BUSY state from the printer
property LPTBusy : Boolean read GetLPTBusy;
// Returns PAPER END state from the printer
property LPTPaperEnd : Boolean read GetLPTPaperEnd;
// Returns SLCT state from the printer
property LPTSlct : Boolean read GetLPTSlct;
// Returns ERROR state from the printer
property LPTError : Boolean read GetLPTError;
published
// Shows how many LPT ports are installed on your PC.
property LPTNumPorts : Byte read GetLPTNumPorts;
// Selects the LPT port to use for all LPT operations
property LPTNumber : Byte read FLPTNumber write SetLPTNumber default 1;
// Returns a base address of the current LPT port.
property LPTBasePort : Word read GetLPTBasePort;
end;
procedure Register;
implementation
//---------------------------------------------------------------------------
// Constants
//---------------------------------------------------------------------------
const
// Masks
BIT0 : Byte = $01;
BIT1 : Byte = $02;
BIT2 : Byte = $04;
BIT3 : Byte = $08;
BIT4 : Byte = $10;
BIT5 : Byte = $20;
BIT6 : Byte = $40;
BIT7 : Byte = $80;
// Printer Port pin numbers
ACK_PIN : Byte = 10;
BUSY_PIN : Byte = 11;
PAPEREND_PIN : Byte = 12;
SELECTOUT_PIN : Byte = 13;
ERROR_PIN : Byte = 15;
STROBE_PIN : Byte = 1;
AUTOFD_PIN : Byte = 14;
INIT_PIN : Byte = 16;
SELECTIN_PIN : Byte = 17;
// DriverLINX DLL filename
LIBRARY_FILENAME : AnsiString = 'DLPortIO.dll';
// WinNT DriverLINX Information
DRIVER_NAME : AnsiString = 'DLPortIO';
DISPLAY_NAME : AnsiString = 'DriverLINX Port I/O Driver';
DRIVER_GROUP : AnsiString = 'SST miniport drivers';
//---------------------------------------------------------------------------
constructor TDLPortIO.Create(Owner : TComponent);
//---------------------------------------------------------------------------
var
os : TOSVersionInfo;
Buffer : array[1..MAX_PATH] of char;
begin
inherited Create(Owner); // Set up our inherited methods, and properties
// Are we running Windows NT?
os.dwPlatformId := 0;
os.dwOSVersionInfoSize := sizeof(os);
GetVersionEx(os);
FRunningWinNT:=(os.dwPlatformId=VER_PLATFORM_WIN32_NT);
// Set default WinNT driver path
GetSystemDirectory(@Buffer, MAX_PATH);
FDriverPath:=Buffer+'\DRIVERS';
// Set the default DLL path
FDLLPath:='';
FActiveHW:=false; // DLL/Driver not loaded
FHardAccess:=true; // Not used, default true
FLastError:=''; // No errors yet
end;
//---------------------------------------------------------------------------
destructor TDLPortIO.Destroy;
//---------------------------------------------------------------------------
begin
// Make sure we close the DLL
if (IsLoaded) then CloseDriver;
inherited Destroy; // Destroy out inherited methods, and properties
end;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -