cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

lasi700.c (4078B)


      1// SPDX-License-Identifier: GPL-2.0-or-later
      2
      3/* PARISC LASI driver for the 53c700 chip
      4 *
      5 * Copyright (C) 2001 by James.Bottomley@HansenPartnership.com
      6**-----------------------------------------------------------------------------
      7**  
      8**
      9**-----------------------------------------------------------------------------
     10 */
     11
     12/*
     13 * Many thanks to Richard Hirst <rhirst@linuxcare.com> for patiently
     14 * debugging this driver on the parisc architecture and suggesting
     15 * many improvements and bug fixes.
     16 *
     17 * Thanks also go to Linuxcare Inc. for providing several PARISC
     18 * machines for me to debug the driver on.
     19 */
     20
     21#include <linux/kernel.h>
     22#include <linux/module.h>
     23#include <linux/init.h>
     24#include <linux/types.h>
     25#include <linux/stat.h>
     26#include <linux/mm.h>
     27#include <linux/blkdev.h>
     28#include <linux/ioport.h>
     29#include <linux/dma-mapping.h>
     30#include <linux/slab.h>
     31
     32#include <asm/page.h>
     33#include <asm/irq.h>
     34#include <asm/hardware.h>
     35#include <asm/parisc-device.h>
     36#include <asm/delay.h>
     37
     38#include <scsi/scsi_host.h>
     39#include <scsi/scsi_device.h>
     40#include <scsi/scsi_transport.h>
     41#include <scsi/scsi_transport_spi.h>
     42
     43#include "53c700.h"
     44
     45MODULE_AUTHOR("James Bottomley");
     46MODULE_DESCRIPTION("lasi700 SCSI Driver");
     47MODULE_LICENSE("GPL");
     48
     49#define LASI_700_SVERSION 0x00071
     50#define LASI_710_SVERSION 0x00082
     51
     52#define LASI700_ID_TABLE {			\
     53	.hw_type	= HPHW_FIO,		\
     54	.sversion	= LASI_700_SVERSION,	\
     55	.hversion	= HVERSION_ANY_ID,	\
     56	.hversion_rev	= HVERSION_REV_ANY_ID,	\
     57}
     58
     59#define LASI710_ID_TABLE {			\
     60	.hw_type	= HPHW_FIO,		\
     61	.sversion	= LASI_710_SVERSION,	\
     62	.hversion	= HVERSION_ANY_ID,	\
     63	.hversion_rev	= HVERSION_REV_ANY_ID,	\
     64}
     65
     66#define LASI700_CLOCK	25
     67#define LASI710_CLOCK	40
     68#define LASI_SCSI_CORE_OFFSET 0x100
     69
     70static const struct parisc_device_id lasi700_ids[] __initconst = {
     71	LASI700_ID_TABLE,
     72	LASI710_ID_TABLE,
     73	{ 0 }
     74};
     75
     76static struct scsi_host_template lasi700_template = {
     77	.name		= "LASI SCSI 53c700",
     78	.proc_name	= "lasi700",
     79	.this_id	= 7,
     80	.module		= THIS_MODULE,
     81};
     82MODULE_DEVICE_TABLE(parisc, lasi700_ids);
     83
     84static int __init
     85lasi700_probe(struct parisc_device *dev)
     86{
     87	unsigned long base = dev->hpa.start + LASI_SCSI_CORE_OFFSET;
     88	struct NCR_700_Host_Parameters *hostdata;
     89	struct Scsi_Host *host;
     90
     91	hostdata = kzalloc(sizeof(*hostdata), GFP_KERNEL);
     92	if (!hostdata) {
     93		dev_printk(KERN_ERR, &dev->dev, "Failed to allocate host data\n");
     94		return -ENOMEM;
     95	}
     96
     97	hostdata->dev = &dev->dev;
     98	dma_set_mask(&dev->dev, DMA_BIT_MASK(32));
     99	hostdata->base = ioremap(base, 0x100);
    100	hostdata->differential = 0;
    101
    102	if (dev->id.sversion == LASI_700_SVERSION) {
    103		hostdata->clock = LASI700_CLOCK;
    104		hostdata->force_le_on_be = 1;
    105	} else {
    106		hostdata->clock = LASI710_CLOCK;
    107		hostdata->force_le_on_be = 0;
    108		hostdata->chip710 = 1;
    109		hostdata->dmode_extra = DMODE_FC2;
    110		hostdata->burst_length = 8;
    111	}
    112
    113	host = NCR_700_detect(&lasi700_template, hostdata, &dev->dev);
    114	if (!host)
    115		goto out_kfree;
    116	host->this_id = 7;
    117	host->base = base;
    118	host->irq = dev->irq;
    119	if(request_irq(dev->irq, NCR_700_intr, IRQF_SHARED, "lasi700", host)) {
    120		printk(KERN_ERR "lasi700: request_irq failed!\n");
    121		goto out_put_host;
    122	}
    123
    124	dev_set_drvdata(&dev->dev, host);
    125	scsi_scan_host(host);
    126
    127	return 0;
    128
    129 out_put_host:
    130	scsi_host_put(host);
    131 out_kfree:
    132	iounmap(hostdata->base);
    133	kfree(hostdata);
    134	return -ENODEV;
    135}
    136
    137static void __exit
    138lasi700_driver_remove(struct parisc_device *dev)
    139{
    140	struct Scsi_Host *host = dev_get_drvdata(&dev->dev);
    141	struct NCR_700_Host_Parameters *hostdata = 
    142		(struct NCR_700_Host_Parameters *)host->hostdata[0];
    143
    144	scsi_remove_host(host);
    145	NCR_700_release(host);
    146	free_irq(host->irq, host);
    147	iounmap(hostdata->base);
    148	kfree(hostdata);
    149}
    150
    151static struct parisc_driver lasi700_driver __refdata = {
    152	.name =		"lasi_scsi",
    153	.id_table =	lasi700_ids,
    154	.probe =	lasi700_probe,
    155	.remove =	__exit_p(lasi700_driver_remove),
    156};
    157
    158static int __init
    159lasi700_init(void)
    160{
    161	return register_parisc_driver(&lasi700_driver);
    162}
    163
    164static void __exit
    165lasi700_exit(void)
    166{
    167	unregister_parisc_driver(&lasi700_driver);
    168}
    169
    170module_init(lasi700_init);
    171module_exit(lasi700_exit);