190 lines · c
1// SPDX-License-Identifier: GPL-2.0-or-later2/*3 * (c) 1998 Grant R. Guenther <grant@torque.net>4 *5 * fit3.c is a low-level protocol driver for newer models6 * of the Fidelity International Technology parallel port adapter.7 * This adapter is used in their TransDisk 3000 portable8 * hard-drives, as well as CD-ROM, PD-CD and other devices.9 *10 * The TD-2000 and certain older devices use a different protocol.11 * Try the fit2 protocol module with them.12 */13 14#include <linux/module.h>15#include <linux/init.h>16#include <linux/delay.h>17#include <linux/kernel.h>18#include <linux/types.h>19#include <linux/wait.h>20#include <asm/io.h>21#include "pata_parport.h"22 23#define j44(a, b) (((a >> 3) & 0x0f) | ((b << 1) & 0xf0))24 25#define w7(byte) out_p(7, byte)26#define r7() (in_p(7) & 0xff)27 28/*29 * cont = 0 - access the IDE register file30 * cont = 1 - access the IDE command set31 */32 33static void fit3_write_regr(struct pi_adapter *pi, int cont, int regr, int val)34{35 regr += cont << 3;36 37 switch (pi->mode) {38 case 0:39 case 1:40 w2(0xc); w0(regr); w2(0x8); w2(0xc);41 w0(val); w2(0xd);42 w0(0); w2(0xc);43 break;44 case 2:45 w2(0xc); w0(regr); w2(0x8); w2(0xc);46 w4(val); w4(0);47 w2(0xc);48 break;49 }50}51 52static int fit3_read_regr(struct pi_adapter *pi, int cont, int regr)53{54 int a, b;55 56 regr += cont << 3;57 58 switch (pi->mode) {59 case 0:60 w2(0xc); w0(regr + 0x10); w2(0x8); w2(0xc);61 w2(0xd); a = r1();62 w2(0xf); b = r1();63 w2(0xc);64 return j44(a, b);65 case 1:66 w2(0xc); w0(regr + 0x90); w2(0x8); w2(0xc);67 w2(0xec); w2(0xee); w2(0xef); a = r0();68 w2(0xc);69 return a;70 case 2:71 w2(0xc); w0(regr + 0x90); w2(0x8); w2(0xc);72 w2(0xec);73 a = r4(); b = r4();74 w2(0xc);75 return a;76 }77 78 return -1;79}80 81static void fit3_read_block(struct pi_adapter *pi, char *buf, int count)82{83 int k, a, b, c, d;84 85 switch (pi->mode) {86 case 0:87 w2(0xc); w0(0x10); w2(0x8); w2(0xc);88 for (k = 0; k < count / 2; k++) {89 w2(0xd); a = r1();90 w2(0xf); b = r1();91 w2(0xc); c = r1();92 w2(0xe); d = r1();93 buf[2 * k] = j44(a, b);94 buf[2 * k + 1] = j44(c, d);95 }96 w2(0xc);97 break;98 case 1:99 w2(0xc); w0(0x90); w2(0x8); w2(0xc);100 w2(0xec); w2(0xee);101 for (k = 0; k < count / 2; k++) {102 w2(0xef); a = r0();103 w2(0xee); b = r0();104 buf[2 * k] = a;105 buf[2 * k + 1] = b;106 }107 w2(0xec);108 w2(0xc);109 break;110 case 2:111 w2(0xc); w0(0x90); w2(0x8); w2(0xc);112 w2(0xec);113 for (k = 0; k < count; k++)114 buf[k] = r4();115 w2(0xc);116 break;117 }118}119 120static void fit3_write_block(struct pi_adapter *pi, char *buf, int count)121{122 int k;123 124 switch (pi->mode) {125 case 0:126 case 1:127 w2(0xc); w0(0); w2(0x8); w2(0xc);128 for (k = 0; k < count / 2; k++) {129 w0(buf[2 * k]); w2(0xd);130 w0(buf[2 * k + 1]); w2(0xc);131 }132 break;133 case 2:134 w2(0xc); w0(0); w2(0x8); w2(0xc);135 for (k = 0; k < count; k++)136 w4(buf[k]);137 w2(0xc);138 break;139 }140}141 142static void fit3_connect(struct pi_adapter *pi)143{144 pi->saved_r0 = r0();145 pi->saved_r2 = r2();146 w2(0xc); w0(0); w2(0xa);147 if (pi->mode == 2) {148 w2(0xc); w0(0x9);149 w2(0x8); w2(0xc);150 }151}152 153static void fit3_disconnect(struct pi_adapter *pi)154{155 w2(0xc); w0(0xa); w2(0x8); w2(0xc);156 w0(pi->saved_r0);157 w2(pi->saved_r2);158}159 160static void fit3_log_adapter(struct pi_adapter *pi)161{162 char *mode_string[3] = { "4-bit", "8-bit", "EPP"};163 164 dev_info(&pi->dev,165 "FIT 3000 adapter at 0x%x, mode %d (%s), delay %d\n",166 pi->port, pi->mode, mode_string[pi->mode], pi->delay);167}168 169static struct pi_protocol fit3 = {170 .owner = THIS_MODULE,171 .name = "fit3",172 .max_mode = 3,173 .epp_first = 2,174 .default_delay = 1,175 .max_units = 1,176 .write_regr = fit3_write_regr,177 .read_regr = fit3_read_regr,178 .write_block = fit3_write_block,179 .read_block = fit3_read_block,180 .connect = fit3_connect,181 .disconnect = fit3_disconnect,182 .log_adapter = fit3_log_adapter,183};184 185MODULE_LICENSE("GPL");186MODULE_AUTHOR("Grant R. Guenther <grant@torque.net>");187MODULE_DESCRIPTION("Fidelity International Technology parallel port IDE adapter"188 "(newer models) protocol driver");189module_pata_parport_driver(fit3);190