/* You  compile  with -O or -O2 or similar. The functions are
   defined as inline macros, and will not be  substituted  in
   without  optimization  enabled,  causing unresolved refer­
   ences at link time.
*/

#include <stdio.h>
#include <stdlib.h>
#include <sys/io.h>
#include <unistd.h>

#define DEBUG 1

/* Base addresses of parallel ports */
#define LPT1 0x378
#define LPT2 0x278
#define LPT3 0x3BC

void usage(void)
{
  printf("Syntax : setport <dataport value> <control port value> <portnum>\n\n");
  printf("portnum: 1, 2 or 3 for LPT1, LPT2 or LPT3.\n");
  return(1);
}

int main(int argc, char *argv[])
  {
  int data = 0;          /* data port value */
  int control = 0;       /* control port value */
  int BASEPORT = 0;      /* selected printer port */

  if (argc != 4) usage();       /* falsche Parameteranzahl */
  switch (argv[3][0])
    {
    case '1': BASEPORT = LPT1; break;
    case '2': BASEPORT = LPT2; break;
    case '3': BASEPORT = LPT3; break;
    default : usage();
    }
  data = atoi(argv[1]);
  if (data < 0 || data > 255)
    { perror("Error: data value out of range"); exit(1); }
  control = atoi(argv[2]);
  if (control < 0 || control > 15)
    { perror("Error: control value out of range"); exit(1); }
  /* Get access to the ports */
  if (ioperm(BASEPORT, 3, 1))
    { perror("Error: cannot access ioport"); exit(1); }
  /* Set the data signals of the port */
#ifdef DEBUG
   printf("Debug: Writing to PORT %X.\n", BASEPORT);
   printf("Debug: Setting Data Port to %X.\n", data);
   printf("Debug: Setting Control Port to %X.\n", control);
#endif
  outb(data, BASEPORT);
  outb(control ^ 0x0B, BASEPORT + 2);
  /* We don't need the ports anymore */
  if (ioperm(BASEPORT, 3, 0))
    { perror("Error: cannot access ioport"); exit(1); }
  return(0);
  }


