linux/drivers/media/dvb/mantis/mantis_hif.c
<<
>>
Prefs
   1/*
   2        Mantis PCI bridge driver
   3
   4        Copyright (C) Manu Abraham (abraham.manu@gmail.com)
   5
   6        This program is free software; you can redistribute it and/or modify
   7        it under the terms of the GNU General Public License as published by
   8        the Free Software Foundation; either version 2 of the License, or
   9        (at your option) any later version.
  10
  11        This program is distributed in the hope that it will be useful,
  12        but WITHOUT ANY WARRANTY; without even the implied warranty of
  13        MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14        GNU General Public License for more details.
  15
  16        You should have received a copy of the GNU General Public License
  17        along with this program; if not, write to the Free Software
  18        Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  19*/
  20
  21#include <linux/kernel.h>
  22#include <linux/signal.h>
  23#include <linux/sched.h>
  24
  25#include <linux/interrupt.h>
  26
  27#include "dmxdev.h"
  28#include "dvbdev.h"
  29#include "dvb_demux.h"
  30#include "dvb_frontend.h"
  31#include "dvb_net.h"
  32
  33#include "mantis_common.h"
  34
  35#include "mantis_hif.h"
  36#include "mantis_link.h" /* temporary due to physical layer stuff */
  37
  38#include "mantis_reg.h"
  39
  40
  41static int mantis_hif_sbuf_opdone_wait(struct mantis_ca *ca)
  42{
  43        struct mantis_pci *mantis = ca->ca_priv;
  44        int rc = 0;
  45
  46        if (wait_event_timeout(ca->hif_opdone_wq,
  47                               ca->hif_event & MANTIS_SBUF_OPDONE,
  48                               msecs_to_jiffies(500)) == -ERESTARTSYS) {
  49
  50                dprintk(MANTIS_ERROR, 1, "Adapter(%d) Slot(0): Smart buffer operation timeout !", mantis->num);
  51                rc = -EREMOTEIO;
  52        }
  53        dprintk(MANTIS_DEBUG, 1, "Smart Buffer Operation complete");
  54        ca->hif_event &= ~MANTIS_SBUF_OPDONE;
  55        return rc;
  56}
  57
  58static int mantis_hif_write_wait(struct mantis_ca *ca)
  59{
  60        struct mantis_pci *mantis = ca->ca_priv;
  61        u32 opdone = 0, timeout = 0;
  62        int rc = 0;
  63
  64        if (wait_event_timeout(ca->hif_write_wq,
  65                               mantis->gpif_status & MANTIS_GPIF_WRACK,
  66                               msecs_to_jiffies(500)) == -ERESTARTSYS) {
  67
  68                dprintk(MANTIS_ERROR, 1, "Adapter(%d) Slot(0): Write ACK timed out !", mantis->num);
  69                rc = -EREMOTEIO;
  70        }
  71        dprintk(MANTIS_DEBUG, 1, "Write Acknowledged");
  72        mantis->gpif_status &= ~MANTIS_GPIF_WRACK;
  73        while (!opdone) {
  74                opdone = (mmread(MANTIS_GPIF_STATUS) & MANTIS_SBUF_OPDONE);
  75                udelay(500);
  76                timeout++;
  77                if (timeout > 100) {
  78                        dprintk(MANTIS_ERROR, 1, "Adater(%d) Slot(0): Write operation timed out!", mantis->num);
  79                        rc = -ETIMEDOUT;
  80                        break;
  81                }
  82        }
  83        dprintk(MANTIS_DEBUG, 1, "HIF Write success");
  84        return rc;
  85}
  86
  87
  88int mantis_hif_read_mem(struct mantis_ca *ca, u32 addr)
  89{
  90        struct mantis_pci *mantis = ca->ca_priv;
  91        u32 hif_addr = 0, data, count = 4;
  92
  93        dprintk(MANTIS_DEBUG, 1, "Adapter(%d) Slot(0): Request HIF Mem Read", mantis->num);
  94        mutex_lock(&ca->ca_lock);
  95        hif_addr &= ~MANTIS_GPIF_PCMCIAREG;
  96        hif_addr &= ~MANTIS_GPIF_PCMCIAIOM;
  97        hif_addr |=  MANTIS_HIF_STATUS;
  98        hif_addr |=  addr;
  99
 100        mmwrite(hif_addr, MANTIS_GPIF_BRADDR);
 101        mmwrite(count, MANTIS_GPIF_BRBYTES);
 102        udelay(20);
 103        mmwrite(hif_addr | MANTIS_GPIF_HIFRDWRN, MANTIS_GPIF_ADDR);
 104
 105        if (mantis_hif_sbuf_opdone_wait(ca) != 0) {
 106                dprintk(MANTIS_ERROR, 1, "Adapter(%d) Slot(0): GPIF Smart Buffer operation failed", mantis->num);
 107                mutex_unlock(&ca->ca_lock);
 108                return -EREMOTEIO;
 109        }
 110        data = mmread(MANTIS_GPIF_DIN);
 111        mutex_unlock(&ca->ca_lock);
 112        dprintk(MANTIS_DEBUG, 1, "Mem Read: 0x%02x", data);
 113        return (data >> 24) & 0xff;
 114}
 115
 116int mantis_hif_write_mem(struct mantis_ca *ca, u32 addr, u8 data)
 117{
 118        struct mantis_slot *slot = ca->slot;
 119        struct mantis_pci *mantis = ca->ca_priv;
 120        u32 hif_addr = 0;
 121
 122        dprintk(MANTIS_DEBUG, 1, "Adapter(%d) Slot(0): Request HIF Mem Write", mantis->num);
 123        mutex_lock(&ca->ca_lock);
 124        hif_addr &= ~MANTIS_GPIF_HIFRDWRN;
 125        hif_addr &= ~MANTIS_GPIF_PCMCIAREG;
 126        hif_addr &= ~MANTIS_GPIF_PCMCIAIOM;
 127        hif_addr |=  MANTIS_HIF_STATUS;
 128        hif_addr |=  addr;
 129
 130        mmwrite(slot->slave_cfg, MANTIS_GPIF_CFGSLA); /* Slot0 alone for now */
 131        mmwrite(hif_addr, MANTIS_GPIF_ADDR);
 132        mmwrite(data, MANTIS_GPIF_DOUT);
 133
 134        if (mantis_hif_write_wait(ca) != 0) {
 135                dprintk(MANTIS_ERROR, 1, "Adapter(%d) Slot(0): HIF Smart Buffer operation failed", mantis->num);
 136                mutex_unlock(&ca->ca_lock);
 137                return -EREMOTEIO;
 138        }
 139        dprintk(MANTIS_DEBUG, 1, "Mem Write: (0x%02x to 0x%02x)", data, addr);
 140        mutex_unlock(&ca->ca_lock);
 141
 142        return 0;
 143}
 144
 145int mantis_hif_read_iom(struct mantis_ca *ca, u32 addr)
 146{
 147        struct mantis_pci *mantis = ca->ca_priv;
 148        u32 data, hif_addr = 0;
 149
 150        dprintk(MANTIS_DEBUG, 1, "Adapter(%d) Slot(0): Request HIF I/O Read", mantis->num);
 151        mutex_lock(&ca->ca_lock);
 152        hif_addr &= ~MANTIS_GPIF_PCMCIAREG;
 153        hif_addr |=  MANTIS_GPIF_PCMCIAIOM;
 154        hif_addr |=  MANTIS_HIF_STATUS;
 155        hif_addr |=  addr;
 156
 157        mmwrite(hif_addr, MANTIS_GPIF_BRADDR);
 158        mmwrite(1, MANTIS_GPIF_BRBYTES);
 159        udelay(20);
 160        mmwrite(hif_addr | MANTIS_GPIF_HIFRDWRN, MANTIS_GPIF_ADDR);
 161
 162        if (mantis_hif_sbuf_opdone_wait(ca) != 0) {
 163                dprintk(MANTIS_ERROR, 1, "Adapter(%d) Slot(0): HIF Smart Buffer operation failed", mantis->num);
 164                mutex_unlock(&ca->ca_lock);
 165                return -EREMOTEIO;
 166        }
 167        data = mmread(MANTIS_GPIF_DIN);
 168        dprintk(MANTIS_DEBUG, 1, "I/O Read: 0x%02x", data);
 169        udelay(50);
 170        mutex_unlock(&ca->ca_lock);
 171
 172        return (u8) data;
 173}
 174
 175int mantis_hif_write_iom(struct mantis_ca *ca, u32 addr, u8 data)
 176{
 177        struct mantis_pci *mantis = ca->ca_priv;
 178        u32 hif_addr = 0;
 179
 180        dprintk(MANTIS_DEBUG, 1, "Adapter(%d) Slot(0): Request HIF I/O Write", mantis->num);
 181        mutex_lock(&ca->ca_lock);
 182        hif_addr &= ~MANTIS_GPIF_PCMCIAREG;
 183        hif_addr &= ~MANTIS_GPIF_HIFRDWRN;
 184        hif_addr |=  MANTIS_GPIF_PCMCIAIOM;
 185        hif_addr |=  MANTIS_HIF_STATUS;
 186        hif_addr |=  addr;
 187
 188        mmwrite(hif_addr, MANTIS_GPIF_ADDR);
 189        mmwrite(data, MANTIS_GPIF_DOUT);
 190
 191        if (mantis_hif_write_wait(ca) != 0) {
 192                dprintk(MANTIS_ERROR, 1, "Adapter(%d) Slot(0): HIF Smart Buffer operation failed", mantis->num);
 193                mutex_unlock(&ca->ca_lock);
 194                return -EREMOTEIO;
 195        }
 196        dprintk(MANTIS_DEBUG, 1, "I/O Write: (0x%02x to 0x%02x)", data, addr);
 197        mutex_unlock(&ca->ca_lock);
 198        udelay(50);
 199
 200        return 0;
 201}
 202
 203int mantis_hif_init(struct mantis_ca *ca)
 204{
 205        struct mantis_slot *slot = ca->slot;
 206        struct mantis_pci *mantis = ca->ca_priv;
 207        u32 irqcfg;
 208
 209        slot[0].slave_cfg = 0x70773028;
 210        dprintk(MANTIS_ERROR, 1, "Adapter(%d) Initializing Mantis Host Interface", mantis->num);
 211
 212        mutex_lock(&ca->ca_lock);
 213        irqcfg = mmread(MANTIS_GPIF_IRQCFG);
 214        irqcfg = MANTIS_MASK_BRRDY      |
 215                 MANTIS_MASK_WRACK      |
 216                 MANTIS_MASK_EXTIRQ     |
 217                 MANTIS_MASK_WSTO       |
 218                 MANTIS_MASK_OTHERR     |
 219                 MANTIS_MASK_OVFLW;
 220
 221        mmwrite(irqcfg, MANTIS_GPIF_IRQCFG);
 222        mutex_unlock(&ca->ca_lock);
 223
 224        return 0;
 225}
 226
 227void mantis_hif_exit(struct mantis_ca *ca)
 228{
 229        struct mantis_pci *mantis = ca->ca_priv;
 230        u32 irqcfg;
 231
 232        dprintk(MANTIS_ERROR, 1, "Adapter(%d) Exiting Mantis Host Interface", mantis->num);
 233        mutex_lock(&ca->ca_lock);
 234        irqcfg = mmread(MANTIS_GPIF_IRQCFG);
 235        irqcfg &= ~MANTIS_MASK_BRRDY;
 236        mmwrite(irqcfg, MANTIS_GPIF_IRQCFG);
 237        mutex_unlock(&ca->ca_lock);
 238}
 239