root/drivers/char/ftape/fc-10.c

/* [previous][next][first][last][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. fc10_enable

   1 /* Yo, Emacs! we're -*- Linux-C -*-
   2  *
   3  
   4    Copyright (C) 1993,1994 Jon Tombs.
   5 
   6    This program is distributed in the hope that it will be useful,
   7    but WITHOUT ANY WARRANTY; without even the implied warranty of
   8    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   9    GNU General Public License for more details.
  10 
  11    The entire guts of this program was written by dosemu, modified to
  12    record reads and writes to the ports in the 0x180-0x188 address space,
  13    while running the CMS program TAPE.EXE V2.0.5 supplied with the drive.
  14 
  15    Modified to use an array of addresses and generally cleaned up (made
  16    much shorter) 4 June 94, dosemu isn't that good at writing short code it
  17    would seem :-). Made independant of 0x180, but I doubt it will work
  18    at any other address.
  19 
  20    Modified for distribution with ftape source. 21 June 94, SJL.
  21 
  22    Modifications on 20 October 95, by Daniel Cohen (catman@wpi.edu):
  23    Modified to support different DMA, IRQ, and IO Ports.  Borland's
  24    Turbo Debugger in virtual 8086 mode (TD386.EXE with hardware breakpoints
  25    provided by the TDH386.SYS Device Driver) was used on the CMS program
  26    TAPE V4.0.5.  I set breakpoints on I/O to ports 0x180-0x187.  Note that
  27    CMS's program will not successfully configure the tape drive if you set
  28    breakpoints on IO Reads, but you can set them on IO Writes without problems.
  29    Known problems:
  30    - You can not use DMA Channels 5 or 7.
  31 
  32    Modification on 29 January 96, by Daniel Cohen (catman@wpi.edu):
  33    Modified to only accept IRQs 3 - 7, or 9.  Since we can only send a 3 bit
  34    number representing the IRQ to the card, special handling is required when
  35    IRQ 9 is selected.  IRQ 2 and 9 are the same, and we should request IRQ 9
  36    from the kernel while telling the card to use IRQ 2.  Thanks to Greg
  37    Crider (gcrider@iclnet.org) for finding and locating this bug, as well as
  38    testing the patch.
  39 
  40  *
  41  *      This file contains code for the CMS FC-10/FC-20 card.
  42  */
  43 
  44 #include <linux/module.h>
  45 #include <linux/ftape.h>
  46 #include <asm/io.h>
  47 
  48 #include "tracing.h"
  49 #include "fdc-io.h"
  50 #include "fc-10.h"
  51 
  52 #ifdef PROBE_FC10
  53 
  54 /*  This code will only work if the FC-10 (or FC-20) is set to
  55  *  use DMA channels 1, 2, or 3.  DMA channels 5 and 7 seem to be 
  56  *  initialized by the same command as channels 1 and 3, respectively.
  57  */
  58 #if (FDC_DMA > 3)
  59 #error : The FC-10/20 must be set to use DMA channels 1, 2, or 3!
  60 #endif
  61 
  62 /*  Only allow the FC-10/20 to use IRQ 3-7, or 9.  Note that CMS's program
  63  *  only accepts IRQ's 2-7, but in linux, IRQ 2 is the same as IRQ 9.
  64  */
  65 #if (FDC_IRQ < 3 || FDC_IRQ == 8 || FDC_IRQ > 9)
  66 #error : The FC-10/20 must be set to use IRQ levels 3 - 7, or 9!
  67 #error :              Note IRQ 9 is the same as IRQ 2
  68 #endif
  69 
  70 unsigned short inbs_magic[] = {
  71         0x3, 0x3, 0x0, 0x4, 0x7, 0x2, 0x5, 0x3, 0x1, 0x4,
  72         0x3, 0x5, 0x2, 0x0, 0x3, 0x7, 0x4, 0x2,
  73         0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7
  74 };
  75 
  76 unsigned short fc10_ports[] = {
  77         0x180, 0x210, 0x2A0, 0x300, 0x330, 0x340, 0x370
  78 };
  79 
  80 int fc10_enable(void)
     /* [previous][next][first][last][top][bottom][index][help] */
  81 {
  82         int i;
  83         byte cardConfig = 0x00;
  84         byte x;
  85 
  86         /*  Clear state machine ???
  87          */
  88         for (i = 0; i < NR_ITEMS(inbs_magic); i++) {
  89                 inb(FDC_BASE + inbs_magic[i]);
  90         }
  91         outb(0x0, FDC_BASE);
  92 
  93         x = inb(FDC_BASE);
  94         if (x == 0x13 || x == 0x93) {
  95                 for (i = 1; i < 8; i++) {
  96                         if (inb(FDC_BASE + i) != x) {
  97                                 return 0;
  98                         }
  99                 }
 100         } else {
 101                 return 0;
 102         }
 103 
 104         outb(0x8, FDC_BASE);
 105 
 106         for (i = 0; i < 8; i++) {
 107                 if (inb(FDC_BASE + i) != 0x0) {
 108                         return 0;
 109                 }
 110         }
 111         outb(0x10, FDC_BASE);
 112 
 113         for (i = 0; i < 8; i++) {
 114                 if (inb(FDC_BASE + i) != 0xff) {
 115                         return 0;
 116                 }
 117         }
 118 
 119         /*  Okay, we found a FC-10 card ! ???
 120          */
 121         outb(0x0, fdc.ccr);
 122 
 123         /*  Clear state machine again ???
 124          */
 125         for (i = 0; i < NR_ITEMS(inbs_magic); i++) {
 126                 inb(FDC_BASE + inbs_magic[i]);
 127         }
 128         /* Send io port */
 129         for (i = 0; i < NR_ITEMS(fc10_ports); i++)
 130                 if (FDC_BASE == fc10_ports[i])
 131                         cardConfig = i + 1;
 132         if (cardConfig == 0)
 133                 return 0;       /* Invalid I/O Port */
 134         /* and IRQ - If using IRQ 9, tell the FC card it is actually IRQ 2 */
 135         if (FDC_IRQ != 9)
 136                 cardConfig |= FDC_IRQ << 3;
 137         else
 138                 cardConfig |= 2 << 3;
 139 
 140         /* and finally DMA Channel */
 141         cardConfig |= FDC_DMA << 6;
 142         outb(cardConfig, FDC_BASE);     /* DMA [2 bits]/IRQ [3 bits]/BASE [3 bits] */
 143 
 144         /*  Enable FC-10 ???
 145          */
 146         outb(0, fdc.ccr);
 147         outb(0, FDC_BASE + 0x6);
 148         outb(8, fdc.dor);
 149         outb(8, fdc.dor);
 150         outb(1, FDC_BASE + 0x6);
 151 
 152         /*  Initialize fdc, select drive B:
 153          */
 154         outb(0x08, fdc.dor);    /* assert reset, dma & irq enabled */
 155         outb(0x0c, fdc.dor);    /* release reset */
 156         outb(0x2d, fdc.dor);    /* select drive 1 */
 157 
 158         return (x == 0x93) ? 2 : 1;
 159 }
 160 
 161 #endif /* CMS_FC10_CONTROLLER */

/* [previous][next][first][last][top][bottom][index][help] */