linux/drivers/media/pci/bt8xx/bt878.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0-or-later
   2/*
   3 * bt878.c: part of the driver for the Pinnacle PCTV Sat DVB PCI card
   4 *
   5 * Copyright (C) 2002 Peter Hettkamp <peter.hettkamp@htp-tel.de>
   6 *
   7 * large parts based on the bttv driver
   8 * Copyright (C) 1996,97,98 Ralph  Metzler (rjkm@metzlerbros.de)
   9 *                        & Marcus Metzler (mocm@metzlerbros.de)
  10 * (c) 1999,2000 Gerd Knorr <kraxel@goldbach.in-berlin.de>
  11 */
  12
  13#include <linux/module.h>
  14#include <linux/kernel.h>
  15#include <linux/pci.h>
  16#include <linux/pgtable.h>
  17#include <asm/io.h>
  18#include <linux/ioport.h>
  19#include <asm/page.h>
  20#include <linux/types.h>
  21#include <linux/interrupt.h>
  22#include <linux/kmod.h>
  23#include <linux/vmalloc.h>
  24#include <linux/init.h>
  25
  26#include <media/dmxdev.h>
  27#include <media/dvbdev.h>
  28#include "bt878.h"
  29#include "dst_priv.h"
  30
  31
  32/**************************************/
  33/* Miscellaneous utility  definitions */
  34/**************************************/
  35
  36static unsigned int bt878_verbose = 1;
  37static unsigned int bt878_debug;
  38
  39module_param_named(verbose, bt878_verbose, int, 0444);
  40MODULE_PARM_DESC(verbose,
  41                 "verbose startup messages, default is 1 (yes)");
  42module_param_named(debug, bt878_debug, int, 0644);
  43MODULE_PARM_DESC(debug, "Turn on/off debugging, default is 0 (off).");
  44
  45int bt878_num;
  46struct bt878 bt878[BT878_MAX];
  47
  48EXPORT_SYMBOL(bt878_num);
  49EXPORT_SYMBOL(bt878);
  50
  51#define btwrite(dat,adr)    bmtwrite((dat), (bt->bt878_mem+(adr)))
  52#define btread(adr)         bmtread(bt->bt878_mem+(adr))
  53
  54#define btand(dat,adr)      btwrite((dat) & btread(adr), adr)
  55#define btor(dat,adr)       btwrite((dat) | btread(adr), adr)
  56#define btaor(dat,mask,adr) btwrite((dat) | ((mask) & btread(adr)), adr)
  57
  58#if defined(dprintk)
  59#undef dprintk
  60#endif
  61#define dprintk(fmt, arg...) \
  62        do { \
  63                if (bt878_debug) \
  64                        printk(KERN_DEBUG fmt, ##arg); \
  65        } while (0)
  66
  67static void bt878_mem_free(struct bt878 *bt)
  68{
  69        if (bt->buf_cpu) {
  70                dma_free_coherent(&bt->dev->dev, bt->buf_size, bt->buf_cpu,
  71                                  bt->buf_dma);
  72                bt->buf_cpu = NULL;
  73        }
  74
  75        if (bt->risc_cpu) {
  76                dma_free_coherent(&bt->dev->dev, bt->risc_size, bt->risc_cpu,
  77                                  bt->risc_dma);
  78                bt->risc_cpu = NULL;
  79        }
  80}
  81
  82static int bt878_mem_alloc(struct bt878 *bt)
  83{
  84        if (!bt->buf_cpu) {
  85                bt->buf_size = 128 * 1024;
  86
  87                bt->buf_cpu = dma_alloc_coherent(&bt->dev->dev, bt->buf_size,
  88                                                 &bt->buf_dma, GFP_KERNEL);
  89                if (!bt->buf_cpu)
  90                        return -ENOMEM;
  91        }
  92
  93        if (!bt->risc_cpu) {
  94                bt->risc_size = PAGE_SIZE;
  95                bt->risc_cpu = dma_alloc_coherent(&bt->dev->dev, bt->risc_size,
  96                                                  &bt->risc_dma, GFP_KERNEL);
  97                if (!bt->risc_cpu) {
  98                        bt878_mem_free(bt);
  99                        return -ENOMEM;
 100                }
 101        }
 102
 103        return 0;
 104}
 105
 106/* RISC instructions */
 107#define RISC_WRITE              (0x01 << 28)
 108#define RISC_JUMP               (0x07 << 28)
 109#define RISC_SYNC               (0x08 << 28)
 110
 111/* RISC bits */
 112#define RISC_WR_SOL             (1 << 27)
 113#define RISC_WR_EOL             (1 << 26)
 114#define RISC_IRQ                (1 << 24)
 115#define RISC_STATUS(status)     ((((~status) & 0x0F) << 20) | ((status & 0x0F) << 16))
 116#define RISC_SYNC_RESYNC        (1 << 15)
 117#define RISC_SYNC_FM1           0x06
 118#define RISC_SYNC_VRO           0x0C
 119
 120#define RISC_FLUSH()            bt->risc_pos = 0
 121#define RISC_INSTR(instr)       bt->risc_cpu[bt->risc_pos++] = cpu_to_le32(instr)
 122
 123static int bt878_make_risc(struct bt878 *bt)
 124{
 125        bt->block_bytes = bt->buf_size >> 4;
 126        bt->block_count = 1 << 4;
 127        bt->line_bytes = bt->block_bytes;
 128        bt->line_count = bt->block_count;
 129
 130        while (bt->line_bytes > 4095) {
 131                bt->line_bytes >>= 1;
 132                bt->line_count <<= 1;
 133        }
 134
 135        if (bt->line_count > 255) {
 136                printk(KERN_ERR "bt878: buffer size error!\n");
 137                return -EINVAL;
 138        }
 139        return 0;
 140}
 141
 142
 143static void bt878_risc_program(struct bt878 *bt, u32 op_sync_orin)
 144{
 145        u32 buf_pos = 0;
 146        u32 line;
 147
 148        RISC_FLUSH();
 149        RISC_INSTR(RISC_SYNC | RISC_SYNC_FM1 | op_sync_orin);
 150        RISC_INSTR(0);
 151
 152        dprintk("bt878: risc len lines %u, bytes per line %u\n",
 153                        bt->line_count, bt->line_bytes);
 154        for (line = 0; line < bt->line_count; line++) {
 155                // At the beginning of every block we issue an IRQ with previous (finished) block number set
 156                if (!(buf_pos % bt->block_bytes))
 157                        RISC_INSTR(RISC_WRITE | RISC_WR_SOL | RISC_WR_EOL |
 158                                   RISC_IRQ |
 159                                   RISC_STATUS(((buf_pos /
 160                                                 bt->block_bytes) +
 161                                                (bt->block_count -
 162                                                 1)) %
 163                                               bt->block_count) | bt->
 164                                   line_bytes);
 165                else
 166                        RISC_INSTR(RISC_WRITE | RISC_WR_SOL | RISC_WR_EOL |
 167                                   bt->line_bytes);
 168                RISC_INSTR(bt->buf_dma + buf_pos);
 169                buf_pos += bt->line_bytes;
 170        }
 171
 172        RISC_INSTR(RISC_SYNC | op_sync_orin | RISC_SYNC_VRO);
 173        RISC_INSTR(0);
 174
 175        RISC_INSTR(RISC_JUMP);
 176        RISC_INSTR(bt->risc_dma);
 177
 178        btwrite((bt->line_count << 16) | bt->line_bytes, BT878_APACK_LEN);
 179}
 180
 181/*****************************/
 182/* Start/Stop grabbing funcs */
 183/*****************************/
 184
 185void bt878_start(struct bt878 *bt, u32 controlreg, u32 op_sync_orin,
 186                u32 irq_err_ignore)
 187{
 188        u32 int_mask;
 189
 190        dprintk("bt878 debug: bt878_start (ctl=%8.8x)\n", controlreg);
 191        /* complete the writing of the risc dma program now we have
 192         * the card specifics
 193         */
 194        bt878_risc_program(bt, op_sync_orin);
 195        controlreg &= ~0x1f;
 196        controlreg |= 0x1b;
 197
 198        btwrite(bt->risc_dma, BT878_ARISC_START);
 199
 200        /* original int mask had :
 201         *    6    2    8    4    0
 202         * 1111 1111 1000 0000 0000
 203         * SCERR|OCERR|PABORT|RIPERR|FDSR|FTRGT|FBUS|RISCI
 204         * Hacked for DST to:
 205         * SCERR | OCERR | FDSR | FTRGT | FBUS | RISCI
 206         */
 207        int_mask = BT878_ASCERR | BT878_AOCERR | BT878_APABORT |
 208                BT878_ARIPERR | BT878_APPERR | BT878_AFDSR | BT878_AFTRGT |
 209                BT878_AFBUS | BT878_ARISCI;
 210
 211
 212        /* ignore pesky bits */
 213        int_mask &= ~irq_err_ignore;
 214
 215        btwrite(int_mask, BT878_AINT_MASK);
 216        btwrite(controlreg, BT878_AGPIO_DMA_CTL);
 217}
 218
 219void bt878_stop(struct bt878 *bt)
 220{
 221        u32 stat;
 222        int i = 0;
 223
 224        dprintk("bt878 debug: bt878_stop\n");
 225
 226        btwrite(0, BT878_AINT_MASK);
 227        btand(~0x13, BT878_AGPIO_DMA_CTL);
 228
 229        do {
 230                stat = btread(BT878_AINT_STAT);
 231                if (!(stat & BT878_ARISC_EN))
 232                        break;
 233                i++;
 234        } while (i < 500);
 235
 236        dprintk("bt878(%d) debug: bt878_stop, i=%d, stat=0x%8.8x\n",
 237                bt->nr, i, stat);
 238}
 239
 240EXPORT_SYMBOL(bt878_start);
 241EXPORT_SYMBOL(bt878_stop);
 242
 243/*****************************/
 244/* Interrupt service routine */
 245/*****************************/
 246
 247static irqreturn_t bt878_irq(int irq, void *dev_id)
 248{
 249        u32 stat, astat, mask;
 250        int count;
 251        struct bt878 *bt;
 252
 253        bt = (struct bt878 *) dev_id;
 254
 255        count = 0;
 256        while (1) {
 257                stat = btread(BT878_AINT_STAT);
 258                mask = btread(BT878_AINT_MASK);
 259                if (!(astat = (stat & mask)))
 260                        return IRQ_NONE;        /* this interrupt is not for me */
 261/*              dprintk("bt878(%d) debug: irq count %d, stat 0x%8.8x, mask 0x%8.8x\n",bt->nr,count,stat,mask); */
 262                btwrite(astat, BT878_AINT_STAT);        /* try to clear interrupt condition */
 263
 264
 265                if (astat & (BT878_ASCERR | BT878_AOCERR)) {
 266                        if (bt878_verbose) {
 267                                printk(KERN_INFO
 268                                       "bt878(%d): irq%s%s risc_pc=%08x\n",
 269                                       bt->nr,
 270                                       (astat & BT878_ASCERR) ? " SCERR" :
 271                                       "",
 272                                       (astat & BT878_AOCERR) ? " OCERR" :
 273                                       "", btread(BT878_ARISC_PC));
 274                        }
 275                }
 276                if (astat & (BT878_APABORT | BT878_ARIPERR | BT878_APPERR)) {
 277                        if (bt878_verbose) {
 278                                printk(KERN_INFO
 279                                     "bt878(%d): irq%s%s%s risc_pc=%08x\n",
 280                                     bt->nr,
 281                                     (astat & BT878_APABORT) ? " PABORT" :
 282                                     "",
 283                                     (astat & BT878_ARIPERR) ? " RIPERR" :
 284                                     "",
 285                                     (astat & BT878_APPERR) ? " PPERR" :
 286                                     "", btread(BT878_ARISC_PC));
 287                        }
 288                }
 289                if (astat & (BT878_AFDSR | BT878_AFTRGT | BT878_AFBUS)) {
 290                        if (bt878_verbose) {
 291                                printk(KERN_INFO
 292                                     "bt878(%d): irq%s%s%s risc_pc=%08x\n",
 293                                     bt->nr,
 294                                     (astat & BT878_AFDSR) ? " FDSR" : "",
 295                                     (astat & BT878_AFTRGT) ? " FTRGT" :
 296                                     "",
 297                                     (astat & BT878_AFBUS) ? " FBUS" : "",
 298                                     btread(BT878_ARISC_PC));
 299                        }
 300                }
 301                if (astat & BT878_ARISCI) {
 302                        bt->finished_block = (stat & BT878_ARISCS) >> 28;
 303                        if (bt->tasklet.callback)
 304                                tasklet_schedule(&bt->tasklet);
 305                        break;
 306                }
 307                count++;
 308                if (count > 20) {
 309                        btwrite(0, BT878_AINT_MASK);
 310                        printk(KERN_ERR
 311                               "bt878(%d): IRQ lockup, cleared int mask\n",
 312                               bt->nr);
 313                        break;
 314                }
 315        }
 316        return IRQ_HANDLED;
 317}
 318
 319int
 320bt878_device_control(struct bt878 *bt, unsigned int cmd, union dst_gpio_packet *mp)
 321{
 322        int retval;
 323
 324        retval = 0;
 325        if (mutex_lock_interruptible(&bt->gpio_lock))
 326                return -ERESTARTSYS;
 327        /* special gpio signal */
 328        switch (cmd) {
 329            case DST_IG_ENABLE:
 330                // dprintk("dvb_bt8xx: dst enable mask 0x%02x enb 0x%02x \n", mp->dstg.enb.mask, mp->dstg.enb.enable);
 331                retval = bttv_gpio_enable(bt->bttv_nr,
 332                                mp->enb.mask,
 333                                mp->enb.enable);
 334                break;
 335            case DST_IG_WRITE:
 336                // dprintk("dvb_bt8xx: dst write gpio mask 0x%02x out 0x%02x\n", mp->dstg.outp.mask, mp->dstg.outp.highvals);
 337                retval = bttv_write_gpio(bt->bttv_nr,
 338                                mp->outp.mask,
 339                                mp->outp.highvals);
 340
 341                break;
 342            case DST_IG_READ:
 343                /* read */
 344                retval =  bttv_read_gpio(bt->bttv_nr, &mp->rd.value);
 345                // dprintk("dvb_bt8xx: dst read gpio 0x%02x\n", (unsigned)mp->dstg.rd.value);
 346                break;
 347            case DST_IG_TS:
 348                /* Set packet size */
 349                bt->TS_Size = mp->psize;
 350                break;
 351
 352            default:
 353                retval = -EINVAL;
 354                break;
 355        }
 356        mutex_unlock(&bt->gpio_lock);
 357        return retval;
 358}
 359
 360EXPORT_SYMBOL(bt878_device_control);
 361
 362#define BROOKTREE_878_DEVICE(vend, dev, name) \
 363        { \
 364                .vendor = PCI_VENDOR_ID_BROOKTREE, \
 365                .device = PCI_DEVICE_ID_BROOKTREE_878, \
 366                .subvendor = (vend), .subdevice = (dev), \
 367                .driver_data = (unsigned long) name \
 368        }
 369
 370static const struct pci_device_id bt878_pci_tbl[] = {
 371        BROOKTREE_878_DEVICE(0x0071, 0x0101, "Nebula Electronics DigiTV"),
 372        BROOKTREE_878_DEVICE(0x1461, 0x0761, "AverMedia AverTV DVB-T 761"),
 373        BROOKTREE_878_DEVICE(0x11bd, 0x001c, "Pinnacle PCTV Sat"),
 374        BROOKTREE_878_DEVICE(0x11bd, 0x0026, "Pinnacle PCTV SAT CI"),
 375        BROOKTREE_878_DEVICE(0x1822, 0x0001, "Twinhan VisionPlus DVB"),
 376        BROOKTREE_878_DEVICE(0x270f, 0xfc00,
 377                                "ChainTech digitop DST-1000 DVB-S"),
 378        BROOKTREE_878_DEVICE(0x1461, 0x0771, "AVermedia AverTV DVB-T 771"),
 379        BROOKTREE_878_DEVICE(0x18ac, 0xdb10, "DViCO FusionHDTV DVB-T Lite"),
 380        BROOKTREE_878_DEVICE(0x18ac, 0xdb11, "Ultraview DVB-T Lite"),
 381        BROOKTREE_878_DEVICE(0x18ac, 0xd500, "DViCO FusionHDTV 5 Lite"),
 382        BROOKTREE_878_DEVICE(0x7063, 0x2000, "pcHDTV HD-2000 TV"),
 383        BROOKTREE_878_DEVICE(0x1822, 0x0026, "DNTV Live! Mini"),
 384        { }
 385};
 386
 387MODULE_DEVICE_TABLE(pci, bt878_pci_tbl);
 388
 389static const char * card_name(const struct pci_device_id *id)
 390{
 391        return id->driver_data ? (const char *)id->driver_data : "Unknown";
 392}
 393
 394/***********************/
 395/* PCI device handling */
 396/***********************/
 397
 398static int bt878_probe(struct pci_dev *dev, const struct pci_device_id *pci_id)
 399{
 400        int result = 0;
 401        unsigned char lat;
 402        struct bt878 *bt;
 403        unsigned int cardid;
 404
 405        printk(KERN_INFO "bt878: Bt878 AUDIO function found (%d).\n",
 406               bt878_num);
 407        if (bt878_num >= BT878_MAX) {
 408                printk(KERN_ERR "bt878: Too many devices inserted\n");
 409                return -ENOMEM;
 410        }
 411        if (pci_enable_device(dev))
 412                return -EIO;
 413
 414        cardid = dev->subsystem_device << 16;
 415        cardid |= dev->subsystem_vendor;
 416
 417        printk(KERN_INFO "%s: card id=[0x%x],[ %s ] has DVB functions.\n",
 418                                __func__, cardid, card_name(pci_id));
 419
 420        bt = &bt878[bt878_num];
 421        bt->dev = dev;
 422        bt->nr = bt878_num;
 423        bt->shutdown = 0;
 424
 425        bt->id = dev->device;
 426        bt->irq = dev->irq;
 427        bt->bt878_adr = pci_resource_start(dev, 0);
 428        if (!request_mem_region(pci_resource_start(dev, 0),
 429                                pci_resource_len(dev, 0), "bt878")) {
 430                result = -EBUSY;
 431                goto fail0;
 432        }
 433
 434        bt->revision = dev->revision;
 435        pci_read_config_byte(dev, PCI_LATENCY_TIMER, &lat);
 436
 437
 438        printk(KERN_INFO "bt878(%d): Bt%x (rev %d) at %02x:%02x.%x, ",
 439               bt878_num, bt->id, bt->revision, dev->bus->number,
 440               PCI_SLOT(dev->devfn), PCI_FUNC(dev->devfn));
 441        printk("irq: %d, latency: %d, memory: 0x%lx\n",
 442               bt->irq, lat, bt->bt878_adr);
 443
 444#ifdef __sparc__
 445        bt->bt878_mem = (unsigned char *) bt->bt878_adr;
 446#else
 447        bt->bt878_mem = ioremap(bt->bt878_adr, 0x1000);
 448#endif
 449
 450        /* clear interrupt mask */
 451        btwrite(0, BT848_INT_MASK);
 452
 453        result = request_irq(bt->irq, bt878_irq,
 454                             IRQF_SHARED, "bt878", (void *) bt);
 455        if (result == -EINVAL) {
 456                printk(KERN_ERR "bt878(%d): Bad irq number or handler\n",
 457                       bt878_num);
 458                goto fail1;
 459        }
 460        if (result == -EBUSY) {
 461                printk(KERN_ERR
 462                       "bt878(%d): IRQ %d busy, change your PnP config in BIOS\n",
 463                       bt878_num, bt->irq);
 464                goto fail1;
 465        }
 466        if (result < 0)
 467                goto fail1;
 468
 469        pci_set_master(dev);
 470        pci_set_drvdata(dev, bt);
 471
 472        if ((result = bt878_mem_alloc(bt))) {
 473                printk(KERN_ERR "bt878: failed to allocate memory!\n");
 474                goto fail2;
 475        }
 476
 477        bt878_make_risc(bt);
 478        btwrite(0, BT878_AINT_MASK);
 479        bt878_num++;
 480
 481        if (!bt->tasklet.func)
 482                tasklet_disable(&bt->tasklet);
 483
 484        return 0;
 485
 486      fail2:
 487        free_irq(bt->irq, bt);
 488      fail1:
 489        release_mem_region(pci_resource_start(bt->dev, 0),
 490                           pci_resource_len(bt->dev, 0));
 491      fail0:
 492        pci_disable_device(dev);
 493        return result;
 494}
 495
 496static void bt878_remove(struct pci_dev *pci_dev)
 497{
 498        u8 command;
 499        struct bt878 *bt = pci_get_drvdata(pci_dev);
 500
 501        if (bt878_verbose)
 502                printk(KERN_INFO "bt878(%d): unloading\n", bt->nr);
 503
 504        /* turn off all capturing, DMA and IRQs */
 505        btand(~0x13, BT878_AGPIO_DMA_CTL);
 506
 507        /* first disable interrupts before unmapping the memory! */
 508        btwrite(0, BT878_AINT_MASK);
 509        btwrite(~0U, BT878_AINT_STAT);
 510
 511        /* disable PCI bus-mastering */
 512        pci_read_config_byte(bt->dev, PCI_COMMAND, &command);
 513        /* Should this be &=~ ?? */
 514        command &= ~PCI_COMMAND_MASTER;
 515        pci_write_config_byte(bt->dev, PCI_COMMAND, command);
 516
 517        free_irq(bt->irq, bt);
 518        printk(KERN_DEBUG "bt878_mem: 0x%p.\n", bt->bt878_mem);
 519        if (bt->bt878_mem)
 520                iounmap(bt->bt878_mem);
 521
 522        release_mem_region(pci_resource_start(bt->dev, 0),
 523                           pci_resource_len(bt->dev, 0));
 524        /* wake up any waiting processes
 525           because shutdown flag is set, no new processes (in this queue)
 526           are expected
 527         */
 528        bt->shutdown = 1;
 529        bt878_mem_free(bt);
 530
 531        pci_disable_device(pci_dev);
 532        return;
 533}
 534
 535static struct pci_driver bt878_pci_driver = {
 536      .name     = "bt878",
 537      .id_table = bt878_pci_tbl,
 538      .probe    = bt878_probe,
 539      .remove   = bt878_remove,
 540};
 541
 542/*******************************/
 543/* Module management functions */
 544/*******************************/
 545
 546static int __init bt878_init_module(void)
 547{
 548        bt878_num = 0;
 549
 550        printk(KERN_INFO "bt878: AUDIO driver version %d.%d.%d loaded\n",
 551               (BT878_VERSION_CODE >> 16) & 0xff,
 552               (BT878_VERSION_CODE >> 8) & 0xff,
 553               BT878_VERSION_CODE & 0xff);
 554
 555        return pci_register_driver(&bt878_pci_driver);
 556}
 557
 558static void __exit bt878_cleanup_module(void)
 559{
 560        pci_unregister_driver(&bt878_pci_driver);
 561}
 562
 563module_init(bt878_init_module);
 564module_exit(bt878_cleanup_module);
 565
 566MODULE_LICENSE("GPL");
 567