1// SPDX-License-Identifier: GPL-2.0-or-later 2/* 3 * (c) 1998 Grant R. Guenther <grant@torque.net> 4 * 5 * ktti.c is a low-level protocol driver for the KT Technology 6 * parallel port adapter. This adapter is used in the "PHd" 7 * portable hard-drives. As far as I can tell, this device 8 * supports 4-bit mode _only_. 9*/ 10 11#include <linux/module.h> 12#include <linux/init.h> 13#include <linux/delay.h> 14#include <linux/kernel.h> 15#include <linux/types.h> 16#include <linux/wait.h> 17#include <asm/io.h> 18#include "pata_parport.h" 19 20#define j44(a, b) (((a >> 4) & 0x0f) | (b & 0xf0)) 21 22/* 23 * cont = 0 - access the IDE register file 24 * cont = 1 - access the IDE command set 25 */ 26static int cont_map[2] = { 0x10, 0x08 }; 27 28static void ktti_write_regr(struct pi_adapter *pi, int cont, int regr, int val) 29{ 30 int r = regr + cont_map[cont]; 31 32 w0(r); w2(0xb); w2(0xa); w2(3); w2(6); 33 w0(val); w2(3); w0(0); w2(6); w2(0xb); 34} 35 36static int ktti_read_regr(struct pi_adapter *pi, int cont, int regr) 37{ 38 int a, b, r; 39 40 r = regr + cont_map[cont]; 41 42 w0(r); w2(0xb); w2(0xa); w2(9); w2(0xc); w2(9); 43 a = r1(); w2(0xc); b = r1(); w2(9); w2(0xc); w2(9); 44 return j44(a, b); 45} 46 47static void ktti_read_block(struct pi_adapter *pi, char *buf, int count) 48{ 49 int k, a, b; 50 51 for (k = 0; k < count / 2; k++) { 52 w0(0x10); w2(0xb); w2(0xa); w2(9); w2(0xc); w2(9); 53 a = r1(); w2(0xc); b = r1(); w2(9); 54 buf[2*k] = j44(a, b); 55 a = r1(); w2(0xc); b = r1(); w2(9); 56 buf[2*k+1] = j44(a, b); 57 } 58} 59 60static void ktti_write_block(struct pi_adapter *pi, char *buf, int count) 61{ 62 int k; 63 64 for (k = 0; k < count / 2; k++) { 65 w0(0x10); w2(0xb); w2(0xa); w2(3); w2(6); 66 w0(buf[2 * k]); w2(3); 67 w0(buf[2 * k + 1]); w2(6); 68 w2(0xb); 69 } 70} 71 72static void ktti_connect(struct pi_adapter *pi) 73{ 74 pi->saved_r0 = r0(); 75 pi->saved_r2 = r2(); 76 w2(0xb); w2(0xa); w0(0); w2(3); w2(6); 77} 78 79static void ktti_disconnect(struct pi_adapter *pi) 80{ 81 w2(0xb); w2(0xa); w0(0xa0); w2(3); w2(4); 82 w0(pi->saved_r0); 83 w2(pi->saved_r2); 84} 85 86static void ktti_log_adapter(struct pi_adapter *pi) 87{ 88 dev_info(&pi->dev, "KT adapter at 0x%x, delay %d\n", 89 pi->port, pi->delay); 90} 91 92static struct pi_protocol ktti = { 93 .owner = THIS_MODULE, 94 .name = "ktti", 95 .max_mode = 1, 96 .epp_first = 2, 97 .default_delay = 1, 98 .max_units = 1, 99 .write_regr = ktti_write_regr, 100 .read_regr = ktti_read_regr, 101 .write_block = ktti_write_block, 102 .read_block = ktti_read_block, 103 .connect = ktti_connect, 104 .disconnect = ktti_disconnect, 105 .log_adapter = ktti_log_adapter, 106}; 107 108MODULE_LICENSE("GPL"); 109MODULE_AUTHOR("Grant R. Guenther <grant@torque.net>"); 110MODULE_DESCRIPTION("KT Technology parallel port IDE adapter protocol driver"); 111module_pata_parport_driver(ktti); 112