home *** CD-ROM | disk | FTP | other *** search
/ Freelog Special Edition 1: Linux / CD1.iso / doc / HOWTO / mini / IO-Port-Programming < prev    next >
Text File  |  1998-10-14  |  27KB  |  727 lines

  1.   Linux I/O port programming mini-HOWTO
  2.   Author: Riku Saikkonen <Riku.Saikkonen@hut.fi>
  3.   v, 28 December 1997
  4.  
  5.   This HOWTO document describes programming hardware I/O ports and wait¡
  6.   ing for small periods of time in user-mode Linux programs running on
  7.   the Intel x86 architecture.
  8.   ______________________________________________________________________
  9.  
  10.   Table of Contents
  11.  
  12.  
  13.   1. Introduction
  14.  
  15.   2. Using I/O ports in C programs
  16.  
  17.      2.1 The normal method
  18.      2.2 An alternate method:
  19.  
  20.   3. Interrupts (IRQs) and DMA access
  21.  
  22.   4. High-resolution timing
  23.  
  24.      4.1 Delays
  25.         4.1.1 Sleeping:
  26.         4.1.2 (TT
  27.         4.1.3 Delaying with port I/O
  28.         4.1.4 Delaying with assembler instructions
  29.         4.1.5 (TT
  30.      4.2 Measuring time
  31.  
  32.   5. Other programming languages
  33.  
  34.   6. Some useful ports
  35.  
  36.      6.1 The parallel port
  37.      6.2 The game (joystick) port
  38.      6.3 The serial port
  39.  
  40.   7. Hints
  41.  
  42.   8. Troubleshooting
  43.  
  44.   9. Example code
  45.  
  46.   10. Credits
  47.  
  48.  
  49.  
  50.   ______________________________________________________________________
  51.  
  52.   1.  Introduction
  53.  
  54.   This HOWTO document describes programming hardware I/O ports and
  55.   waiting for small periods of time in user-mode Linux programs running
  56.   on the Intel x86 architecture. This document is a descendant of the
  57.   very small IO-Port mini-HOWTO by the same author.
  58.  
  59.   This document is Copyright 1995-1997 Riku Saikkonen. See the Linux
  60.   HOWTO copyright
  61.   <http://sunsite.unc.edu/pub/Linux/docs/HOWTO/COPYRIGHT> for details.
  62.  
  63.   If you have corrections or something to add, feel free to e-mail me
  64.   (Riku.Saikkonen@hut.fi)...
  65.  
  66.  
  67.   Changes from the previous released version (Mar 30 1997):
  68.  
  69.   ╖  Clarified things regarding inb_p/outb_p and port 0x80.
  70.  
  71.   ╖  Removed information about udelay(), since nanosleep() provides a
  72.      cleaner way of using it.
  73.  
  74.   ╖  Converted to Linuxdoc-SGML, and reorganised somewhat.
  75.  
  76.   ╖  Lots of minor additions and modifications.
  77.  
  78.  
  79.  
  80.   2.  Using I/O ports in C programs
  81.  
  82.   2.1.  The normal method
  83.  
  84.   Routines for accessing I/O ports are in /usr/include/asm/io.h (or
  85.   linux/include/asm-i386/io.h in the kernel source distribution). The
  86.   routines there are inline macros, so it is enough to #include
  87.   <asm/io.h>; you do not need any additional libraries.
  88.  
  89.   Because of a limitation in gcc (present at least in 2.7.2.3 and below)
  90.   and in egcs (all versions), you have to compile any source code that
  91.   uses these routines with optimisation turned on (gcc -O1 or higher),
  92.   or alternatively #define extern to be empty before you #include
  93.   <asm/io.h>.
  94.  
  95.   For debugging, you can use gcc -g -O (at least with modern versions of
  96.   gcc), though optimisation can sometimes make the debugger behave a bit
  97.   strangely. If this bothers you, put the routines that use I/O port
  98.   access in a separate source file and compile only that with
  99.   optimisation turned on.
  100.  
  101.   Before you access any ports, you must give your program permission to
  102.   do so. This is done by calling the ioperm() function (declared in
  103.   unistd.h, and defined in the kernel) somewhere near the start of your
  104.   program (before any I/O port accesses). The syntax is ioperm(from,
  105.   num, turn_on), where from is the first port number to give access to,
  106.   and num the number of consecutive ports to give access to. For
  107.   example, ioperm(0x300, 5, 1) would give access to ports 0x300 through
  108.   0x304 (a total of 5 ports). The last argument is a Boolean value
  109.   specifying whether to give access to the program to the ports (true
  110.   (1)) or to remove access (false (0)). You can call ioperm() multiple
  111.   times to enable multiple non-consecutive ports. See the ioperm(2)
  112.   manual page for details on the syntax.
  113.  
  114.   The ioperm() call requires your program to have root privileges; thus
  115.   you need to either run it as the root user, or make it setuid root.
  116.   You can drop the root privileges after you have called ioperm() to
  117.   enable the ports you want to use. You are not required to explicitly
  118.   drop your port access privileges with ioperm(..., 0) at the end of
  119.   your program; this is done automatically as the process exits.
  120.  
  121.   A setuid() to a non-root user does not disable the port access granted
  122.   by ioperm(), but a fork() does (the child process does not get access,
  123.   but the parent retains it).
  124.  
  125.   ioperm() can only give access to ports 0x000 through 0x3ff; for higher
  126.   ports, you need to use iopl() (which gives you access to all ports at
  127.   once). Use the level argument 3 (i.e., iopl(3)) to give your program
  128.   access to all I/O ports (so be careful --- accessing the wrong ports
  129.   can do all sorts of nasty things to your computer). Again, you need
  130.   root privileges to call iopl(). See the iopl(2) manual page for
  131.   details.
  132.  
  133.   Then, to actually accessing the ports... To input a byte (8 bits) from
  134.   a port, call inb(port), it returns the byte it got. To output a byte,
  135.   call outb(value, port) (please note the order of the parameters).  To
  136.   input a word (16 bits) from ports x and x+1 (one byte from each to
  137.   form the word, using the assembler instruction inw), call inw(x). To
  138.   output a word to the two ports, use outw(value, x). If you're unsure
  139.   of which port instructions (byte or word) to use, you probably want
  140.   inb() and outb() --- most devices are designed for bytewise port
  141.   access. Note that all port access instructions take at least about a
  142.   microsecond to execute.
  143.  
  144.   The inb_p(), outb_p(), inw_p(), and outw_p() macros work otherwise
  145.   identically to the ones above, but they do an additional short (about
  146.   one microsecond) delay after the port access; you can make the delay
  147.   about four microseconds with #define REALLY_SLOW_IO before you
  148.   #include <asm/io.h>. These macros normally (unless you #define
  149.   SLOW_IO_BY_JUMPING, which is probably less accurate) use a port output
  150.   to port 0x80 for their delay, so you need to give access to port 0x80
  151.   with ioperm() first (outputs to port 0x80 should not affect any part
  152.   of the system). For more versatile methods of delaying, read on.
  153.  
  154.   There are man pages for ioperm(2), iopl(2), and the above macros in
  155.   reasonably recent releases of the Linux manual page collection.
  156.  
  157.  
  158.  
  159.   2.2.  An alternate method: /dev/port
  160.  
  161.   Another way to access I/O ports is to open() /dev/port (a character
  162.   device, major number 1, minor 4) for reading and/or writing (the stdio
  163.   f*() functions have internal buffering, so avoid them). Then lseek()
  164.   to the appropriate byte in the file (file position 0 = port 0x00, file
  165.   position 1 = port 0x01, and so on), and read() or write() a byte or
  166.   word from or to it.
  167.  
  168.   Naturally, for this to work your program needs read/write access to
  169.   /dev/port. This method is probably slower than the normal method
  170.   above, but does not need compiler optimisation nor ioperm(). It
  171.   doesn't need root access either, if you give a non-root user or group
  172.   access to /dev/port --- but this is a very bad thing to do in terms of
  173.   system security, since it is possible to hurt the system, perhaps even
  174.   gain root access, by using /dev/port to access hard disks, network
  175.   cards, etc. directly.
  176.  
  177.  
  178.  
  179.   3.  Interrupts (IRQs) and DMA access
  180.  
  181.   You cannot use IRQs or DMA directly from a user-mode process. You need
  182.   to write a kernel driver; see The Linux Kernel Hacker's Guide
  183.   <http://www.redhat.com:8080/HyperNews/get/khg.html> for details and
  184.   the kernel source code for examples.
  185.  
  186.   Also, you cannot disable interrupts from within a user-mode program.
  187.  
  188.  
  189.  
  190.   4.  High-resolution timing
  191.  
  192.   4.1.  Delays
  193.  
  194.   First of all, I should say that you cannot guarantee user-mode
  195.   processes to have exact control of timing because of the multi-tasking
  196.   nature of Linux. Your process might be scheduled out at any time for
  197.   anything from about 10 milliseconds to a few seconds (on a system with
  198.   very high load). However, for most applications using I/O ports, this
  199.   does not really matter. To minimise this, you may want to nice your
  200.   process to a high-priority value (see the nice(2) manual page) or use
  201.   real-time scheduling (see below).
  202.  
  203.   If you want more precise timing than normal user-mode processes give
  204.   you, there are some provisions for user-mode `real time' support.
  205.   Linux 2.x kernels have soft real time support; see the manual page for
  206.   sched_setscheduler(2) for details. There is a special kernel that
  207.   supports hard real time; see  <http://luz.cs.nmt.edu/~rtlinux/> for
  208.   more information on this.
  209.  
  210.  
  211.   4.1.1.  Sleeping: sleep()  and usleep()
  212.  
  213.   Now, let me start with the easier timing calls. For delays of multiple
  214.   seconds, your best bet is probably to use sleep(). For delays of at
  215.   least tens of milliseconds (about 10 ms seems to be the minimum
  216.   delay), usleep() should work. These functions give the CPU to other
  217.   processes (``sleep''), so CPU time isn't wasted. See the manual pages
  218.   sleep(3) and usleep(3) for details.
  219.  
  220.   For delays of under about 50 milliseconds (depending on the speed of
  221.   your processor and machine, and the system load), giving up the CPU
  222.   takes too much time, because the Linux scheduler (for the x86
  223.   architecture) usually takes at least about 10-30 milliseconds before
  224.   it returns control to your process. Due to this, in small delays,
  225.   usleep(3) usually delays somewhat more than the amount that you
  226.   specify in the parameters, and at least about 10 ms.
  227.  
  228.  
  229.   4.1.2.  nanosleep()
  230.  
  231.   In the 2.0.x series of Linux kernels, there is a new system call,
  232.   nanosleep() (see the nanosleep(2) manual page), that allows you to
  233.   sleep or delay for short times (a few microseconds or more).
  234.  
  235.   For delays <= 2 ms, if (and only if) your process is set to soft real
  236.   time scheduling (using sched_setscheduler()), nanosleep() uses a busy
  237.   loop; otherwise it sleeps, just like usleep().
  238.  
  239.   The busy loop uses udelay() (an internal kernel function used by many
  240.   kernel drivers), and the length of the loop is calculated using the
  241.   BogoMips value (the speed of this kind of busy loop is one of the
  242.   things that BogoMips measures accurately). See
  243.   /usr/include/asm/delay.h) for details on how it works.
  244.  
  245.  
  246.   4.1.3.  Delaying with port I/O
  247.  
  248.   Another way of delaying small numbers of microseconds is port I/O.
  249.   Inputting or outputting any byte from/to port 0x80 (see above for how
  250.   to do it) should wait for almost exactly 1 microsecond independent of
  251.   your processor type and speed. You can do this multiple times to wait
  252.   a few microseconds. The port output should have no harmful side
  253.   effects on any standard machine (and some kernel drivers use it). This
  254.   is how {in|out}[bw]_p() normally do the delay (see asm/io.h).
  255.  
  256.   Actually, a port I/O instruction on most ports in the 0-0x3ff range
  257.   takes almost exactly 1 microsecond, so if you're, for example, using
  258.   the parallel port directly, just do additional inb()s from that port
  259.   to delay.
  260.  
  261.  
  262.  
  263.  
  264.  
  265.   4.1.4.  Delaying with assembler instructions
  266.  
  267.   If you know the processor type and clock speed of the machine the
  268.   program will be running on, you can hard-code shorter delays by
  269.   running certain assembler instructions (but remember, your process
  270.   might be scheduled out at any time, so the delays might well be longer
  271.   every now and then). For the table below, the internal processor speed
  272.   determines the number of clock cycles taken; e.g., for a 50 MHz
  273.   processor (e.g. 486DX-50 or 486DX2-50), one clock cycle takes
  274.   1/50000000 seconds (=200 nanoseconds).
  275.  
  276.  
  277.  
  278.        Instruction   i386 clock cycles   i486 clock cycles
  279.        nop                   3                   1
  280.        xchg %ax,%ax          3                   3
  281.        or %ax,%ax            2                   1
  282.        mov %ax,%ax           2                   1
  283.        add %ax,0             2                   1
  284.  
  285.  
  286.  
  287.  
  288.   (Sorry, I don't know about Pentiums; probably close to the i486. I
  289.   cannot find an instruction which would use one clock cycle on an i386.
  290.   Use the one-clock-cycle instructions if you can, otherwise the
  291.   pipelining used in modern processors may shorten the times.)
  292.  
  293.   The instructions nop and xchg in the table should have no side
  294.   effects. The rest may modify the flags register, but this shouldn't
  295.   matter since gcc should detect it. nop is a good choice.
  296.  
  297.   To use these, call asm("instruction") in your program. The syntax of
  298.   the instructions is as in the table above; if you want multiple
  299.   instructions in a single asm() statement, separate them with
  300.   semicolons. For example, asm("nop ; nop ; nop ; nop") executes four
  301.   nop instructions, delaying for four clock cycles on i486 or Pentium
  302.   processors (or 12 clock cycles on an i386).
  303.  
  304.   asm() is translated into inline assembler code by gcc, so there is no
  305.   function call overhead.
  306.  
  307.   Shorter delays than one clock cycle are impossible in the Intel x86
  308.   architecture.
  309.  
  310.  
  311.   4.1.5.  rdtsc  for Pentiums
  312.  
  313.   For Pentiums, you can get the number of clock cycles elapsed since the
  314.   last reboot with the following C code:
  315.  
  316.  
  317.  
  318.        ______________________________________________________________________
  319.           extern __inline__ unsigned long long int rdtsc()
  320.           {
  321.             unsigned long long int x;
  322.             __asm__ volatile (".byte 0x0f, 0x31" : "=A" (x));
  323.             return x;
  324.           }
  325.        ______________________________________________________________________
  326.  
  327.  
  328.  
  329.  
  330.  
  331.   You can poll this value to delay for as many clock cycles as you want.
  332.  
  333.  
  334.  
  335.   4.2.  Measuring time
  336.  
  337.   For times accurate to one second, it is probably easiest to use
  338.   time(). For more accurate times, gettimeofday() is accurate to about a
  339.   microsecond (but see above about scheduling). For Pentiums, the rdtsc
  340.   code fragment above is accurate to one clock cycle.
  341.  
  342.   If you want your process to get a signal after some amount of time,
  343.   use setitimer() or alarm(). See the manual pages of the functions for
  344.   details.
  345.  
  346.  
  347.  
  348.   5.  Other programming languages
  349.  
  350.   The description above concentrates on the C programming language. It
  351.   should apply directly to C++ and Objective C. In assembler, you have
  352.   to call ioperm() or iopl() as in C, but after that you can use the I/O
  353.   port read/write instructions directly.
  354.  
  355.   In other languages, unless you can insert inline assembler or C code
  356.   into the program or use the system calls mentioned above, it is
  357.   probably easiest to write a simple C source file with functions for
  358.   the I/O port accesses or delays that you need, and compile and link it
  359.   in with the rest of your program. Or use /dev/port as described above.
  360.  
  361.  
  362.  
  363.   6.  Some useful ports
  364.  
  365.   Here is some programming information for common ports that can be
  366.   directly used for general-purpose TTL (or CMOS) logic I/O.
  367.  
  368.   If you want to use these or other common ports for their intended
  369.   purpose (e.g., to control a normal printer or modem), you should most
  370.   likely use existing drivers (which are usually included in the kernel)
  371.   instead of programming the ports directly as this HOWTO describes.
  372.   This section is intended for those people who want to connect LCD
  373.   displays, stepper motors, or other custom electronics to a PC's
  374.   standard ports.
  375.  
  376.   If you want to control a mass-market device like a scanner (that has
  377.   been on the market for a while), look for an existing Linux driver for
  378.   it. The Hardware-HOWTO
  379.   <http://sunsite.unc.edu/pub/Linux/docs/HOWTO/Hardware-HOWTO> is a good
  380.   place to start.
  381.  
  382.   <http://www.hut.fi/Misc/Electronics/> is a good source for more
  383.   information on connecting devices to computers (and on electronics in
  384.   general).
  385.  
  386.  
  387.  
  388.   6.1.  The parallel port
  389.  
  390.   The parallel port's base address (called ``BASE'' below) is 0x3bc for
  391.   /dev/lp0, 0x378 for /dev/lp1, and 0x278 for /dev/lp2. If you only want
  392.   to control something that acts like a normal printer, see the
  393.   Printing-HOWTO <http://sunsite.unc.edu/pub/Linux/docs/HOWTO/Printing-
  394.   HOWTO>.
  395.  
  396.  
  397.   In addition to the standard output-only mode described below, there is
  398.   an `extended' bidirectional mode in most parallel ports. For
  399.   information on this and the newer ECP/EPP modes (and the IEEE 1284
  400.   standard in general), see  <http://www.fapo.com/> and
  401.   <http://www.senet.com.au/~cpeacock/parallel.htm>. Remember that since
  402.   you cannot use IRQs or DMA in a user-mode program, you will probably
  403.   have to write a kernel driver to use ECP/EPP; I think someone is
  404.   writing such a driver, but I don't know the details.
  405.  
  406.   The port BASE+0 (Data port) controls the data signals of the port (D0
  407.   to D7 for bits 0 to 7, respectively; states: 0 = low (0 V), 1 = high
  408.   (5 V)). A write to this port latches the data on the pins. A read
  409.   returns the data last written in standard or extended write mode, or
  410.   the data in the pins from another device in extended read mode.
  411.  
  412.   The port BASE+1 (Status port) is read-only, and returns the state of
  413.   the following input signals:
  414.  
  415.   ╖  Bits 0 and 1 are reserved.
  416.  
  417.   ╖  Bit 2 IRQ status (not a pin, I don't know how this works)
  418.  
  419.   ╖  Bit 3 ERROR (1=high)
  420.  
  421.   ╖  Bit 4 SLCT (1=high)
  422.  
  423.   ╖  Bit 5 PE (1=high)
  424.  
  425.   ╖  Bit 6 ACK (1=high)
  426.  
  427.   ╖  Bit 7 -BUSY (0=high)
  428.  
  429.      (I'm not sure about the high and low states.)
  430.  
  431.   The port BASE+2 (Control port) is write-only (a read returns the data
  432.   last written), and controls the following status signals:
  433.  
  434.   ╖  Bit 0 -STROBE (0=high)
  435.  
  436.   ╖  Bit 1 AUTO_FD_XT (1=high)
  437.  
  438.   ╖  Bit 2 -INIT (0=high)
  439.  
  440.   ╖  Bit 3 SLCT_IN (1=high)
  441.  
  442.   ╖  Bit 4 enables the parallel port IRQ (which occurs on the low-to-
  443.      high transition of ACK) when set to 1.
  444.  
  445.   ╖  Bit 5 controls the extended mode direction (0 = write, 1 = read),
  446.      and is completely write-only (a read returns nothing useful for
  447.      this bit).
  448.  
  449.   ╖  Bits 6 and 7 are reserved.
  450.  
  451.      (Again, I am not sure about the high and low states.)
  452.  
  453.   Pinout (a 25-pin female D-shell connector on the port) (i=input,
  454.   o=output):
  455.  
  456.  
  457.        1io -STROBE, 2io D0, 3io D1, 4io D2, 5io D3, 6io D4, 7io D5, 8io D6,
  458.        9io D7, 10i ACK, 11i -BUSY, 12i PE, 13i SLCT, 14o AUTO_FD_XT,
  459.        15i ERROR, 16o -INIT, 17o SLCT_IN, 18-25 Ground
  460.  
  461.  
  462.  
  463.   The IBM specifications say that pins 1, 14, 16, and 17 (the control
  464.   outputs) have open collector drivers pulled to 5 V through 4.7 kiloohm
  465.   resistors (sink 20 mA, source 0.55 mA, high-level output 5.0 V minus
  466.   pullup). The rest of the pins sink 24 mA, source 15 mA, and their
  467.   high-level output is min. 2.4 V. The low state for both is max. 0.5 V.
  468.   Non-IBM parallel ports probably deviate from this standard. For more
  469.   information on this, see
  470.   <http://www.hut.fi/Misc/Electronics/circuits/lptpower.html>.
  471.  
  472.   Finally, a warning: Be careful with grounding. I've broken several
  473.   parallel ports by connecting to them while the computer is turned on.
  474.   It might be a good thing to use a parallel port not integrated on the
  475.   motherboard for things like this. (You can usually get a second
  476.   parallel port for your machine with a cheap standard `multi-I/O' card;
  477.   just disable the ports that you don't need, and set the parallel port
  478.   I/O address on the card to a free address. You don't need to care
  479.   about the parallel port IRQ, since it isn't normally used.)
  480.  
  481.  
  482.  
  483.   6.2.  The game (joystick) port
  484.  
  485.   The game port is located at port addresses 0x200-0x207. For
  486.   controlling normal joysticks, there is a kernel-level joystick driver,
  487.   see  <ftp://sunsite.unc.edu/pub/Linux/kernel/patches/>, filename
  488.   joystick-*.
  489.  
  490.   Pinout (a 15-pin female D-shell connector on the port):
  491.  
  492.   ╖  1,8,9,15: +5 V (power)
  493.  
  494.   ╖  4,5,12: Ground
  495.  
  496.   ╖  2,7,10,14: Digital inputs BA1, BA2, BB1, and BB2, respectively
  497.  
  498.   ╖  3,6,11,13: ``Analog'' inputs AX, AY, BX, and BY, respectively
  499.  
  500.   The +5 V pins seem to often be connected directly to the power lines
  501.   in the motherboard, so they should be able to source quite a lot of
  502.   power, depending on the motherboard, power supply and game port.
  503.  
  504.   The digital inputs are used for the buttons of the two joysticks
  505.   (joystick A and joystick B, with two buttons each) that you can
  506.   connect to the port. They should be normal TTL-level inputs, and you
  507.   can read their status directly from the status port (see below). A
  508.   real joystick returns a low (0 V) status when the button is pressed
  509.   and a high (the 5 V from the power pins through an 1 Kohm resistor)
  510.   status otherwise.
  511.  
  512.   The so-called analog inputs actually measure resistance. The game port
  513.   has a quad one-shot multivibrator (a 558 chip) connected to the four
  514.   inputs. In each input, there is a 2.2 Kohm resistor between the input
  515.   pin and the multivibrator output, and a 0.01 uF timing capacitor
  516.   between the multivibrator output and the ground. A real joystick has a
  517.   potentiometer for each axis (X and Y), wired between +5 V and the
  518.   appropriate input pin (AX or AY for joystick A, or BX or BY for
  519.   joystick B).
  520.  
  521.   The multivibrator, when activated, sets its output lines high (5 V)
  522.   and waits for each timing capacitor to reach 3.3 V before lowering the
  523.   respective output line. Thus the high period duration of the
  524.   multivibrator is proportional to the resistance of the potentiometer
  525.   in the joystick (i.e., the position of the joystick in the appropriate
  526.   axis), as follows:
  527.  
  528.  
  529.   R = (t - 24.2) / 0.011,
  530.  
  531.  
  532.   where R is the resistance (ohms) of the potentiometer and t the high
  533.   period duration (seconds).
  534.  
  535.   Thus, to read the analog inputs, you first activate the multivibrator
  536.   (with a port write; see below), then poll the state of the four axes
  537.   (with repeated port reads) until they drop from high to low state,
  538.   measuring their high period duration. This polling uses quite a lot of
  539.   CPU time, and on a non-realtime multitasking system like (normal user-
  540.   mode) Linux, the result is not very accurate because you cannot poll
  541.   the port constantly (unless you use a kernel-level driver and disable
  542.   interrupts while polling, but this wastes even more CPU time). If you
  543.   know that the signal is going to take a long time (tens of ms) to go
  544.   down, you can call usleep() before polling to give CPU time to other
  545.   processes.
  546.  
  547.   The only I/O port you need to access is port 0x201 (the other ports
  548.   either behave identically or do nothing). Any write to this port (it
  549.   doesn't matter what you write) activates the multivibrator. A read
  550.   from this port returns the state of the input signals:
  551.  
  552.   ╖  Bit 0: AX (status (1=high) of the multivibrator output)
  553.  
  554.   ╖  Bit 1: AY (status (1=high) of the multivibrator output)
  555.  
  556.   ╖  Bit 2: BX (status (1=high) of the multivibrator output)
  557.  
  558.   ╖  Bit 3: BY (status (1=high) of the multivibrator output)
  559.  
  560.   ╖  Bit 4: BA1 (digital input, 1=high)
  561.  
  562.   ╖  Bit 5: BA2 (digital input, 1=high)
  563.  
  564.   ╖  Bit 6: BB1 (digital input, 1=high)
  565.  
  566.   ╖  Bit 7: BB2 (digital input, 1=high)
  567.  
  568.  
  569.  
  570.   6.3.  The serial port
  571.  
  572.   If the device you're talking to supports something resembling RS-232,
  573.   you should be able to use the serial port to talk to it. The Linux
  574.   serial driver should be enough for almost all applications (you
  575.   shouldn't have to program the serial port directly, and you'd probably
  576.   have to write a kernel driver to do it); it is quite versatile, so
  577.   using non-standard bps rates and so on shouldn't be a problem.
  578.  
  579.   See the termios(3) manual page, the serial driver source code
  580.   (linux/drivers/char/serial.c), and
  581.   <http://www.easysw.com/~mike/serial/index.html> for more information
  582.   on programming serial ports on Unix systems.
  583.  
  584.  
  585.  
  586.   7.  Hints
  587.  
  588.   If you want good analog I/O, you can wire up ADC and/or DAC chips to
  589.   the parallel port (hint: for power, use the game port connector or a
  590.   spare disk drive power connector wired to outside the computer case,
  591.   unless you have a low-power device and can use the parallel port
  592.   itself for power, or use an external power supply), or buy an AD/DA
  593.   card (most of the older/slower ones are controlled by I/O ports). Or,
  594.   if you're satisfied with 1 or 2 channels, inaccuracy, and (probably)
  595.   bad zeroing, a cheap sound card supported by the Linux sound driver
  596.   should do (and it's quite fast).
  597.  
  598.   With accurate analog devices, improper grounding may generate errors
  599.   in the analog inputs or outputs. If you experience something like
  600.   this, you could try electrically isolating your device from the
  601.   computer with optocouplers (on all signals between the computer and
  602.   your device). Try to get power for the optocouplers from the computer
  603.   (spare signals on the port may give enough power) to achieve better
  604.   isolation.
  605.  
  606.   If you're looking for printed circuit board design software for Linux,
  607.   there is a free X11 application called Pcb that should do a nice job,
  608.   at least if you aren't doing anything very complex. It is included in
  609.   many Linux distributions, and available in
  610.   <ftp://sunsite.unc.edu/pub/Linux/apps/circuits/> (filename pcb-*).
  611.  
  612.  
  613.  
  614.   8.  Troubleshooting
  615.  
  616.  
  617.      Q1.
  618.         I get segmentation faults when accessing ports.
  619.  
  620.  
  621.      A1.
  622.         Either your program does not have root privileges, or the
  623.         ioperm() call failed for some other reason. Check the return
  624.         value of ioperm(). Also, check that you're actually accessing
  625.         the ports that you enabled with ioperm() (see Q3). If you're
  626.         using the delaying macros (inb_p(), outb_p(), and so on),
  627.         remember to call ioperm() to get access to port 0x80 too.
  628.  
  629.  
  630.      Q2.
  631.         I can't find the in*(), out*() functions defined anywhere, and
  632.         gcc complains about undefined references.
  633.  
  634.  
  635.      A2.
  636.         You did not compile with optimisation turned on (-O), and thus
  637.         gcc could not resolve the macros in asm/io.h. Or you did not
  638.         #include <asm/io.h> at all.
  639.  
  640.  
  641.      Q3.
  642.         out*() doesn't do anything, or does something weird.
  643.  
  644.  
  645.      A3.
  646.         Check the order of the parameters; it should be outb(value,
  647.         port), not outportb(port, value) as is common in MS-DOS.
  648.  
  649.  
  650.      Q4.
  651.         I want to control a standard RS-232 device/parallel
  652.         printer/joystick...
  653.  
  654.  
  655.      A4.
  656.         You're probably better off using existing drivers (in the Linux
  657.         kernel or an X server or somewhere else) to do it. The drivers
  658.         are usually quite versatile, so even slightly non-standard
  659.         devices usually work with them. See the information on standard
  660.         ports above for pointers to documentation for them.
  661.   9.  Example code
  662.  
  663.   Here's a piece of simple example code for I/O port access:
  664.  
  665.  
  666.  
  667.        ______________________________________________________________________
  668.        /*
  669.         * example.c: very simple example of port I/O
  670.         *
  671.         * This code does nothing useful, just a port write, a pause,
  672.         * and a port read. Compile with `gcc -O2 -o example example.c',
  673.         * and run as root with `./example'.
  674.         */
  675.  
  676.        #include <stdio.h>
  677.        #include <unistd.h>
  678.        #include <asm/io.h>
  679.  
  680.        #define BASEPORT 0x378 /* lp1 */
  681.  
  682.        int main()
  683.        {
  684.          /* Get access to the ports */
  685.          if (ioperm(BASEPORT, 3, 1)) {perror("ioperm"); exit(1);}
  686.  
  687.          /* Set the data signals (D0-7) of the port to all low (0) */
  688.          outb(0, BASEPORT);
  689.  
  690.          /* Sleep for a while (100 ms) */
  691.          usleep(100000);
  692.  
  693.          /* Read from the status port (BASE+1) and display the result */
  694.          printf("status: %d\n", inb(BASEPORT + 1));
  695.  
  696.          /* We don't need the ports anymore */
  697.          if (ioperm(BASEPORT, 3, 0)) {perror("ioperm"); exit(1);}
  698.  
  699.          exit(0);
  700.        }
  701.  
  702.        /* end of example.c */
  703.        ______________________________________________________________________
  704.  
  705.  
  706.  
  707.  
  708.  
  709.  
  710.   10.  Credits
  711.  
  712.   Too many people have contributed for me to list, but thanks a lot,
  713.   everyone. I have not replied to all the contributions that I've
  714.   received; sorry for that, and thanks again for the help.
  715.  
  716.  
  717.  
  718.  
  719.  
  720.  
  721.  
  722.  
  723.  
  724.  
  725.  
  726.  
  727.