Programmer’s Guide

Ikon 10115 & 10117
Windows NT Parallel Class Driver
Revision 1.05


The Ikon 10115/10117 hardcopy interface is a high performance parallel interface capable of driving either Centronics or Versatec (VPI) compatible printers and plotters. The cards do not have a standard parallel port register set, and they require a custom device driver to allow them to operate under Windows NT 3.51 or Windows NT 4.00. The parallel class driver, IKONPCI.SYS, provided by Moxie Technologies, Inc. is just such a device driver.

IKONPCI.SYS supports the following features:

This document covers installation and operation of IKONPCI.SYS. It assumes that the reader is a developer familiar with the following: Installation Installation of the IKONPCI.SYS driver under Windows NT is straightforward. Simply copy the driver into the "\WINNT\SYSTEM32\DRIVERS" directory and add the following registry keys and their values to HKEY_LOCAL_MACHINE (the file IKONPCI.INI can be used with the NT DDK utility "REGINI.EXE" to load the registry values):
Value Name: Value Type: Value Data:
ErrorControl REG_DWORD 0
Group REG_SZ Extended base

Value Name: Value Type: Value Data:
BreakOnEntry REG_DWORD 0
DebugLevel REG_DWORD 0
PortSpeed REG_DWORD 1

Value Name: Value Type: Value Data:
TypesSupported REG_DWORD 7
EventMessageFile REG_EXPAND_SZ %SystemRoot%\System32\IoLogMsg.dll;%SystemRoot%\System32\Drivers\Ikonpci.sys
Values within the Parameters subkey may be changed to customize Win32 device names or to change the default port speed (0-3 with 0 being the fastest). The BreakOnEntry and DebugLevel values are used when debugging IKONPCI.SYS. They should not be changed unless you have the source code to IKONPCI.SYS and are doing development work. Please note that you should NOT attempt to stop/restart the IKONPCI.SYS driver if you have chosen "LPT" as either your VPIDosName or your CENTDosName. Choosing "LPT" as a name also causes a single event log error entry from the Parallel driver for every Ikon board which is found. It is best not to use LPT as an Ikon device name.

Once the registry values are set up, restart Windows NT and your Ikon devices should become active. To verify that the Ikon boards have been detected, start the WINOBJ.EXE utility and double click on the DosDevices category. Assuming you used the values outlined above, you will find either "CPTx" or "VPTx" devices (depending on board configuration). Double clicking on these names will show them mapped to "\Device\Ikonpci0" where the 0 is a number indicating the Ikon board number. Please note that this number should remain constant as long as boards are not moved due to the way PCI bus enumeration is handled within IKONPCI.SYS.

Win32 Interface When strapped for Centronics (or strapped for VPI with the Ikon 10115 "Default Mode" switch set to "PRINT") the IKONPCI.SYS driver can be used with the Windows NT 3.51 printing subsystem without the need for a custom spooler. When used in VPI plot mode or with custom applications the IKONPCI.SYS driver must be driven by a custom spooler through Win32.

Custom spoolers for the Ikon board are nothing more than Win32 applications, DLLs, or services which use CreateFile, WriteFile, DeviceIoControl, and CloseHandle to manage an Ikon device object. This section covers the use of each of these functions with IKONPCI.SYS.

CreateFile Windows NT will have one or more Ikon device objects with a name such as "\Device\Ikonpci0", and each of these objects will be mapped to one or more DOS device names such as "VPT1". This DOS device name can be used with CreateFile to open the Ikon device object as follows:

hfileIkon = CreateFile

This is the recommended way to open an Ikon board. Some points to consider:

If the call fails INVALID_HANDLE_VALUE is returned and, as usual, GetLastError() must be used to determine the cause of the failure (which is most likely that the device does not exist or someone else already has it open).

The handle returned by a successful CreateFile call is used in each of the subsequent Win32 calls. A successful CreateFile call initializes the Ikon board as follows:

WriteFile Once a device object is opened with CreateFile, the returned handle can be used to call WriteFile to move data into the Ikon FIFOs. The prototype for WriteFile is as follows:

BOOL WriteFile
LPCVOID lpBuffer,
DWORD nNumberOfBytesToWrite,
LPDWORD lpNumberOfBytesWritten,

There are no restrictions on the use of this function as long as the Win32 documentation is followed. Overlapped I/O is supported. Please note that WriteFile calls complete as soon as the last byte of a user buffer is written to the Ikon 10115 FIFO, not when the last byte of the user buffer is written to the peripheral. To wait for data to move to a device, use the DeviceIoControl call IHCPIO_RDY_WAIT.

DeviceIoControl Most of the operations which require the use of a custom spooler are handled by this function. DeviceIoControl calls are prototyped in Win32 as follows:

BOOL DeviceIoControl
HANDLE hDevice,
DWORD dwIoControlCode,
LPVOID lpInBuffer,
DWORD nInBufferSize,
LPVOID lpOutBuffer,
DWORD nOutBufferSize,
LPDWORD lpBytesReturned,

The DeviceIoControl function is called exactly as described in the Win32 documentation (including the use of overlapped I/O). However, to make the calls Ikon specific, however, you need the IKONPCI.SYS I/O control codes. These are found in the include file IKONCTL.H (see the file for definitions of constants below). To use this file include <winioctl.h> from the NT SDK include directory to resolve the CTL_CODE macros. Once included you will have access to the following functions:

Control Code Dir Description
IHCPIO_DEV_RESET N/A resets board, clears fifo, resets attached device
IHCPIO_SET_CONFIG IN select device timing and busy mode
IHCPIO_SET_DMATIME IN set DMA timeout in seconds (not implemented)
IHCPIO_SET_FIFOTIME IN set fifo<1/2 full and fifo empty+device timeout
IHCPIO_GET_STATUS OUT return device status
IHCPIO_GET_BOARD OUT return board type
IHCPIO_SET_VMODE IN set versatec print/plot/spp mode
IHCPIO_SET_AUTOLTR IN set auto-ltr width or disable it (versatec only)
IHCPIO_V_CMD IN send pulse command to plotter (versatec only)
IHCPIO_DATA_OUT IN manually send up to 255 bytes to Ikon FIFO
IHCPIO_RDY_WAIT N/A wait for fifo empty and device ready
IHCPIO_HALF_WAIT N/A wait for fifo less than 1/2 full
IHCPIO_STREAM_ON N/A select data streaming mode (centronics only)
IHCPIO_STREAM_OFF N/A clear data streaming mode (centronics only)
IHCPIO_GET_FLAGS OUT returns unit_flags (not implemented)
IHCPIO_GET_FIFO OUT returns fifo status
IHCPIO_SOFT_ACK N/A simulates ack sequence from device
IHCPIO_MASTER_CLEAR N/A resets board and clears fifo
IHCPIO_GET_REGS OUT return board's registers in array of 8 DWORDS
In the above table, "N/A" indicates that no data is required for the command to complete. lpInBuffer, nInBufferSize, lpOutBuffer, and nOutBufferSize are all ignored and are not checked for consistency. Unless otherwise noted, "IN" means that a single DWORD value is sent to the driver (nInBufferSize=4), and "OUT" means that a single DWORD value is returned from the driver (nOutBufferSize=4).


This command resets the Ikon 10115 board with a master clear, and resets the attached device with a 1m s pulse on either INPUT PRIME (Centronics) or RESET (Versatec). The master clear means that the current contents of the FIFO are lost, but the settings associated with previous IHCPIO_SET_* and IHCPIO_STREAM_* calls are maintained.

As implied above, this IOCTL does not wait for the FIFO to drain before it does its work (if it did it couldn’t be used to clear hung devices, etc.). The IHCPIO_RDY_WAIT call can be used to synchronize resets with FIFO/device events.

This call may cause the PRINT line to momentarily toggle (the time between the master clear and the restoration of the original setting is the gray area). This should not cause problems for most devices, but the application writer should be aware of the behavior.


This command sets the current speed and handshaking options. The single DWORD sent to the driver consists of a speed constant (IHCPIO_SPEED[0-3]) possibly combined with handshaking options (IHCPIO_IGNORE_BUSY, IHCPIO_USE_BUSY, IHCPIO_FOUR_EDGE). All data in the Ikon FIFO at the time this command is issued will be sent before the speed change takes effect. This means that there could be a momentary break in output when the FIFO drains. Please see the Ikon 10115 hardcopy interface documentation for a description of the various speed and handshaking options.


IHCPIO_SET_DMATIME is not currently implemented and will return success no matter how it is called. Do not rely on it for anything at the present time.

The following commands directly or indirectly wait for either FIFO half full or FIFO empty and ready events (possibly multiple times) in order to complete: IHCPIO_SET_VMODE*, IHCPIO_V_CMD, IHCPIO_DATA_OUT, IHCPIO_*_WAIT, IHCPIO_STREAM_*. In addition, calls to WriteFile must also wait for FIFO not half full events one or more times. The IHCPIO_SET_FIFOTIME call sets the overall time that these commands will wait before timing out due to lack of movement of data through the FIFO.

Both WriteFile and DeviceIoControl calls which timeout will fail, and the return from GetLastError() will reflect the nature of the timeout (for example, device busy, device fault, or no paper). The FIFO is not cleared with these errors, but the application has no indication of how much data actually made it into the FIFO before the error occurred. Most applications abort spooling at this point and issue a IHCPIO_DEV_RESET to clear the Ikon board and, hopefully, the attached device.


Returns a formatted DWORD containing the bitwise-or of any of the following flags:

Flag Description
IHCPIO_DEV_RDY Versatec READY or Centronics ACK asserted
IHCPIO_DEV_BUSY Centronics asserting BUSY
IHCPIO_DEV_FAULT Centronics asserting FAULT
IHCPIO_DEV_POUT Versatec or Centronics asserting NO_PAPER
IHCPIO_DEV_SEL Versatec ONLINE or Centronics SELECT asserted
This status byte is returned immediately after any commands submitted ahead of it complete. For example, if you performed an overlapped WriteFile immediately followed by an overlapped DeviceIoControl with this command, the status word would be formed and returned after the WriteFile completed, but possibly before all the data from that WriteFile has made it out of the FIFO to the device. For this reason, it is best not to try to determine a devices status by using this function unless you have first used IHCPIO_RDY_WAIT. If you use it earlier, you may get false results (an indication the device is ready when it is really about to go not-ready).


Returns a flag (IHCPIO_VERS_DIFF, IHCPIO_VERS_TTL or IHCPIO_CENT) which indicates how the Ikon 10115 is currently strapped. This can be called at any time.


This Vesatec-only command allows the application to change the PRINT/PLOT/SPP mode of the VPI interface. Typically, only PRINT and PLOT are used. In order to force the change, pass the address of a DWORD set to one of the following values: IHCPIO_V_SPP, IHCPIO_V_PLOT, IHCPIO_V_NPRINT.

These commands are actually fed through the FIFO like data (see the Ikon manual for more information). This means that the mode change DeviceIoControl call may succeed well before the mode actually changes. A WriteFile/DeviceIoControl/WriteFile (regardless of whether the calls were made with overlapped I/O) will send all of the first WriteFile’s data normally, followed by the VMODE change, followed by all of the second WriteFile’s data using the new mode. Another side effect of going through the FIFO is that these commands may timeout like normal data writes.


This Versatec-only IOCTL is used to enable or disable auto remote-line-terminate. The Ikon board is capable of automatically sending a remote-line-terminate command after every ndw bytes of data. The argument for this IOCTL command is actually ndw and must be between 1 and 0x10000 inclusive. Passing 0 to this IOCTL causes auto-ltr to be disabled in which case WriteFile commands must be alternated with IHCPIO_V_CMDs to issue the remote-line-terminates.


This Versatec-only IOCTL is used to send VPI remote commands. The allowed remote commands are IHCPIO_VCLR, IHCPIO_VFED, IHCPIO_VEOT, and IHCPIO_VLTR. As with IHCPIO_SET_VMODE*, these commands are sent through the FIFO. When they reach the far end of the FIFO they cause a pulse on the selected VPI remote line. The width of the pulse is the same as the strobe width selected with IHCPIO_SET_CONFIG. See the Ikon documentation for more information on the different timing modes and on the Command register.

NOTE! If you try to use one speed to send a data burst, and another to send the remote commands, you will interrupt the smooth flow of data through the FIFO (because the FIFO must empty before a speed command takes hold). For this reason it is much better to run at a slower speed and issue V_CMDs than it is to try to change speeds dynamically.


This is another back-compatibility IOCTL. It can be used to send up to 255 bytes of data to the Ikon board just as if you had done the equivalent WriteFile (only slower). If at all possible, use of this IOCTL should be avoided in favor of regular WriteFile calls.


These commands efficiently wait for either FIFO half full (applications should never need to use this—it is here for compatibility) or for FIFO empty and device ready. Essentially the IHCPIO_RDY_WAIT puts a thread to sleep until DIRY in the interface status register is asserted.


Neither of these functions takes an argument. They enable or disable data streaming. When enabled, data streaming causes the 10115 to transmit data to the attached plotter as fast as possible, without waiting for a handshake. It is only suitable for devices compatible with this mode (i.e., some Tektronix devices). Note that just like the IHCPIO_SET_VMODE* commands, these commands are sent through the FIFO.


Not implemented. This function is present for back-compatibility with older software based on the Ikon IOCTL set. It simply zeroes the DWORD output buffer.


Returns one of the following: IHCPIO_FIFO_EMPTY (the FIFO is empty), 0 (the FIFO is less than ½ full, but not empty), IHCPIO_FIFO_HALF (the FIFO is more than half full, but not full), or IHCPIO_FIFO_HALF | IHCPIO_FIFO_FULL (the FIFO is full). The function can be used in conjunction with IHCPIO_GET_STATUS to do accurate polled waits without IHCPIO_*_WAIT.


Simulates the receipt of an ACK pulse from a Centronics compatible device, or a false then true sequence on the Versatec READY line. It can be used to restore synchronization with the attached device after a handshake error, or for diagnostic purposes.


This command is the same as the IHCPIO_DEV_RESET command, except that no device reset occurs. The Ikon board is reset and the operating parameters are restored. This function effectively clears the FIFO of any data left over from previous commands without changing anything else. This command should not be used in a commercial application as it is primarily diagnostic in nature.


This function requires the output buffer to point at an array of 8 DWORDs. Upon completion the array is filled with a snapshot of all the readable Ikon registers. The registers are returned as follows:

dwOutRegs[1] = MODE
dwOutRegs[5] = DEVICE STATUS

IHCPIO_GET_REGS is for diagnostic/educational purposes only and should never be relied on in a commercial application. The function is subject to change at any time depending on the needs of the driver author.

CloseHandle When I/O to the Ikon device is completed, the device should be closed using CloseHandle. This call releases the board for use by other applications. Simply terminating your process will also release the object, but CloseHandle is the preferred method of doing things.

CloseHandle( hfileIkon );

Closing the Ikon device does NOT terminate all I/O with the Ikon board. Anything which is in the boards FIFOs continues to move to the device. Closing the device while data is still in the FIFO should be discouraged. The application should wait for completion of all I/O requests before closing the device.