2071 lines · c
1// SPDX-License-Identifier: GPL-2.0-only2/*3 * SCSI low-level driver for the MESH (Macintosh Enhanced SCSI Hardware)4 * bus adaptor found on Power Macintosh computers.5 * We assume the MESH is connected to a DBDMA (descriptor-based DMA)6 * controller.7 *8 * Paul Mackerras, August 1996.9 * Copyright (C) 1996 Paul Mackerras.10 *11 * Apr. 21 2002 - BenH Rework bus reset code for new error handler12 * Add delay after initial bus reset13 * Add module parameters14 *15 * Sep. 27 2003 - BenH Move to new driver model, fix some write posting16 * issues17 * To do:18 * - handle aborts correctly19 * - retry arbitration if lost (unless higher levels do this for us)20 * - power down the chip when no device is detected21 */22#include <linux/module.h>23#include <linux/kernel.h>24#include <linux/delay.h>25#include <linux/types.h>26#include <linux/string.h>27#include <linux/blkdev.h>28#include <linux/proc_fs.h>29#include <linux/stat.h>30#include <linux/interrupt.h>31#include <linux/reboot.h>32#include <linux/spinlock.h>33#include <linux/pci.h>34#include <linux/pgtable.h>35#include <asm/dbdma.h>36#include <asm/io.h>37#include <asm/prom.h>38#include <asm/irq.h>39#include <asm/hydra.h>40#include <asm/processor.h>41#include <asm/setup.h>42#include <asm/pmac_feature.h>43#include <asm/macio.h>44 45#include <scsi/scsi.h>46#include <scsi/scsi_cmnd.h>47#include <scsi/scsi_device.h>48#include <scsi/scsi_host.h>49 50#include "mesh.h"51 52#if 153#undef KERN_DEBUG54#define KERN_DEBUG KERN_WARNING55#endif56 57MODULE_AUTHOR("Paul Mackerras <paulus@samba.org>");58MODULE_DESCRIPTION("PowerMac MESH SCSI driver");59MODULE_LICENSE("GPL");60 61static int sync_rate = CONFIG_SCSI_MESH_SYNC_RATE;62static int sync_targets = 0xff;63static int resel_targets = 0xff;64static int debug_targets = 0; /* print debug for these targets */65static int init_reset_delay = CONFIG_SCSI_MESH_RESET_DELAY_MS;66 67module_param(sync_rate, int, 0);68MODULE_PARM_DESC(sync_rate, "Synchronous rate (0..10, 0=async)");69module_param(sync_targets, int, 0);70MODULE_PARM_DESC(sync_targets, "Bitmask of targets allowed to set synchronous");71module_param(resel_targets, int, 0);72MODULE_PARM_DESC(resel_targets, "Bitmask of targets allowed to set disconnect");73module_param(debug_targets, int, 0644);74MODULE_PARM_DESC(debug_targets, "Bitmask of debugged targets");75module_param(init_reset_delay, int, 0);76MODULE_PARM_DESC(init_reset_delay, "Initial bus reset delay (0=no reset)");77 78static int mesh_sync_period = 100;79static int mesh_sync_offset = 0;80static unsigned char use_active_neg = 0; /* bit mask for SEQ_ACTIVE_NEG if used */81 82#define ALLOW_SYNC(tgt) ((sync_targets >> (tgt)) & 1)83#define ALLOW_RESEL(tgt) ((resel_targets >> (tgt)) & 1)84#define ALLOW_DEBUG(tgt) ((debug_targets >> (tgt)) & 1)85#define DEBUG_TARGET(cmd) ((cmd) && ALLOW_DEBUG((cmd)->device->id))86 87#undef MESH_DBG88#define N_DBG_LOG 5089#define N_DBG_SLOG 2090#define NUM_DBG_EVENTS 1391#undef DBG_USE_TB /* bombs on 601 */92 93struct dbglog {94 char *fmt;95 u32 tb;96 u8 phase;97 u8 bs0;98 u8 bs1;99 u8 tgt;100 int d;101};102 103enum mesh_phase {104 idle,105 arbitrating,106 selecting,107 commanding,108 dataing,109 statusing,110 busfreeing,111 disconnecting,112 reselecting,113 sleeping114};115 116enum msg_phase {117 msg_none,118 msg_out,119 msg_out_xxx,120 msg_out_last,121 msg_in,122 msg_in_bad,123};124 125enum sdtr_phase {126 do_sdtr,127 sdtr_sent,128 sdtr_done129};130 131struct mesh_target {132 enum sdtr_phase sdtr_state;133 int sync_params;134 int data_goes_out; /* guess as to data direction */135 struct scsi_cmnd *current_req;136 u32 saved_ptr;137#ifdef MESH_DBG138 int log_ix;139 int n_log;140 struct dbglog log[N_DBG_LOG];141#endif142};143 144struct mesh_state {145 volatile struct mesh_regs __iomem *mesh;146 int meshintr;147 volatile struct dbdma_regs __iomem *dma;148 int dmaintr;149 struct Scsi_Host *host;150 struct mesh_state *next;151 struct scsi_cmnd *request_q;152 struct scsi_cmnd *request_qtail;153 enum mesh_phase phase; /* what we're currently trying to do */154 enum msg_phase msgphase;155 int conn_tgt; /* target we're connected to */156 struct scsi_cmnd *current_req; /* req we're currently working on */157 int data_ptr;158 int dma_started;159 int dma_count;160 int stat;161 int aborting;162 int expect_reply;163 int n_msgin;164 u8 msgin[16];165 int n_msgout;166 int last_n_msgout;167 u8 msgout[16];168 struct dbdma_cmd *dma_cmds; /* space for dbdma commands, aligned */169 dma_addr_t dma_cmd_bus;170 void *dma_cmd_space;171 int dma_cmd_size;172 int clk_freq;173 struct mesh_target tgts[8];174 struct macio_dev *mdev;175 struct pci_dev* pdev;176#ifdef MESH_DBG177 int log_ix;178 int n_log;179 struct dbglog log[N_DBG_SLOG];180#endif181};182 183/*184 * Driver is too messy, we need a few prototypes...185 */186static void mesh_done(struct mesh_state *ms, int start_next);187static void mesh_interrupt(struct mesh_state *ms);188static void cmd_complete(struct mesh_state *ms);189static void set_dma_cmds(struct mesh_state *ms, struct scsi_cmnd *cmd);190static void halt_dma(struct mesh_state *ms);191static void phase_mismatch(struct mesh_state *ms);192 193 194/*195 * Some debugging & logging routines196 */197 198#ifdef MESH_DBG199 200static inline u32 readtb(void)201{202 u32 tb;203 204#ifdef DBG_USE_TB205 /* Beware: if you enable this, it will crash on 601s. */206 asm ("mftb %0" : "=r" (tb) : );207#else208 tb = 0;209#endif210 return tb;211}212 213static void dlog(struct mesh_state *ms, char *fmt, int a)214{215 struct mesh_target *tp = &ms->tgts[ms->conn_tgt];216 struct dbglog *tlp, *slp;217 218 tlp = &tp->log[tp->log_ix];219 slp = &ms->log[ms->log_ix];220 tlp->fmt = fmt;221 tlp->tb = readtb();222 tlp->phase = (ms->msgphase << 4) + ms->phase;223 tlp->bs0 = ms->mesh->bus_status0;224 tlp->bs1 = ms->mesh->bus_status1;225 tlp->tgt = ms->conn_tgt;226 tlp->d = a;227 *slp = *tlp;228 if (++tp->log_ix >= N_DBG_LOG)229 tp->log_ix = 0;230 if (tp->n_log < N_DBG_LOG)231 ++tp->n_log;232 if (++ms->log_ix >= N_DBG_SLOG)233 ms->log_ix = 0;234 if (ms->n_log < N_DBG_SLOG)235 ++ms->n_log;236}237 238static void dumplog(struct mesh_state *ms, int t)239{240 struct mesh_target *tp = &ms->tgts[t];241 struct dbglog *lp;242 int i;243 244 if (tp->n_log == 0)245 return;246 i = tp->log_ix - tp->n_log;247 if (i < 0)248 i += N_DBG_LOG;249 tp->n_log = 0;250 do {251 lp = &tp->log[i];252 printk(KERN_DEBUG "mesh log %d: bs=%.2x%.2x ph=%.2x ",253 t, lp->bs1, lp->bs0, lp->phase);254#ifdef DBG_USE_TB255 printk("tb=%10u ", lp->tb);256#endif257 printk(lp->fmt, lp->d);258 printk("\n");259 if (++i >= N_DBG_LOG)260 i = 0;261 } while (i != tp->log_ix);262}263 264static void dumpslog(struct mesh_state *ms)265{266 struct dbglog *lp;267 int i;268 269 if (ms->n_log == 0)270 return;271 i = ms->log_ix - ms->n_log;272 if (i < 0)273 i += N_DBG_SLOG;274 ms->n_log = 0;275 do {276 lp = &ms->log[i];277 printk(KERN_DEBUG "mesh log: bs=%.2x%.2x ph=%.2x t%d ",278 lp->bs1, lp->bs0, lp->phase, lp->tgt);279#ifdef DBG_USE_TB280 printk("tb=%10u ", lp->tb);281#endif282 printk(lp->fmt, lp->d);283 printk("\n");284 if (++i >= N_DBG_SLOG)285 i = 0;286 } while (i != ms->log_ix);287}288 289#else290 291static inline void dlog(struct mesh_state *ms, char *fmt, int a)292{}293static inline void dumplog(struct mesh_state *ms, int tgt)294{}295static inline void dumpslog(struct mesh_state *ms)296{}297 298#endif /* MESH_DBG */299 300#define MKWORD(a, b, c, d) (((a) << 24) + ((b) << 16) + ((c) << 8) + (d))301 302static void303mesh_dump_regs(struct mesh_state *ms)304{305 volatile struct mesh_regs __iomem *mr = ms->mesh;306 volatile struct dbdma_regs __iomem *md = ms->dma;307 int t;308 struct mesh_target *tp;309 310 printk(KERN_DEBUG "mesh: state at %p, regs at %p, dma at %p\n",311 ms, mr, md);312 printk(KERN_DEBUG " ct=%4x seq=%2x bs=%4x fc=%2x "313 "exc=%2x err=%2x im=%2x int=%2x sp=%2x\n",314 (mr->count_hi << 8) + mr->count_lo, mr->sequence,315 (mr->bus_status1 << 8) + mr->bus_status0, mr->fifo_count,316 mr->exception, mr->error, mr->intr_mask, mr->interrupt,317 mr->sync_params);318 while(in_8(&mr->fifo_count))319 printk(KERN_DEBUG " fifo data=%.2x\n",in_8(&mr->fifo));320 printk(KERN_DEBUG " dma stat=%x cmdptr=%x\n",321 in_le32(&md->status), in_le32(&md->cmdptr));322 printk(KERN_DEBUG " phase=%d msgphase=%d conn_tgt=%d data_ptr=%d\n",323 ms->phase, ms->msgphase, ms->conn_tgt, ms->data_ptr);324 printk(KERN_DEBUG " dma_st=%d dma_ct=%d n_msgout=%d\n",325 ms->dma_started, ms->dma_count, ms->n_msgout);326 for (t = 0; t < 8; ++t) {327 tp = &ms->tgts[t];328 if (tp->current_req == NULL)329 continue;330 printk(KERN_DEBUG " target %d: req=%p goes_out=%d saved_ptr=%d\n",331 t, tp->current_req, tp->data_goes_out, tp->saved_ptr);332 }333}334 335 336/*337 * Flush write buffers on the bus path to the mesh338 */339static inline void mesh_flush_io(volatile struct mesh_regs __iomem *mr)340{341 (void)in_8(&mr->mesh_id);342}343 344 345/* Called with meshinterrupt disabled, initialize the chipset346 * and eventually do the initial bus reset. The lock must not be347 * held since we can schedule.348 */349static void mesh_init(struct mesh_state *ms)350{351 volatile struct mesh_regs __iomem *mr = ms->mesh;352 volatile struct dbdma_regs __iomem *md = ms->dma;353 354 mesh_flush_io(mr);355 udelay(100);356 357 /* Reset controller */358 out_le32(&md->control, (RUN|PAUSE|FLUSH|WAKE) << 16); /* stop dma */359 out_8(&mr->exception, 0xff); /* clear all exception bits */360 out_8(&mr->error, 0xff); /* clear all error bits */361 out_8(&mr->sequence, SEQ_RESETMESH);362 mesh_flush_io(mr);363 udelay(10);364 out_8(&mr->intr_mask, INT_ERROR | INT_EXCEPTION | INT_CMDDONE);365 out_8(&mr->source_id, ms->host->this_id);366 out_8(&mr->sel_timeout, 25); /* 250ms */367 out_8(&mr->sync_params, ASYNC_PARAMS);368 369 if (init_reset_delay) {370 printk(KERN_INFO "mesh: performing initial bus reset...\n");371 372 /* Reset bus */373 out_8(&mr->bus_status1, BS1_RST); /* assert RST */374 mesh_flush_io(mr);375 udelay(30); /* leave it on for >= 25us */376 out_8(&mr->bus_status1, 0); /* negate RST */377 mesh_flush_io(mr);378 379 /* Wait for bus to come back */380 msleep(init_reset_delay);381 }382 383 /* Reconfigure controller */384 out_8(&mr->interrupt, 0xff); /* clear all interrupt bits */385 out_8(&mr->sequence, SEQ_FLUSHFIFO);386 mesh_flush_io(mr);387 udelay(1);388 out_8(&mr->sync_params, ASYNC_PARAMS);389 out_8(&mr->sequence, SEQ_ENBRESEL);390 391 ms->phase = idle;392 ms->msgphase = msg_none;393}394 395 396static void mesh_start_cmd(struct mesh_state *ms, struct scsi_cmnd *cmd)397{398 volatile struct mesh_regs __iomem *mr = ms->mesh;399 int t, id;400 401 id = cmd->device->id;402 ms->current_req = cmd;403 ms->tgts[id].data_goes_out = cmd->sc_data_direction == DMA_TO_DEVICE;404 ms->tgts[id].current_req = cmd;405 406#if 1407 if (DEBUG_TARGET(cmd)) {408 int i;409 printk(KERN_DEBUG "mesh_start: %p tgt=%d cmd=", cmd, id);410 for (i = 0; i < cmd->cmd_len; ++i)411 printk(" %x", cmd->cmnd[i]);412 printk(" use_sg=%d buffer=%p bufflen=%u\n",413 scsi_sg_count(cmd), scsi_sglist(cmd), scsi_bufflen(cmd));414 }415#endif416 if (ms->dma_started)417 panic("mesh: double DMA start !\n");418 419 ms->phase = arbitrating;420 ms->msgphase = msg_none;421 ms->data_ptr = 0;422 ms->dma_started = 0;423 ms->n_msgout = 0;424 ms->last_n_msgout = 0;425 ms->expect_reply = 0;426 ms->conn_tgt = id;427 ms->tgts[id].saved_ptr = 0;428 ms->stat = DID_OK;429 ms->aborting = 0;430#ifdef MESH_DBG431 ms->tgts[id].n_log = 0;432 dlog(ms, "start cmd=%x", (int) cmd);433#endif434 435 /* Off we go */436 dlog(ms, "about to arb, intr/exc/err/fc=%.8x",437 MKWORD(mr->interrupt, mr->exception, mr->error, mr->fifo_count));438 out_8(&mr->interrupt, INT_CMDDONE);439 out_8(&mr->sequence, SEQ_ENBRESEL);440 mesh_flush_io(mr);441 udelay(1);442 443 if (in_8(&mr->bus_status1) & (BS1_BSY | BS1_SEL)) {444 /*445 * Some other device has the bus or is arbitrating for it -446 * probably a target which is about to reselect us.447 */448 dlog(ms, "busy b4 arb, intr/exc/err/fc=%.8x",449 MKWORD(mr->interrupt, mr->exception,450 mr->error, mr->fifo_count));451 for (t = 100; t > 0; --t) {452 if ((in_8(&mr->bus_status1) & (BS1_BSY | BS1_SEL)) == 0)453 break;454 if (in_8(&mr->interrupt) != 0) {455 dlog(ms, "intr b4 arb, intr/exc/err/fc=%.8x",456 MKWORD(mr->interrupt, mr->exception,457 mr->error, mr->fifo_count));458 mesh_interrupt(ms);459 if (ms->phase != arbitrating)460 return;461 }462 udelay(1);463 }464 if (in_8(&mr->bus_status1) & (BS1_BSY | BS1_SEL)) {465 /* XXX should try again in a little while */466 ms->stat = DID_BUS_BUSY;467 ms->phase = idle;468 mesh_done(ms, 0);469 return;470 }471 }472 473 /*474 * Apparently the mesh has a bug where it will assert both its475 * own bit and the target's bit on the bus during arbitration.476 */477 out_8(&mr->dest_id, mr->source_id);478 479 /*480 * There appears to be a race with reselection sometimes,481 * where a target reselects us just as we issue the482 * arbitrate command. It seems that then the arbitrate483 * command just hangs waiting for the bus to be free484 * without giving us a reselection exception.485 * The only way I have found to get it to respond correctly486 * is this: disable reselection before issuing the arbitrate487 * command, then after issuing it, if it looks like a target488 * is trying to reselect us, reset the mesh and then enable489 * reselection.490 */491 out_8(&mr->sequence, SEQ_DISRESEL);492 if (in_8(&mr->interrupt) != 0) {493 dlog(ms, "intr after disresel, intr/exc/err/fc=%.8x",494 MKWORD(mr->interrupt, mr->exception,495 mr->error, mr->fifo_count));496 mesh_interrupt(ms);497 if (ms->phase != arbitrating)498 return;499 dlog(ms, "after intr after disresel, intr/exc/err/fc=%.8x",500 MKWORD(mr->interrupt, mr->exception,501 mr->error, mr->fifo_count));502 }503 504 out_8(&mr->sequence, SEQ_ARBITRATE);505 506 for (t = 230; t > 0; --t) {507 if (in_8(&mr->interrupt) != 0)508 break;509 udelay(1);510 }511 dlog(ms, "after arb, intr/exc/err/fc=%.8x",512 MKWORD(mr->interrupt, mr->exception, mr->error, mr->fifo_count));513 if (in_8(&mr->interrupt) == 0 && (in_8(&mr->bus_status1) & BS1_SEL)514 && (in_8(&mr->bus_status0) & BS0_IO)) {515 /* looks like a reselection - try resetting the mesh */516 dlog(ms, "resel? after arb, intr/exc/err/fc=%.8x",517 MKWORD(mr->interrupt, mr->exception, mr->error, mr->fifo_count));518 out_8(&mr->sequence, SEQ_RESETMESH);519 mesh_flush_io(mr);520 udelay(10);521 out_8(&mr->interrupt, INT_ERROR | INT_EXCEPTION | INT_CMDDONE);522 out_8(&mr->intr_mask, INT_ERROR | INT_EXCEPTION | INT_CMDDONE);523 out_8(&mr->sequence, SEQ_ENBRESEL);524 mesh_flush_io(mr);525 for (t = 10; t > 0 && in_8(&mr->interrupt) == 0; --t)526 udelay(1);527 dlog(ms, "tried reset after arb, intr/exc/err/fc=%.8x",528 MKWORD(mr->interrupt, mr->exception, mr->error, mr->fifo_count));529#ifndef MESH_MULTIPLE_HOSTS530 if (in_8(&mr->interrupt) == 0 && (in_8(&mr->bus_status1) & BS1_SEL)531 && (in_8(&mr->bus_status0) & BS0_IO)) {532 printk(KERN_ERR "mesh: controller not responding"533 " to reselection!\n");534 /*535 * If this is a target reselecting us, and the536 * mesh isn't responding, the higher levels of537 * the scsi code will eventually time out and538 * reset the bus.539 */540 }541#endif542 }543}544 545/*546 * Start the next command for a MESH.547 * Should be called with interrupts disabled.548 */549static void mesh_start(struct mesh_state *ms)550{551 struct scsi_cmnd *cmd, *prev, *next;552 553 if (ms->phase != idle || ms->current_req != NULL) {554 printk(KERN_ERR "inappropriate mesh_start (phase=%d, ms=%p)",555 ms->phase, ms);556 return;557 }558 559 while (ms->phase == idle) {560 prev = NULL;561 for (cmd = ms->request_q; ; cmd = (struct scsi_cmnd *) cmd->host_scribble) {562 if (cmd == NULL)563 return;564 if (ms->tgts[cmd->device->id].current_req == NULL)565 break;566 prev = cmd;567 }568 next = (struct scsi_cmnd *) cmd->host_scribble;569 if (prev == NULL)570 ms->request_q = next;571 else572 prev->host_scribble = (void *) next;573 if (next == NULL)574 ms->request_qtail = prev;575 576 mesh_start_cmd(ms, cmd);577 }578}579 580static void mesh_done(struct mesh_state *ms, int start_next)581{582 struct scsi_cmnd *cmd;583 struct mesh_target *tp = &ms->tgts[ms->conn_tgt];584 585 cmd = ms->current_req;586 ms->current_req = NULL;587 tp->current_req = NULL;588 if (cmd) {589 struct mesh_cmd_priv *mcmd = mesh_priv(cmd);590 591 set_host_byte(cmd, ms->stat);592 set_status_byte(cmd, mcmd->status);593 if (ms->stat == DID_OK)594 scsi_msg_to_host_byte(cmd, mcmd->message);595 if (DEBUG_TARGET(cmd)) {596 printk(KERN_DEBUG "mesh_done: result = %x, data_ptr=%d, buflen=%d\n",597 cmd->result, ms->data_ptr, scsi_bufflen(cmd));598#if 0599 /* needs to use sg? */600 if ((cmd->cmnd[0] == 0 || cmd->cmnd[0] == 0x12 || cmd->cmnd[0] == 3)601 && cmd->request_buffer != 0) {602 unsigned char *b = cmd->request_buffer;603 printk(KERN_DEBUG "buffer = %x %x %x %x %x %x %x %x\n",604 b[0], b[1], b[2], b[3], b[4], b[5], b[6], b[7]);605 }606#endif607 }608 mcmd->this_residual -= ms->data_ptr;609 scsi_done(cmd);610 }611 if (start_next) {612 out_8(&ms->mesh->sequence, SEQ_ENBRESEL);613 mesh_flush_io(ms->mesh);614 udelay(1);615 ms->phase = idle;616 mesh_start(ms);617 }618}619 620static inline void add_sdtr_msg(struct mesh_state *ms)621{622 int i = ms->n_msgout;623 624 ms->msgout[i] = EXTENDED_MESSAGE;625 ms->msgout[i+1] = 3;626 ms->msgout[i+2] = EXTENDED_SDTR;627 ms->msgout[i+3] = mesh_sync_period/4;628 ms->msgout[i+4] = (ALLOW_SYNC(ms->conn_tgt)? mesh_sync_offset: 0);629 ms->n_msgout = i + 5;630}631 632static void set_sdtr(struct mesh_state *ms, int period, int offset)633{634 struct mesh_target *tp = &ms->tgts[ms->conn_tgt];635 volatile struct mesh_regs __iomem *mr = ms->mesh;636 int v, tr;637 638 tp->sdtr_state = sdtr_done;639 if (offset == 0) {640 /* asynchronous */641 if (SYNC_OFF(tp->sync_params))642 printk(KERN_INFO "mesh: target %d now asynchronous\n",643 ms->conn_tgt);644 tp->sync_params = ASYNC_PARAMS;645 out_8(&mr->sync_params, ASYNC_PARAMS);646 return;647 }648 /*649 * We need to compute ceil(clk_freq * period / 500e6) - 2650 * without incurring overflow.651 */652 v = (ms->clk_freq / 5000) * period;653 if (v <= 250000) {654 /* special case: sync_period == 5 * clk_period */655 v = 0;656 /* units of tr are 100kB/s */657 tr = (ms->clk_freq + 250000) / 500000;658 } else {659 /* sync_period == (v + 2) * 2 * clk_period */660 v = (v + 99999) / 100000 - 2;661 if (v > 15)662 v = 15; /* oops */663 tr = ((ms->clk_freq / (v + 2)) + 199999) / 200000;664 }665 if (offset > 15)666 offset = 15; /* can't happen */667 tp->sync_params = SYNC_PARAMS(offset, v);668 out_8(&mr->sync_params, tp->sync_params);669 printk(KERN_INFO "mesh: target %d synchronous at %d.%d MB/s\n",670 ms->conn_tgt, tr/10, tr%10);671}672 673static void start_phase(struct mesh_state *ms)674{675 int i, seq, nb;676 volatile struct mesh_regs __iomem *mr = ms->mesh;677 volatile struct dbdma_regs __iomem *md = ms->dma;678 struct scsi_cmnd *cmd = ms->current_req;679 struct mesh_target *tp = &ms->tgts[ms->conn_tgt];680 681 dlog(ms, "start_phase nmo/exc/fc/seq = %.8x",682 MKWORD(ms->n_msgout, mr->exception, mr->fifo_count, mr->sequence));683 out_8(&mr->interrupt, INT_ERROR | INT_EXCEPTION | INT_CMDDONE);684 seq = use_active_neg + (ms->n_msgout? SEQ_ATN: 0);685 switch (ms->msgphase) {686 case msg_none:687 break;688 689 case msg_in:690 out_8(&mr->count_hi, 0);691 out_8(&mr->count_lo, 1);692 out_8(&mr->sequence, SEQ_MSGIN + seq);693 ms->n_msgin = 0;694 return;695 696 case msg_out:697 /*698 * To make sure ATN drops before we assert ACK for699 * the last byte of the message, we have to do the700 * last byte specially.701 */702 if (ms->n_msgout <= 0) {703 printk(KERN_ERR "mesh: msg_out but n_msgout=%d\n",704 ms->n_msgout);705 mesh_dump_regs(ms);706 ms->msgphase = msg_none;707 break;708 }709 if (ALLOW_DEBUG(ms->conn_tgt)) {710 printk(KERN_DEBUG "mesh: sending %d msg bytes:",711 ms->n_msgout);712 for (i = 0; i < ms->n_msgout; ++i)713 printk(" %x", ms->msgout[i]);714 printk("\n");715 }716 dlog(ms, "msgout msg=%.8x", MKWORD(ms->n_msgout, ms->msgout[0],717 ms->msgout[1], ms->msgout[2]));718 out_8(&mr->count_hi, 0);719 out_8(&mr->sequence, SEQ_FLUSHFIFO);720 mesh_flush_io(mr);721 udelay(1);722 /*723 * If ATN is not already asserted, we assert it, then724 * issue a SEQ_MSGOUT to get the mesh to drop ACK.725 */726 if ((in_8(&mr->bus_status0) & BS0_ATN) == 0) {727 dlog(ms, "bus0 was %.2x explicitly asserting ATN", mr->bus_status0);728 out_8(&mr->bus_status0, BS0_ATN); /* explicit ATN */729 mesh_flush_io(mr);730 udelay(1);731 out_8(&mr->count_lo, 1);732 out_8(&mr->sequence, SEQ_MSGOUT + seq);733 out_8(&mr->bus_status0, 0); /* release explicit ATN */734 dlog(ms,"hace: after explicit ATN bus0=%.2x",mr->bus_status0);735 }736 if (ms->n_msgout == 1) {737 /*738 * We can't issue the SEQ_MSGOUT without ATN739 * until the target has asserted REQ. The logic740 * in cmd_complete handles both situations:741 * REQ already asserted or not.742 */743 cmd_complete(ms);744 } else {745 out_8(&mr->count_lo, ms->n_msgout - 1);746 out_8(&mr->sequence, SEQ_MSGOUT + seq);747 for (i = 0; i < ms->n_msgout - 1; ++i)748 out_8(&mr->fifo, ms->msgout[i]);749 }750 return;751 752 default:753 printk(KERN_ERR "mesh bug: start_phase msgphase=%d\n",754 ms->msgphase);755 }756 757 switch (ms->phase) {758 case selecting:759 out_8(&mr->dest_id, ms->conn_tgt);760 out_8(&mr->sequence, SEQ_SELECT + SEQ_ATN);761 break;762 case commanding:763 out_8(&mr->sync_params, tp->sync_params);764 out_8(&mr->count_hi, 0);765 if (cmd) {766 out_8(&mr->count_lo, cmd->cmd_len);767 out_8(&mr->sequence, SEQ_COMMAND + seq);768 for (i = 0; i < cmd->cmd_len; ++i)769 out_8(&mr->fifo, cmd->cmnd[i]);770 } else {771 out_8(&mr->count_lo, 6);772 out_8(&mr->sequence, SEQ_COMMAND + seq);773 for (i = 0; i < 6; ++i)774 out_8(&mr->fifo, 0);775 }776 break;777 case dataing:778 /* transfer data, if any */779 if (!ms->dma_started) {780 set_dma_cmds(ms, cmd);781 out_le32(&md->cmdptr, virt_to_phys(ms->dma_cmds));782 out_le32(&md->control, (RUN << 16) | RUN);783 ms->dma_started = 1;784 }785 nb = ms->dma_count;786 if (nb > 0xfff0)787 nb = 0xfff0;788 ms->dma_count -= nb;789 ms->data_ptr += nb;790 out_8(&mr->count_lo, nb);791 out_8(&mr->count_hi, nb >> 8);792 out_8(&mr->sequence, (tp->data_goes_out?793 SEQ_DATAOUT: SEQ_DATAIN) + SEQ_DMA_MODE + seq);794 break;795 case statusing:796 out_8(&mr->count_hi, 0);797 out_8(&mr->count_lo, 1);798 out_8(&mr->sequence, SEQ_STATUS + seq);799 break;800 case busfreeing:801 case disconnecting:802 out_8(&mr->sequence, SEQ_ENBRESEL);803 mesh_flush_io(mr);804 udelay(1);805 dlog(ms, "enbresel intr/exc/err/fc=%.8x",806 MKWORD(mr->interrupt, mr->exception, mr->error,807 mr->fifo_count));808 out_8(&mr->sequence, SEQ_BUSFREE);809 break;810 default:811 printk(KERN_ERR "mesh: start_phase called with phase=%d\n",812 ms->phase);813 dumpslog(ms);814 }815 816}817 818static inline void get_msgin(struct mesh_state *ms)819{820 volatile struct mesh_regs __iomem *mr = ms->mesh;821 int i, n;822 823 n = mr->fifo_count;824 if (n != 0) {825 i = ms->n_msgin;826 ms->n_msgin = i + n;827 for (; n > 0; --n)828 ms->msgin[i++] = in_8(&mr->fifo);829 }830}831 832static inline int msgin_length(struct mesh_state *ms)833{834 int b, n;835 836 n = 1;837 if (ms->n_msgin > 0) {838 b = ms->msgin[0];839 if (b == 1) {840 /* extended message */841 n = ms->n_msgin < 2? 2: ms->msgin[1] + 2;842 } else if (0x20 <= b && b <= 0x2f) {843 /* 2-byte message */844 n = 2;845 }846 }847 return n;848}849 850static void reselected(struct mesh_state *ms)851{852 volatile struct mesh_regs __iomem *mr = ms->mesh;853 struct scsi_cmnd *cmd;854 struct mesh_target *tp;855 int b, t, prev;856 857 switch (ms->phase) {858 case idle:859 break;860 case arbitrating:861 if ((cmd = ms->current_req) != NULL) {862 /* put the command back on the queue */863 cmd->host_scribble = (void *) ms->request_q;864 if (ms->request_q == NULL)865 ms->request_qtail = cmd;866 ms->request_q = cmd;867 tp = &ms->tgts[cmd->device->id];868 tp->current_req = NULL;869 }870 break;871 case busfreeing:872 ms->phase = reselecting;873 mesh_done(ms, 0);874 break;875 case disconnecting:876 break;877 default:878 printk(KERN_ERR "mesh: reselected in phase %d/%d tgt %d\n",879 ms->msgphase, ms->phase, ms->conn_tgt);880 dumplog(ms, ms->conn_tgt);881 dumpslog(ms);882 }883 884 if (ms->dma_started) {885 printk(KERN_ERR "mesh: reselected with DMA started !\n");886 halt_dma(ms);887 }888 ms->current_req = NULL;889 ms->phase = dataing;890 ms->msgphase = msg_in;891 ms->n_msgout = 0;892 ms->last_n_msgout = 0;893 prev = ms->conn_tgt;894 895 /*896 * We seem to get abortive reselections sometimes.897 */898 while ((in_8(&mr->bus_status1) & BS1_BSY) == 0) {899 static int mesh_aborted_resels;900 mesh_aborted_resels++;901 out_8(&mr->interrupt, INT_ERROR | INT_EXCEPTION | INT_CMDDONE);902 mesh_flush_io(mr);903 udelay(1);904 out_8(&mr->sequence, SEQ_ENBRESEL);905 mesh_flush_io(mr);906 udelay(5);907 dlog(ms, "extra resel err/exc/fc = %.6x",908 MKWORD(0, mr->error, mr->exception, mr->fifo_count));909 }910 out_8(&mr->interrupt, INT_ERROR | INT_EXCEPTION | INT_CMDDONE);911 mesh_flush_io(mr);912 udelay(1);913 out_8(&mr->sequence, SEQ_ENBRESEL);914 mesh_flush_io(mr);915 udelay(1);916 out_8(&mr->sync_params, ASYNC_PARAMS);917 918 /*919 * Find out who reselected us.920 */921 if (in_8(&mr->fifo_count) == 0) {922 printk(KERN_ERR "mesh: reselection but nothing in fifo?\n");923 ms->conn_tgt = ms->host->this_id;924 goto bogus;925 }926 /* get the last byte in the fifo */927 do {928 b = in_8(&mr->fifo);929 dlog(ms, "reseldata %x", b);930 } while (in_8(&mr->fifo_count));931 for (t = 0; t < 8; ++t)932 if ((b & (1 << t)) != 0 && t != ms->host->this_id)933 break;934 if (b != (1 << t) + (1 << ms->host->this_id)) {935 printk(KERN_ERR "mesh: bad reselection data %x\n", b);936 ms->conn_tgt = ms->host->this_id;937 goto bogus;938 }939 940 941 /*942 * Set up to continue with that target's transfer.943 */944 ms->conn_tgt = t;945 tp = &ms->tgts[t];946 out_8(&mr->sync_params, tp->sync_params);947 if (ALLOW_DEBUG(t)) {948 printk(KERN_DEBUG "mesh: reselected by target %d\n", t);949 printk(KERN_DEBUG "mesh: saved_ptr=%x goes_out=%d cmd=%p\n",950 tp->saved_ptr, tp->data_goes_out, tp->current_req);951 }952 ms->current_req = tp->current_req;953 if (tp->current_req == NULL) {954 printk(KERN_ERR "mesh: reselected by tgt %d but no cmd!\n", t);955 goto bogus;956 }957 ms->data_ptr = tp->saved_ptr;958 dlog(ms, "resel prev tgt=%d", prev);959 dlog(ms, "resel err/exc=%.4x", MKWORD(0, 0, mr->error, mr->exception));960 start_phase(ms);961 return;962 963bogus:964 dumplog(ms, ms->conn_tgt);965 dumpslog(ms);966 ms->data_ptr = 0;967 ms->aborting = 1;968 start_phase(ms);969}970 971static void do_abort(struct mesh_state *ms)972{973 ms->msgout[0] = ABORT;974 ms->n_msgout = 1;975 ms->aborting = 1;976 ms->stat = DID_ABORT;977 dlog(ms, "abort", 0);978}979 980static void handle_reset(struct mesh_state *ms)981{982 int tgt;983 struct mesh_target *tp;984 struct scsi_cmnd *cmd;985 volatile struct mesh_regs __iomem *mr = ms->mesh;986 987 for (tgt = 0; tgt < 8; ++tgt) {988 tp = &ms->tgts[tgt];989 if ((cmd = tp->current_req) != NULL) {990 set_host_byte(cmd, DID_RESET);991 tp->current_req = NULL;992 scsi_done(cmd);993 }994 ms->tgts[tgt].sdtr_state = do_sdtr;995 ms->tgts[tgt].sync_params = ASYNC_PARAMS;996 }997 ms->current_req = NULL;998 while ((cmd = ms->request_q) != NULL) {999 ms->request_q = (struct scsi_cmnd *) cmd->host_scribble;1000 set_host_byte(cmd, DID_RESET);1001 scsi_done(cmd);1002 }1003 ms->phase = idle;1004 ms->msgphase = msg_none;1005 out_8(&mr->interrupt, INT_ERROR | INT_EXCEPTION | INT_CMDDONE);1006 out_8(&mr->sequence, SEQ_FLUSHFIFO);1007 mesh_flush_io(mr);1008 udelay(1);1009 out_8(&mr->sync_params, ASYNC_PARAMS);1010 out_8(&mr->sequence, SEQ_ENBRESEL);1011}1012 1013static irqreturn_t do_mesh_interrupt(int irq, void *dev_id)1014{1015 unsigned long flags;1016 struct mesh_state *ms = dev_id;1017 struct Scsi_Host *dev = ms->host;1018 1019 spin_lock_irqsave(dev->host_lock, flags);1020 mesh_interrupt(ms);1021 spin_unlock_irqrestore(dev->host_lock, flags);1022 return IRQ_HANDLED;1023}1024 1025static void handle_error(struct mesh_state *ms)1026{1027 int err, exc, count;1028 volatile struct mesh_regs __iomem *mr = ms->mesh;1029 1030 err = in_8(&mr->error);1031 exc = in_8(&mr->exception);1032 out_8(&mr->interrupt, INT_ERROR | INT_EXCEPTION | INT_CMDDONE);1033 dlog(ms, "error err/exc/fc/cl=%.8x",1034 MKWORD(err, exc, mr->fifo_count, mr->count_lo));1035 if (err & ERR_SCSIRESET) {1036 /* SCSI bus was reset */1037 printk(KERN_INFO "mesh: SCSI bus reset detected: "1038 "waiting for end...");1039 while ((in_8(&mr->bus_status1) & BS1_RST) != 0)1040 udelay(1);1041 printk("done\n");1042 if (ms->dma_started)1043 halt_dma(ms);1044 handle_reset(ms);1045 /* request_q is empty, no point in mesh_start() */1046 return;1047 }1048 if (err & ERR_UNEXPDISC) {1049 /* Unexpected disconnect */1050 if (exc & EXC_RESELECTED) {1051 reselected(ms);1052 return;1053 }1054 if (!ms->aborting) {1055 printk(KERN_WARNING "mesh: target %d aborted\n",1056 ms->conn_tgt);1057 dumplog(ms, ms->conn_tgt);1058 dumpslog(ms);1059 }1060 out_8(&mr->interrupt, INT_CMDDONE);1061 ms->stat = DID_ABORT;1062 mesh_done(ms, 1);1063 return;1064 }1065 if (err & ERR_PARITY) {1066 if (ms->msgphase == msg_in) {1067 printk(KERN_ERR "mesh: msg parity error, target %d\n",1068 ms->conn_tgt);1069 ms->msgout[0] = MSG_PARITY_ERROR;1070 ms->n_msgout = 1;1071 ms->msgphase = msg_in_bad;1072 cmd_complete(ms);1073 return;1074 }1075 if (ms->stat == DID_OK) {1076 printk(KERN_ERR "mesh: parity error, target %d\n",1077 ms->conn_tgt);1078 ms->stat = DID_PARITY;1079 }1080 count = (mr->count_hi << 8) + mr->count_lo;1081 if (count == 0) {1082 cmd_complete(ms);1083 } else {1084 /* reissue the data transfer command */1085 out_8(&mr->sequence, mr->sequence);1086 }1087 return;1088 }1089 if (err & ERR_SEQERR) {1090 if (exc & EXC_RESELECTED) {1091 /* This can happen if we issue a command to1092 get the bus just after the target reselects us. */1093 static int mesh_resel_seqerr;1094 mesh_resel_seqerr++;1095 reselected(ms);1096 return;1097 }1098 if (exc == EXC_PHASEMM) {1099 static int mesh_phasemm_seqerr;1100 mesh_phasemm_seqerr++;1101 phase_mismatch(ms);1102 return;1103 }1104 printk(KERN_ERR "mesh: sequence error (err=%x exc=%x)\n",1105 err, exc);1106 } else {1107 printk(KERN_ERR "mesh: unknown error %x (exc=%x)\n", err, exc);1108 }1109 mesh_dump_regs(ms);1110 dumplog(ms, ms->conn_tgt);1111 if (ms->phase > selecting && (in_8(&mr->bus_status1) & BS1_BSY)) {1112 /* try to do what the target wants */1113 do_abort(ms);1114 phase_mismatch(ms);1115 return;1116 }1117 ms->stat = DID_ERROR;1118 mesh_done(ms, 1);1119}1120 1121static void handle_exception(struct mesh_state *ms)1122{1123 int exc;1124 volatile struct mesh_regs __iomem *mr = ms->mesh;1125 1126 exc = in_8(&mr->exception);1127 out_8(&mr->interrupt, INT_EXCEPTION | INT_CMDDONE);1128 if (exc & EXC_RESELECTED) {1129 static int mesh_resel_exc;1130 mesh_resel_exc++;1131 reselected(ms);1132 } else if (exc == EXC_ARBLOST) {1133 printk(KERN_DEBUG "mesh: lost arbitration\n");1134 ms->stat = DID_BUS_BUSY;1135 mesh_done(ms, 1);1136 } else if (exc == EXC_SELTO) {1137 /* selection timed out */1138 ms->stat = DID_BAD_TARGET;1139 mesh_done(ms, 1);1140 } else if (exc == EXC_PHASEMM) {1141 /* target wants to do something different:1142 find out what it wants and do it. */1143 phase_mismatch(ms);1144 } else {1145 printk(KERN_ERR "mesh: can't cope with exception %x\n", exc);1146 mesh_dump_regs(ms);1147 dumplog(ms, ms->conn_tgt);1148 do_abort(ms);1149 phase_mismatch(ms);1150 }1151}1152 1153static void handle_msgin(struct mesh_state *ms)1154{1155 int i, code;1156 struct scsi_cmnd *cmd = ms->current_req;1157 struct mesh_target *tp = &ms->tgts[ms->conn_tgt];1158 1159 if (ms->n_msgin == 0)1160 return;1161 code = ms->msgin[0];1162 if (ALLOW_DEBUG(ms->conn_tgt)) {1163 printk(KERN_DEBUG "got %d message bytes:", ms->n_msgin);1164 for (i = 0; i < ms->n_msgin; ++i)1165 printk(" %x", ms->msgin[i]);1166 printk("\n");1167 }1168 dlog(ms, "msgin msg=%.8x",1169 MKWORD(ms->n_msgin, code, ms->msgin[1], ms->msgin[2]));1170 1171 ms->expect_reply = 0;1172 ms->n_msgout = 0;1173 if (ms->n_msgin < msgin_length(ms))1174 goto reject;1175 if (cmd)1176 mesh_priv(cmd)->message = code;1177 switch (code) {1178 case COMMAND_COMPLETE:1179 break;1180 case EXTENDED_MESSAGE:1181 switch (ms->msgin[2]) {1182 case EXTENDED_MODIFY_DATA_POINTER:1183 ms->data_ptr += (ms->msgin[3] << 24) + ms->msgin[6]1184 + (ms->msgin[4] << 16) + (ms->msgin[5] << 8);1185 break;1186 case EXTENDED_SDTR:1187 if (tp->sdtr_state != sdtr_sent) {1188 /* reply with an SDTR */1189 add_sdtr_msg(ms);1190 /* limit period to at least his value,1191 offset to no more than his */1192 if (ms->msgout[3] < ms->msgin[3])1193 ms->msgout[3] = ms->msgin[3];1194 if (ms->msgout[4] > ms->msgin[4])1195 ms->msgout[4] = ms->msgin[4];1196 set_sdtr(ms, ms->msgout[3], ms->msgout[4]);1197 ms->msgphase = msg_out;1198 } else {1199 set_sdtr(ms, ms->msgin[3], ms->msgin[4]);1200 }1201 break;1202 default:1203 goto reject;1204 }1205 break;1206 case SAVE_POINTERS:1207 tp->saved_ptr = ms->data_ptr;1208 break;1209 case RESTORE_POINTERS:1210 ms->data_ptr = tp->saved_ptr;1211 break;1212 case DISCONNECT:1213 ms->phase = disconnecting;1214 break;1215 case ABORT:1216 break;1217 case MESSAGE_REJECT:1218 if (tp->sdtr_state == sdtr_sent)1219 set_sdtr(ms, 0, 0);1220 break;1221 case NOP:1222 break;1223 default:1224 if (IDENTIFY_BASE <= code && code <= IDENTIFY_BASE + 7) {1225 if (cmd == NULL) {1226 do_abort(ms);1227 ms->msgphase = msg_out;1228 } else if (code != cmd->device->lun + IDENTIFY_BASE) {1229 printk(KERN_WARNING "mesh: lun mismatch "1230 "(%d != %llu) on reselection from "1231 "target %d\n", code - IDENTIFY_BASE,1232 cmd->device->lun, ms->conn_tgt);1233 }1234 break;1235 }1236 goto reject;1237 }1238 return;1239 1240 reject:1241 printk(KERN_WARNING "mesh: rejecting message from target %d:",1242 ms->conn_tgt);1243 for (i = 0; i < ms->n_msgin; ++i)1244 printk(" %x", ms->msgin[i]);1245 printk("\n");1246 ms->msgout[0] = MESSAGE_REJECT;1247 ms->n_msgout = 1;1248 ms->msgphase = msg_out;1249}1250 1251/*1252 * Set up DMA commands for transferring data.1253 */1254static void set_dma_cmds(struct mesh_state *ms, struct scsi_cmnd *cmd)1255{1256 int i, dma_cmd, total, off, dtot;1257 struct scatterlist *scl;1258 struct dbdma_cmd *dcmds;1259 1260 dma_cmd = ms->tgts[ms->conn_tgt].data_goes_out?1261 OUTPUT_MORE: INPUT_MORE;1262 dcmds = ms->dma_cmds;1263 dtot = 0;1264 if (cmd) {1265 int nseg;1266 1267 mesh_priv(cmd)->this_residual = scsi_bufflen(cmd);1268 1269 nseg = scsi_dma_map(cmd);1270 BUG_ON(nseg < 0);1271 1272 if (nseg) {1273 total = 0;1274 off = ms->data_ptr;1275 1276 scsi_for_each_sg(cmd, scl, nseg, i) {1277 u32 dma_addr = sg_dma_address(scl);1278 u32 dma_len = sg_dma_len(scl);1279 1280 total += scl->length;1281 if (off >= dma_len) {1282 off -= dma_len;1283 continue;1284 }1285 if (dma_len > 0xffff)1286 panic("mesh: scatterlist element >= 64k");1287 dcmds->req_count = cpu_to_le16(dma_len - off);1288 dcmds->command = cpu_to_le16(dma_cmd);1289 dcmds->phy_addr = cpu_to_le32(dma_addr + off);1290 dcmds->xfer_status = 0;1291 ++dcmds;1292 dtot += dma_len - off;1293 off = 0;1294 }1295 }1296 }1297 if (dtot == 0) {1298 /* Either the target has overrun our buffer,1299 or the caller didn't provide a buffer. */1300 static char mesh_extra_buf[64];1301 1302 dtot = sizeof(mesh_extra_buf);1303 dcmds->req_count = cpu_to_le16(dtot);1304 dcmds->phy_addr = cpu_to_le32(virt_to_phys(mesh_extra_buf));1305 dcmds->xfer_status = 0;1306 ++dcmds;1307 }1308 dma_cmd += OUTPUT_LAST - OUTPUT_MORE;1309 dcmds[-1].command = cpu_to_le16(dma_cmd);1310 memset(dcmds, 0, sizeof(*dcmds));1311 dcmds->command = cpu_to_le16(DBDMA_STOP);1312 ms->dma_count = dtot;1313}1314 1315static void halt_dma(struct mesh_state *ms)1316{1317 volatile struct dbdma_regs __iomem *md = ms->dma;1318 volatile struct mesh_regs __iomem *mr = ms->mesh;1319 struct scsi_cmnd *cmd = ms->current_req;1320 int t, nb;1321 1322 if (!ms->tgts[ms->conn_tgt].data_goes_out) {1323 /* wait a little while until the fifo drains */1324 t = 50;1325 while (t > 0 && in_8(&mr->fifo_count) != 01326 && (in_le32(&md->status) & ACTIVE) != 0) {1327 --t;1328 udelay(1);1329 }1330 }1331 out_le32(&md->control, RUN << 16); /* turn off RUN bit */1332 nb = (mr->count_hi << 8) + mr->count_lo;1333 dlog(ms, "halt_dma fc/count=%.6x",1334 MKWORD(0, mr->fifo_count, 0, nb));1335 if (ms->tgts[ms->conn_tgt].data_goes_out)1336 nb += mr->fifo_count;1337 /* nb is the number of bytes not yet transferred1338 to/from the target. */1339 ms->data_ptr -= nb;1340 dlog(ms, "data_ptr %x", ms->data_ptr);1341 if (ms->data_ptr < 0) {1342 printk(KERN_ERR "mesh: halt_dma: data_ptr=%d (nb=%d, ms=%p)\n",1343 ms->data_ptr, nb, ms);1344 ms->data_ptr = 0;1345#ifdef MESH_DBG1346 dumplog(ms, ms->conn_tgt);1347 dumpslog(ms);1348#endif /* MESH_DBG */1349 } else if (cmd && scsi_bufflen(cmd) &&1350 ms->data_ptr > scsi_bufflen(cmd)) {1351 printk(KERN_DEBUG "mesh: target %d overrun, "1352 "data_ptr=%x total=%x goes_out=%d\n",1353 ms->conn_tgt, ms->data_ptr, scsi_bufflen(cmd),1354 ms->tgts[ms->conn_tgt].data_goes_out);1355 }1356 if (cmd)1357 scsi_dma_unmap(cmd);1358 ms->dma_started = 0;1359}1360 1361static void phase_mismatch(struct mesh_state *ms)1362{1363 volatile struct mesh_regs __iomem *mr = ms->mesh;1364 int phase;1365 1366 dlog(ms, "phasemm ch/cl/seq/fc=%.8x",1367 MKWORD(mr->count_hi, mr->count_lo, mr->sequence, mr->fifo_count));1368 phase = in_8(&mr->bus_status0) & BS0_PHASE;1369 if (ms->msgphase == msg_out_xxx && phase == BP_MSGOUT) {1370 /* output the last byte of the message, without ATN */1371 out_8(&mr->count_lo, 1);1372 out_8(&mr->sequence, SEQ_MSGOUT + use_active_neg);1373 mesh_flush_io(mr);1374 udelay(1);1375 out_8(&mr->fifo, ms->msgout[ms->n_msgout-1]);1376 ms->msgphase = msg_out_last;1377 return;1378 }1379 1380 if (ms->msgphase == msg_in) {1381 get_msgin(ms);1382 if (ms->n_msgin)1383 handle_msgin(ms);1384 }1385 1386 if (ms->dma_started)1387 halt_dma(ms);1388 if (mr->fifo_count) {1389 out_8(&mr->sequence, SEQ_FLUSHFIFO);1390 mesh_flush_io(mr);1391 udelay(1);1392 }1393 1394 ms->msgphase = msg_none;1395 switch (phase) {1396 case BP_DATAIN:1397 ms->tgts[ms->conn_tgt].data_goes_out = 0;1398 ms->phase = dataing;1399 break;1400 case BP_DATAOUT:1401 ms->tgts[ms->conn_tgt].data_goes_out = 1;1402 ms->phase = dataing;1403 break;1404 case BP_COMMAND:1405 ms->phase = commanding;1406 break;1407 case BP_STATUS:1408 ms->phase = statusing;1409 break;1410 case BP_MSGIN:1411 ms->msgphase = msg_in;1412 ms->n_msgin = 0;1413 break;1414 case BP_MSGOUT:1415 ms->msgphase = msg_out;1416 if (ms->n_msgout == 0) {1417 if (ms->aborting) {1418 do_abort(ms);1419 } else {1420 if (ms->last_n_msgout == 0) {1421 printk(KERN_DEBUG1422 "mesh: no msg to repeat\n");1423 ms->msgout[0] = NOP;1424 ms->last_n_msgout = 1;1425 }1426 ms->n_msgout = ms->last_n_msgout;1427 }1428 }1429 break;1430 default:1431 printk(KERN_DEBUG "mesh: unknown scsi phase %x\n", phase);1432 ms->stat = DID_ERROR;1433 mesh_done(ms, 1);1434 return;1435 }1436 1437 start_phase(ms);1438}1439 1440static void cmd_complete(struct mesh_state *ms)1441{1442 volatile struct mesh_regs __iomem *mr = ms->mesh;1443 struct scsi_cmnd *cmd = ms->current_req;1444 struct mesh_target *tp = &ms->tgts[ms->conn_tgt];1445 int seq, n, t;1446 1447 dlog(ms, "cmd_complete fc=%x", mr->fifo_count);1448 seq = use_active_neg + (ms->n_msgout? SEQ_ATN: 0);1449 switch (ms->msgphase) {1450 case msg_out_xxx:1451 /* huh? we expected a phase mismatch */1452 ms->n_msgin = 0;1453 ms->msgphase = msg_in;1454 fallthrough;1455 1456 case msg_in:1457 /* should have some message bytes in fifo */1458 get_msgin(ms);1459 n = msgin_length(ms);1460 if (ms->n_msgin < n) {1461 out_8(&mr->count_lo, n - ms->n_msgin);1462 out_8(&mr->sequence, SEQ_MSGIN + seq);1463 } else {1464 ms->msgphase = msg_none;1465 handle_msgin(ms);1466 start_phase(ms);1467 }1468 break;1469 1470 case msg_in_bad:1471 out_8(&mr->sequence, SEQ_FLUSHFIFO);1472 mesh_flush_io(mr);1473 udelay(1);1474 out_8(&mr->count_lo, 1);1475 out_8(&mr->sequence, SEQ_MSGIN + SEQ_ATN + use_active_neg);1476 break;1477 1478 case msg_out:1479 /*1480 * To get the right timing on ATN wrt ACK, we have1481 * to get the MESH to drop ACK, wait until REQ gets1482 * asserted, then drop ATN. To do this we first1483 * issue a SEQ_MSGOUT with ATN and wait for REQ,1484 * then change the command to a SEQ_MSGOUT w/o ATN.1485 * If we don't see REQ in a reasonable time, we1486 * change the command to SEQ_MSGIN with ATN,1487 * wait for the phase mismatch interrupt, then1488 * issue the SEQ_MSGOUT without ATN.1489 */1490 out_8(&mr->count_lo, 1);1491 out_8(&mr->sequence, SEQ_MSGOUT + use_active_neg + SEQ_ATN);1492 t = 30; /* wait up to 30us */1493 while ((in_8(&mr->bus_status0) & BS0_REQ) == 0 && --t >= 0)1494 udelay(1);1495 dlog(ms, "last_mbyte err/exc/fc/cl=%.8x",1496 MKWORD(mr->error, mr->exception,1497 mr->fifo_count, mr->count_lo));1498 if (in_8(&mr->interrupt) & (INT_ERROR | INT_EXCEPTION)) {1499 /* whoops, target didn't do what we expected */1500 ms->last_n_msgout = ms->n_msgout;1501 ms->n_msgout = 0;1502 if (in_8(&mr->interrupt) & INT_ERROR) {1503 printk(KERN_ERR "mesh: error %x in msg_out\n",1504 in_8(&mr->error));1505 handle_error(ms);1506 return;1507 }1508 if (in_8(&mr->exception) != EXC_PHASEMM)1509 printk(KERN_ERR "mesh: exc %x in msg_out\n",1510 in_8(&mr->exception));1511 else1512 printk(KERN_DEBUG "mesh: bs0=%x in msg_out\n",1513 in_8(&mr->bus_status0));1514 handle_exception(ms);1515 return;1516 }1517 if (in_8(&mr->bus_status0) & BS0_REQ) {1518 out_8(&mr->sequence, SEQ_MSGOUT + use_active_neg);1519 mesh_flush_io(mr);1520 udelay(1);1521 out_8(&mr->fifo, ms->msgout[ms->n_msgout-1]);1522 ms->msgphase = msg_out_last;1523 } else {1524 out_8(&mr->sequence, SEQ_MSGIN + use_active_neg + SEQ_ATN);1525 ms->msgphase = msg_out_xxx;1526 }1527 break;1528 1529 case msg_out_last:1530 ms->last_n_msgout = ms->n_msgout;1531 ms->n_msgout = 0;1532 ms->msgphase = ms->expect_reply? msg_in: msg_none;1533 start_phase(ms);1534 break;1535 1536 case msg_none:1537 switch (ms->phase) {1538 case idle:1539 printk(KERN_ERR "mesh: interrupt in idle phase?\n");1540 dumpslog(ms);1541 return;1542 case selecting:1543 dlog(ms, "Selecting phase at command completion",0);1544 ms->msgout[0] = IDENTIFY(ALLOW_RESEL(ms->conn_tgt),1545 (cmd? cmd->device->lun: 0));1546 ms->n_msgout = 1;1547 ms->expect_reply = 0;1548 if (ms->aborting) {1549 ms->msgout[0] = ABORT;1550 ms->n_msgout++;1551 } else if (tp->sdtr_state == do_sdtr) {1552 /* add SDTR message */1553 add_sdtr_msg(ms);1554 ms->expect_reply = 1;1555 tp->sdtr_state = sdtr_sent;1556 }1557 ms->msgphase = msg_out;1558 /*1559 * We need to wait for REQ before dropping ATN.1560 * We wait for at most 30us, then fall back to1561 * a scheme where we issue a SEQ_COMMAND with ATN,1562 * which will give us a phase mismatch interrupt1563 * when REQ does come, and then we send the message.1564 */1565 t = 230; /* wait up to 230us */1566 while ((in_8(&mr->bus_status0) & BS0_REQ) == 0) {1567 if (--t < 0) {1568 dlog(ms, "impatient for req", ms->n_msgout);1569 ms->msgphase = msg_none;1570 break;1571 }1572 udelay(1);1573 }1574 break;1575 case dataing:1576 if (ms->dma_count != 0) {1577 start_phase(ms);1578 return;1579 }1580 /*1581 * We can get a phase mismatch here if the target1582 * changes to the status phase, even though we have1583 * had a command complete interrupt. Then, if we1584 * issue the SEQ_STATUS command, we'll get a sequence1585 * error interrupt. Which isn't so bad except that1586 * occasionally the mesh actually executes the1587 * SEQ_STATUS *as well as* giving us the sequence1588 * error and phase mismatch exception.1589 */1590 out_8(&mr->sequence, 0);1591 out_8(&mr->interrupt,1592 INT_ERROR | INT_EXCEPTION | INT_CMDDONE);1593 halt_dma(ms);1594 break;1595 case statusing:1596 if (cmd) {1597 struct mesh_cmd_priv *mcmd = mesh_priv(cmd);1598 1599 mcmd->status = mr->fifo;1600 if (DEBUG_TARGET(cmd))1601 printk(KERN_DEBUG "mesh: status is %x\n",1602 mcmd->status);1603 }1604 ms->msgphase = msg_in;1605 break;1606 case busfreeing:1607 mesh_done(ms, 1);1608 return;1609 case disconnecting:1610 ms->current_req = NULL;1611 ms->phase = idle;1612 mesh_start(ms);1613 return;1614 default:1615 break;1616 }1617 ++ms->phase;1618 start_phase(ms);1619 break;1620 }1621}1622 1623 1624/*1625 * Called by midlayer with host locked to queue a new1626 * request1627 */1628static int mesh_queue_lck(struct scsi_cmnd *cmd)1629{1630 struct mesh_state *ms;1631 1632 cmd->host_scribble = NULL;1633 1634 ms = (struct mesh_state *) cmd->device->host->hostdata;1635 1636 if (ms->request_q == NULL)1637 ms->request_q = cmd;1638 else1639 ms->request_qtail->host_scribble = (void *) cmd;1640 ms->request_qtail = cmd;1641 1642 if (ms->phase == idle)1643 mesh_start(ms);1644 1645 return 0;1646}1647 1648static DEF_SCSI_QCMD(mesh_queue)1649 1650/*1651 * Called to handle interrupts, either call by the interrupt1652 * handler (do_mesh_interrupt) or by other functions in1653 * exceptional circumstances1654 */1655static void mesh_interrupt(struct mesh_state *ms)1656{1657 volatile struct mesh_regs __iomem *mr = ms->mesh;1658 int intr;1659 1660#if 01661 if (ALLOW_DEBUG(ms->conn_tgt))1662 printk(KERN_DEBUG "mesh_intr, bs0=%x int=%x exc=%x err=%x "1663 "phase=%d msgphase=%d\n", mr->bus_status0,1664 mr->interrupt, mr->exception, mr->error,1665 ms->phase, ms->msgphase);1666#endif1667 while ((intr = in_8(&mr->interrupt)) != 0) {1668 dlog(ms, "interrupt intr/err/exc/seq=%.8x", 1669 MKWORD(intr, mr->error, mr->exception, mr->sequence));1670 if (intr & INT_ERROR) {1671 handle_error(ms);1672 } else if (intr & INT_EXCEPTION) {1673 handle_exception(ms);1674 } else if (intr & INT_CMDDONE) {1675 out_8(&mr->interrupt, INT_CMDDONE);1676 cmd_complete(ms);1677 }1678 }1679}1680 1681/* Todo: here we can at least try to remove the command from the1682 * queue if it isn't connected yet, and for pending command, assert1683 * ATN until the bus gets freed.1684 */1685static int mesh_abort(struct scsi_cmnd *cmd)1686{1687 struct mesh_state *ms = (struct mesh_state *) cmd->device->host->hostdata;1688 1689 printk(KERN_DEBUG "mesh_abort(%p)\n", cmd);1690 mesh_dump_regs(ms);1691 dumplog(ms, cmd->device->id);1692 dumpslog(ms);1693 return FAILED;1694}1695 1696/*1697 * Called by the midlayer with the lock held to reset the1698 * SCSI host and bus.1699 * The midlayer will wait for devices to come back, we don't need1700 * to do that ourselves1701 */1702static int mesh_host_reset(struct scsi_cmnd *cmd)1703{1704 struct mesh_state *ms = (struct mesh_state *) cmd->device->host->hostdata;1705 volatile struct mesh_regs __iomem *mr = ms->mesh;1706 volatile struct dbdma_regs __iomem *md = ms->dma;1707 unsigned long flags;1708 1709 printk(KERN_DEBUG "mesh_host_reset\n");1710 1711 spin_lock_irqsave(ms->host->host_lock, flags);1712 1713 if (ms->dma_started)1714 halt_dma(ms);1715 1716 /* Reset the controller & dbdma channel */1717 out_le32(&md->control, (RUN|PAUSE|FLUSH|WAKE) << 16); /* stop dma */1718 out_8(&mr->exception, 0xff); /* clear all exception bits */1719 out_8(&mr->error, 0xff); /* clear all error bits */1720 out_8(&mr->sequence, SEQ_RESETMESH);1721 mesh_flush_io(mr);1722 udelay(1);1723 out_8(&mr->intr_mask, INT_ERROR | INT_EXCEPTION | INT_CMDDONE);1724 out_8(&mr->source_id, ms->host->this_id);1725 out_8(&mr->sel_timeout, 25); /* 250ms */1726 out_8(&mr->sync_params, ASYNC_PARAMS);1727 1728 /* Reset the bus */1729 out_8(&mr->bus_status1, BS1_RST); /* assert RST */1730 mesh_flush_io(mr);1731 udelay(30); /* leave it on for >= 25us */1732 out_8(&mr->bus_status1, 0); /* negate RST */1733 1734 /* Complete pending commands */1735 handle_reset(ms);1736 1737 spin_unlock_irqrestore(ms->host->host_lock, flags);1738 return SUCCESS;1739}1740 1741static void set_mesh_power(struct mesh_state *ms, int state)1742{1743 if (!machine_is(powermac))1744 return;1745 if (state) {1746 pmac_call_feature(PMAC_FTR_MESH_ENABLE, macio_get_of_node(ms->mdev), 0, 1);1747 msleep(200);1748 } else {1749 pmac_call_feature(PMAC_FTR_MESH_ENABLE, macio_get_of_node(ms->mdev), 0, 0);1750 msleep(10);1751 }1752}1753 1754 1755#ifdef CONFIG_PM1756static int mesh_suspend(struct macio_dev *mdev, pm_message_t mesg)1757{1758 struct mesh_state *ms = (struct mesh_state *)macio_get_drvdata(mdev);1759 unsigned long flags;1760 1761 switch (mesg.event) {1762 case PM_EVENT_SUSPEND:1763 case PM_EVENT_HIBERNATE:1764 case PM_EVENT_FREEZE:1765 break;1766 default:1767 return 0;1768 }1769 if (ms->phase == sleeping)1770 return 0;1771 1772 scsi_block_requests(ms->host);1773 spin_lock_irqsave(ms->host->host_lock, flags);1774 while(ms->phase != idle) {1775 spin_unlock_irqrestore(ms->host->host_lock, flags);1776 msleep(10);1777 spin_lock_irqsave(ms->host->host_lock, flags);1778 }1779 ms->phase = sleeping;1780 spin_unlock_irqrestore(ms->host->host_lock, flags);1781 disable_irq(ms->meshintr);1782 set_mesh_power(ms, 0);1783 1784 return 0;1785}1786 1787static int mesh_resume(struct macio_dev *mdev)1788{1789 struct mesh_state *ms = (struct mesh_state *)macio_get_drvdata(mdev);1790 unsigned long flags;1791 1792 if (ms->phase != sleeping)1793 return 0;1794 1795 set_mesh_power(ms, 1);1796 mesh_init(ms);1797 spin_lock_irqsave(ms->host->host_lock, flags);1798 mesh_start(ms);1799 spin_unlock_irqrestore(ms->host->host_lock, flags);1800 enable_irq(ms->meshintr);1801 scsi_unblock_requests(ms->host);1802 1803 return 0;1804}1805 1806#endif /* CONFIG_PM */1807 1808/*1809 * If we leave drives set for synchronous transfers (especially1810 * CDROMs), and reboot to MacOS, it gets confused, poor thing.1811 * So, on reboot we reset the SCSI bus.1812 */1813static int mesh_shutdown(struct macio_dev *mdev)1814{1815 struct mesh_state *ms = (struct mesh_state *)macio_get_drvdata(mdev);1816 volatile struct mesh_regs __iomem *mr;1817 unsigned long flags;1818 1819 printk(KERN_INFO "resetting MESH scsi bus(es)\n");1820 spin_lock_irqsave(ms->host->host_lock, flags);1821 mr = ms->mesh;1822 out_8(&mr->intr_mask, 0);1823 out_8(&mr->interrupt, INT_ERROR | INT_EXCEPTION | INT_CMDDONE);1824 out_8(&mr->bus_status1, BS1_RST);1825 mesh_flush_io(mr);1826 udelay(30);1827 out_8(&mr->bus_status1, 0);1828 spin_unlock_irqrestore(ms->host->host_lock, flags);1829 1830 return 0;1831}1832 1833static const struct scsi_host_template mesh_template = {1834 .proc_name = "mesh",1835 .name = "MESH",1836 .queuecommand = mesh_queue,1837 .eh_abort_handler = mesh_abort,1838 .eh_host_reset_handler = mesh_host_reset,1839 .can_queue = 20,1840 .this_id = 7,1841 .sg_tablesize = SG_ALL,1842 .cmd_per_lun = 2,1843 .max_segment_size = 65535,1844 .cmd_size = sizeof(struct mesh_cmd_priv),1845};1846 1847static int mesh_probe(struct macio_dev *mdev, const struct of_device_id *match)1848{1849 struct device_node *mesh = macio_get_of_node(mdev);1850 struct pci_dev* pdev = macio_get_pci_dev(mdev);1851 int tgt, minper;1852 const int *cfp;1853 struct mesh_state *ms;1854 struct Scsi_Host *mesh_host;1855 void *dma_cmd_space;1856 dma_addr_t dma_cmd_bus;1857 1858 switch (mdev->bus->chip->type) {1859 case macio_heathrow:1860 case macio_gatwick:1861 case macio_paddington:1862 use_active_neg = 0;1863 break;1864 default:1865 use_active_neg = SEQ_ACTIVE_NEG;1866 }1867 1868 if (macio_resource_count(mdev) != 2 || macio_irq_count(mdev) != 2) {1869 printk(KERN_ERR "mesh: expected 2 addrs and 2 intrs"1870 " (got %d,%d)\n", macio_resource_count(mdev),1871 macio_irq_count(mdev));1872 return -ENODEV;1873 }1874 1875 if (macio_request_resources(mdev, "mesh") != 0) {1876 printk(KERN_ERR "mesh: unable to request memory resources");1877 return -EBUSY;1878 }1879 mesh_host = scsi_host_alloc(&mesh_template, sizeof(struct mesh_state));1880 if (mesh_host == NULL) {1881 printk(KERN_ERR "mesh: couldn't register host");1882 goto out_release;1883 }1884 1885 mesh_host->base = macio_resource_start(mdev, 0);1886 mesh_host->irq = macio_irq(mdev, 0);1887 ms = (struct mesh_state *) mesh_host->hostdata;1888 macio_set_drvdata(mdev, ms);1889 ms->host = mesh_host;1890 ms->mdev = mdev;1891 ms->pdev = pdev;1892 1893 ms->mesh = ioremap(macio_resource_start(mdev, 0), 0x1000);1894 if (ms->mesh == NULL) {1895 printk(KERN_ERR "mesh: can't map registers\n");1896 goto out_free;1897 } 1898 ms->dma = ioremap(macio_resource_start(mdev, 1), 0x1000);1899 if (ms->dma == NULL) {1900 printk(KERN_ERR "mesh: can't map registers\n");1901 iounmap(ms->mesh);1902 goto out_free;1903 }1904 1905 ms->meshintr = macio_irq(mdev, 0);1906 ms->dmaintr = macio_irq(mdev, 1);1907 1908 /* Space for dma command list: +1 for stop command,1909 * +1 to allow for aligning.1910 */1911 ms->dma_cmd_size = (mesh_host->sg_tablesize + 2) * sizeof(struct dbdma_cmd);1912 1913 /* We use the PCI APIs for now until the generic one gets fixed1914 * enough or until we get some macio-specific versions1915 */1916 dma_cmd_space = dma_alloc_coherent(&macio_get_pci_dev(mdev)->dev,1917 ms->dma_cmd_size, &dma_cmd_bus,1918 GFP_KERNEL);1919 if (dma_cmd_space == NULL) {1920 printk(KERN_ERR "mesh: can't allocate DMA table\n");1921 goto out_unmap;1922 }1923 1924 ms->dma_cmds = (struct dbdma_cmd *) DBDMA_ALIGN(dma_cmd_space);1925 ms->dma_cmd_space = dma_cmd_space;1926 ms->dma_cmd_bus = dma_cmd_bus + ((unsigned long)ms->dma_cmds)1927 - (unsigned long)dma_cmd_space;1928 ms->current_req = NULL;1929 for (tgt = 0; tgt < 8; ++tgt) {1930 ms->tgts[tgt].sdtr_state = do_sdtr;1931 ms->tgts[tgt].sync_params = ASYNC_PARAMS;1932 ms->tgts[tgt].current_req = NULL;1933 }1934 1935 if ((cfp = of_get_property(mesh, "clock-frequency", NULL)))1936 ms->clk_freq = *cfp;1937 else {1938 printk(KERN_INFO "mesh: assuming 50MHz clock frequency\n");1939 ms->clk_freq = 50000000;1940 }1941 1942 /* The maximum sync rate is clock / 5; increase1943 * mesh_sync_period if necessary.1944 */1945 minper = 1000000000 / (ms->clk_freq / 5); /* ns */1946 if (mesh_sync_period < minper)1947 mesh_sync_period = minper;1948 1949 /* Power up the chip */1950 set_mesh_power(ms, 1);1951 1952 /* Set it up */1953 mesh_init(ms);1954 1955 /* Request interrupt */1956 if (request_irq(ms->meshintr, do_mesh_interrupt, 0, "MESH", ms)) {1957 printk(KERN_ERR "MESH: can't get irq %d\n", ms->meshintr);1958 goto out_shutdown;1959 }1960 1961 /* Add scsi host & scan */1962 if (scsi_add_host(mesh_host, &mdev->ofdev.dev))1963 goto out_release_irq;1964 scsi_scan_host(mesh_host);1965 1966 return 0;1967 1968 out_release_irq:1969 free_irq(ms->meshintr, ms);1970 out_shutdown:1971 /* shutdown & reset bus in case of error or macos can be confused1972 * at reboot if the bus was set to synchronous mode already1973 */1974 mesh_shutdown(mdev);1975 set_mesh_power(ms, 0);1976 dma_free_coherent(&macio_get_pci_dev(mdev)->dev, ms->dma_cmd_size,1977 ms->dma_cmd_space, ms->dma_cmd_bus);1978 out_unmap:1979 iounmap(ms->dma);1980 iounmap(ms->mesh);1981 out_free:1982 scsi_host_put(mesh_host);1983 out_release:1984 macio_release_resources(mdev);1985 1986 return -ENODEV;1987}1988 1989static void mesh_remove(struct macio_dev *mdev)1990{1991 struct mesh_state *ms = (struct mesh_state *)macio_get_drvdata(mdev);1992 struct Scsi_Host *mesh_host = ms->host;1993 1994 scsi_remove_host(mesh_host);1995 1996 free_irq(ms->meshintr, ms);1997 1998 /* Reset scsi bus */1999 mesh_shutdown(mdev);2000 2001 /* Shut down chip & termination */2002 set_mesh_power(ms, 0);2003 2004 /* Unmap registers & dma controller */2005 iounmap(ms->mesh);2006 iounmap(ms->dma);2007 2008 /* Free DMA commands memory */2009 dma_free_coherent(&macio_get_pci_dev(mdev)->dev, ms->dma_cmd_size,2010 ms->dma_cmd_space, ms->dma_cmd_bus);2011 2012 /* Release memory resources */2013 macio_release_resources(mdev);2014 2015 scsi_host_put(mesh_host);2016}2017 2018static struct of_device_id mesh_match[] = 2019{2020 {2021 .name = "mesh",2022 },2023 {2024 .type = "scsi",2025 .compatible = "chrp,mesh0"2026 },2027 {},2028};2029MODULE_DEVICE_TABLE (of, mesh_match);2030 2031static struct macio_driver mesh_driver = 2032{2033 .driver = {2034 .name = "mesh",2035 .owner = THIS_MODULE,2036 .of_match_table = mesh_match,2037 },2038 .probe = mesh_probe,2039 .remove = mesh_remove,2040 .shutdown = mesh_shutdown,2041#ifdef CONFIG_PM2042 .suspend = mesh_suspend,2043 .resume = mesh_resume,2044#endif2045};2046 2047 2048static int __init init_mesh(void)2049{2050 2051 /* Calculate sync rate from module parameters */2052 if (sync_rate > 10)2053 sync_rate = 10;2054 if (sync_rate > 0) {2055 printk(KERN_INFO "mesh: configured for synchronous %d MB/s\n", sync_rate);2056 mesh_sync_period = 1000 / sync_rate; /* ns */2057 mesh_sync_offset = 15;2058 } else2059 printk(KERN_INFO "mesh: configured for asynchronous\n");2060 2061 return macio_register_driver(&mesh_driver);2062}2063 2064static void __exit exit_mesh(void)2065{2066 return macio_unregister_driver(&mesh_driver);2067}2068 2069module_init(init_mesh);2070module_exit(exit_mesh);2071