linux/drivers/media/pci/ttpci/av7110_av.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0-or-later
   2/*
   3 * av7110_av.c: audio and video MPEG decoder stuff
   4 *
   5 * Copyright (C) 1999-2002 Ralph  Metzler
   6 *                       & Marcus Metzler for convergence integrated media GmbH
   7 *
   8 * originally based on code by:
   9 * Copyright (C) 1998,1999 Christian Theiss <mistert@rz.fh-augsburg.de>
  10 *
  11 * the project's page is at https://linuxtv.org
  12 */
  13
  14#include <linux/types.h>
  15#include <linux/kernel.h>
  16#include <linux/string.h>
  17#include <linux/delay.h>
  18#include <linux/fs.h>
  19
  20#include "av7110.h"
  21#include "av7110_hw.h"
  22#include "av7110_av.h"
  23#include "av7110_ipack.h"
  24
  25/* MPEG-2 (ISO 13818 / H.222.0) stream types */
  26#define PROG_STREAM_MAP  0xBC
  27#define PRIVATE_STREAM1  0xBD
  28#define PADDING_STREAM   0xBE
  29#define PRIVATE_STREAM2  0xBF
  30#define AUDIO_STREAM_S   0xC0
  31#define AUDIO_STREAM_E   0xDF
  32#define VIDEO_STREAM_S   0xE0
  33#define VIDEO_STREAM_E   0xEF
  34#define ECM_STREAM       0xF0
  35#define EMM_STREAM       0xF1
  36#define DSM_CC_STREAM    0xF2
  37#define ISO13522_STREAM  0xF3
  38#define PROG_STREAM_DIR  0xFF
  39
  40#define PTS_DTS_FLAGS    0xC0
  41
  42//pts_dts flags
  43#define PTS_ONLY         0x80
  44#define PTS_DTS          0xC0
  45#define TS_SIZE          188
  46#define TRANS_ERROR      0x80
  47#define PAY_START        0x40
  48#define TRANS_PRIO       0x20
  49#define PID_MASK_HI      0x1F
  50//flags
  51#define TRANS_SCRMBL1    0x80
  52#define TRANS_SCRMBL2    0x40
  53#define ADAPT_FIELD      0x20
  54#define PAYLOAD          0x10
  55#define COUNT_MASK       0x0F
  56
  57// adaptation flags
  58#define DISCON_IND       0x80
  59#define RAND_ACC_IND     0x40
  60#define ES_PRI_IND       0x20
  61#define PCR_FLAG         0x10
  62#define OPCR_FLAG        0x08
  63#define SPLICE_FLAG      0x04
  64#define TRANS_PRIV       0x02
  65#define ADAP_EXT_FLAG    0x01
  66
  67// adaptation extension flags
  68#define LTW_FLAG         0x80
  69#define PIECE_RATE       0x40
  70#define SEAM_SPLICE      0x20
  71
  72
  73static void p_to_t(u8 const *buf, long int length, u16 pid,
  74                   u8 *counter, struct dvb_demux_feed *feed);
  75static int write_ts_to_decoder(struct av7110 *av7110, int type, const u8 *buf, size_t len);
  76
  77
  78int av7110_record_cb(struct dvb_filter_pes2ts *p2t, u8 *buf, size_t len)
  79{
  80        struct dvb_demux_feed *dvbdmxfeed = (struct dvb_demux_feed *) p2t->priv;
  81
  82        if (!(dvbdmxfeed->ts_type & TS_PACKET))
  83                return 0;
  84        if (buf[3] == 0xe0)      // video PES do not have a length in TS
  85                buf[4] = buf[5] = 0;
  86        if (dvbdmxfeed->ts_type & TS_PAYLOAD_ONLY)
  87                return dvbdmxfeed->cb.ts(buf, len, NULL, 0,
  88                                         &dvbdmxfeed->feed.ts, NULL);
  89        else
  90                return dvb_filter_pes2ts(p2t, buf, len, 1);
  91}
  92
  93static int dvb_filter_pes2ts_cb(void *priv, unsigned char *data)
  94{
  95        struct dvb_demux_feed *dvbdmxfeed = (struct dvb_demux_feed *) priv;
  96
  97        dvbdmxfeed->cb.ts(data, 188, NULL, 0,
  98                          &dvbdmxfeed->feed.ts, NULL);
  99        return 0;
 100}
 101
 102int av7110_av_start_record(struct av7110 *av7110, int av,
 103                           struct dvb_demux_feed *dvbdmxfeed)
 104{
 105        int ret = 0;
 106        struct dvb_demux *dvbdmx = dvbdmxfeed->demux;
 107
 108        dprintk(2, "av7110:%p, , dvb_demux_feed:%p\n", av7110, dvbdmxfeed);
 109
 110        if (av7110->playing || (av7110->rec_mode & av))
 111                return -EBUSY;
 112        av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Stop, 0);
 113        dvbdmx->recording = 1;
 114        av7110->rec_mode |= av;
 115
 116        switch (av7110->rec_mode) {
 117        case RP_AUDIO:
 118                dvb_filter_pes2ts_init(&av7110->p2t[0],
 119                                       dvbdmx->pesfilter[0]->pid,
 120                                       dvb_filter_pes2ts_cb,
 121                                       (void *) dvbdmx->pesfilter[0]);
 122                ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Record, 2, AudioPES, 0);
 123                break;
 124
 125        case RP_VIDEO:
 126                dvb_filter_pes2ts_init(&av7110->p2t[1],
 127                                       dvbdmx->pesfilter[1]->pid,
 128                                       dvb_filter_pes2ts_cb,
 129                                       (void *) dvbdmx->pesfilter[1]);
 130                ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Record, 2, VideoPES, 0);
 131                break;
 132
 133        case RP_AV:
 134                dvb_filter_pes2ts_init(&av7110->p2t[0],
 135                                       dvbdmx->pesfilter[0]->pid,
 136                                       dvb_filter_pes2ts_cb,
 137                                       (void *) dvbdmx->pesfilter[0]);
 138                dvb_filter_pes2ts_init(&av7110->p2t[1],
 139                                       dvbdmx->pesfilter[1]->pid,
 140                                       dvb_filter_pes2ts_cb,
 141                                       (void *) dvbdmx->pesfilter[1]);
 142                ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Record, 2, AV_PES, 0);
 143                break;
 144        }
 145        return ret;
 146}
 147
 148int av7110_av_start_play(struct av7110 *av7110, int av)
 149{
 150        int ret = 0;
 151        dprintk(2, "av7110:%p, \n", av7110);
 152
 153        if (av7110->rec_mode)
 154                return -EBUSY;
 155        if (av7110->playing & av)
 156                return -EBUSY;
 157
 158        av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Stop, 0);
 159
 160        if (av7110->playing == RP_NONE) {
 161                av7110_ipack_reset(&av7110->ipack[0]);
 162                av7110_ipack_reset(&av7110->ipack[1]);
 163        }
 164
 165        av7110->playing |= av;
 166        switch (av7110->playing) {
 167        case RP_AUDIO:
 168                ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Play, 2, AudioPES, 0);
 169                break;
 170        case RP_VIDEO:
 171                ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Play, 2, VideoPES, 0);
 172                av7110->sinfo = 0;
 173                break;
 174        case RP_AV:
 175                av7110->sinfo = 0;
 176                ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Play, 2, AV_PES, 0);
 177                break;
 178        }
 179        return ret;
 180}
 181
 182int av7110_av_stop(struct av7110 *av7110, int av)
 183{
 184        int ret = 0;
 185        dprintk(2, "av7110:%p, \n", av7110);
 186
 187        if (!(av7110->playing & av) && !(av7110->rec_mode & av))
 188                return 0;
 189        av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Stop, 0);
 190        if (av7110->playing) {
 191                av7110->playing &= ~av;
 192                switch (av7110->playing) {
 193                case RP_AUDIO:
 194                        ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Play, 2, AudioPES, 0);
 195                        break;
 196                case RP_VIDEO:
 197                        ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Play, 2, VideoPES, 0);
 198                        break;
 199                case RP_NONE:
 200                        ret = av7110_set_vidmode(av7110, av7110->vidmode);
 201                        break;
 202                }
 203        } else {
 204                av7110->rec_mode &= ~av;
 205                switch (av7110->rec_mode) {
 206                case RP_AUDIO:
 207                        ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Record, 2, AudioPES, 0);
 208                        break;
 209                case RP_VIDEO:
 210                        ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Record, 2, VideoPES, 0);
 211                        break;
 212                case RP_NONE:
 213                        break;
 214                }
 215        }
 216        return ret;
 217}
 218
 219
 220int av7110_pes_play(void *dest, struct dvb_ringbuffer *buf, int dlen)
 221{
 222        int len;
 223        u32 sync;
 224        u16 blen;
 225
 226        if (!dlen) {
 227                wake_up(&buf->queue);
 228                return -1;
 229        }
 230        while (1) {
 231                len = dvb_ringbuffer_avail(buf);
 232                if (len < 6) {
 233                        wake_up(&buf->queue);
 234                        return -1;
 235                }
 236                sync =  DVB_RINGBUFFER_PEEK(buf, 0) << 24;
 237                sync |= DVB_RINGBUFFER_PEEK(buf, 1) << 16;
 238                sync |= DVB_RINGBUFFER_PEEK(buf, 2) << 8;
 239                sync |= DVB_RINGBUFFER_PEEK(buf, 3);
 240
 241                if (((sync &~ 0x0f) == 0x000001e0) ||
 242                    ((sync &~ 0x1f) == 0x000001c0) ||
 243                    (sync == 0x000001bd))
 244                        break;
 245                printk("resync\n");
 246                DVB_RINGBUFFER_SKIP(buf, 1);
 247        }
 248        blen =  DVB_RINGBUFFER_PEEK(buf, 4) << 8;
 249        blen |= DVB_RINGBUFFER_PEEK(buf, 5);
 250        blen += 6;
 251        if (len < blen || blen > dlen) {
 252                //printk("buffer empty - avail %d blen %u dlen %d\n", len, blen, dlen);
 253                wake_up(&buf->queue);
 254                return -1;
 255        }
 256
 257        dvb_ringbuffer_read(buf, dest, (size_t) blen);
 258
 259        dprintk(2, "pread=0x%08lx, pwrite=0x%08lx\n",
 260               (unsigned long) buf->pread, (unsigned long) buf->pwrite);
 261        wake_up(&buf->queue);
 262        return blen;
 263}
 264
 265
 266int av7110_set_volume(struct av7110 *av7110, unsigned int volleft,
 267                      unsigned int volright)
 268{
 269        unsigned int vol, val, balance = 0;
 270        int err;
 271
 272        dprintk(2, "av7110:%p, \n", av7110);
 273
 274        av7110->mixer.volume_left = volleft;
 275        av7110->mixer.volume_right = volright;
 276
 277        switch (av7110->adac_type) {
 278        case DVB_ADAC_TI:
 279                volleft = (volleft * 256) / 1036;
 280                volright = (volright * 256) / 1036;
 281                if (volleft > 0x3f)
 282                        volleft = 0x3f;
 283                if (volright > 0x3f)
 284                        volright = 0x3f;
 285                if ((err = SendDAC(av7110, 3, 0x80 + volleft)))
 286                        return err;
 287                return SendDAC(av7110, 4, volright);
 288
 289        case DVB_ADAC_CRYSTAL:
 290                volleft = 127 - volleft / 2;
 291                volright = 127 - volright / 2;
 292                i2c_writereg(av7110, 0x20, 0x03, volleft);
 293                i2c_writereg(av7110, 0x20, 0x04, volright);
 294                return 0;
 295
 296        case DVB_ADAC_MSP34x0:
 297                vol  = (volleft > volright) ? volleft : volright;
 298                val     = (vol * 0x73 / 255) << 8;
 299                if (vol > 0)
 300                       balance = ((volright - volleft) * 127) / vol;
 301                msp_writereg(av7110, MSP_WR_DSP, 0x0001, balance << 8);
 302                msp_writereg(av7110, MSP_WR_DSP, 0x0000, val); /* loudspeaker */
 303                msp_writereg(av7110, MSP_WR_DSP, 0x0006, val); /* headphonesr */
 304                return 0;
 305
 306        case DVB_ADAC_MSP34x5:
 307                vol = (volleft > volright) ? volleft : volright;
 308                val = (vol * 0x73 / 255) << 8;
 309                if (vol > 0)
 310                        balance = ((volright - volleft) * 127) / vol;
 311                msp_writereg(av7110, MSP_WR_DSP, 0x0001, balance << 8);
 312                msp_writereg(av7110, MSP_WR_DSP, 0x0000, val); /* loudspeaker */
 313                return 0;
 314        }
 315
 316        return 0;
 317}
 318
 319int av7110_set_vidmode(struct av7110 *av7110, enum av7110_video_mode mode)
 320{
 321        int ret;
 322        dprintk(2, "av7110:%p, \n", av7110);
 323
 324        ret = av7110_fw_cmd(av7110, COMTYPE_ENCODER, LoadVidCode, 1, mode);
 325
 326        if (!ret && !av7110->playing) {
 327                ret = ChangePIDs(av7110, av7110->pids[DMX_PES_VIDEO],
 328                           av7110->pids[DMX_PES_AUDIO],
 329                           av7110->pids[DMX_PES_TELETEXT],
 330                           0, av7110->pids[DMX_PES_PCR]);
 331                if (!ret)
 332                        ret = av7110_fw_cmd(av7110, COMTYPE_PIDFILTER, Scan, 0);
 333        }
 334        return ret;
 335}
 336
 337
 338static enum av7110_video_mode sw2mode[16] = {
 339        AV7110_VIDEO_MODE_PAL, AV7110_VIDEO_MODE_NTSC,
 340        AV7110_VIDEO_MODE_NTSC, AV7110_VIDEO_MODE_PAL,
 341        AV7110_VIDEO_MODE_NTSC, AV7110_VIDEO_MODE_NTSC,
 342        AV7110_VIDEO_MODE_PAL, AV7110_VIDEO_MODE_NTSC,
 343        AV7110_VIDEO_MODE_PAL, AV7110_VIDEO_MODE_PAL,
 344        AV7110_VIDEO_MODE_PAL, AV7110_VIDEO_MODE_PAL,
 345        AV7110_VIDEO_MODE_PAL, AV7110_VIDEO_MODE_PAL,
 346        AV7110_VIDEO_MODE_PAL, AV7110_VIDEO_MODE_PAL,
 347};
 348
 349static int get_video_format(struct av7110 *av7110, u8 *buf, int count)
 350{
 351        int i;
 352        int hsize, vsize;
 353        int sw;
 354        u8 *p;
 355        int ret = 0;
 356
 357        dprintk(2, "av7110:%p, \n", av7110);
 358
 359        if (av7110->sinfo)
 360                return 0;
 361        for (i = 7; i < count - 10; i++) {
 362                p = buf + i;
 363                if (p[0] || p[1] || p[2] != 0x01 || p[3] != 0xb3)
 364                        continue;
 365                p += 4;
 366                hsize = ((p[1] &0xF0) >> 4) | (p[0] << 4);
 367                vsize = ((p[1] &0x0F) << 8) | (p[2]);
 368                sw = (p[3] & 0x0F);
 369                ret = av7110_set_vidmode(av7110, sw2mode[sw]);
 370                if (!ret) {
 371                        dprintk(2, "playback %dx%d fr=%d\n", hsize, vsize, sw);
 372                        av7110->sinfo = 1;
 373                }
 374                break;
 375        }
 376        return ret;
 377}
 378
 379
 380/****************************************************************************
 381 * I/O buffer management and control
 382 ****************************************************************************/
 383
 384static inline long aux_ring_buffer_write(struct dvb_ringbuffer *rbuf,
 385                                         const u8 *buf, unsigned long count)
 386{
 387        unsigned long todo = count;
 388        int free;
 389
 390        while (todo > 0) {
 391                if (dvb_ringbuffer_free(rbuf) < 2048) {
 392                        if (wait_event_interruptible(rbuf->queue,
 393                                                     (dvb_ringbuffer_free(rbuf) >= 2048)))
 394                                return count - todo;
 395                }
 396                free = dvb_ringbuffer_free(rbuf);
 397                if (free > todo)
 398                        free = todo;
 399                dvb_ringbuffer_write(rbuf, buf, free);
 400                todo -= free;
 401                buf += free;
 402        }
 403
 404        return count - todo;
 405}
 406
 407static void play_video_cb(u8 *buf, int count, void *priv)
 408{
 409        struct av7110 *av7110 = (struct av7110 *) priv;
 410        dprintk(2, "av7110:%p, \n", av7110);
 411
 412        if ((buf[3] & 0xe0) == 0xe0) {
 413                get_video_format(av7110, buf, count);
 414                aux_ring_buffer_write(&av7110->avout, buf, count);
 415        } else
 416                aux_ring_buffer_write(&av7110->aout, buf, count);
 417}
 418
 419static void play_audio_cb(u8 *buf, int count, void *priv)
 420{
 421        struct av7110 *av7110 = (struct av7110 *) priv;
 422        dprintk(2, "av7110:%p, \n", av7110);
 423
 424        aux_ring_buffer_write(&av7110->aout, buf, count);
 425}
 426
 427
 428#define FREE_COND_TS (dvb_ringbuffer_free(rb) >= 4096)
 429
 430static ssize_t ts_play(struct av7110 *av7110, const char __user *buf,
 431                       unsigned long count, int nonblock, int type)
 432{
 433        struct dvb_ringbuffer *rb;
 434        u8 *kb;
 435        unsigned long todo = count;
 436
 437        dprintk(2, "%s: type %d cnt %lu\n", __func__, type, count);
 438
 439        rb = (type) ? &av7110->avout : &av7110->aout;
 440        kb = av7110->kbuf[type];
 441
 442        if (!kb)
 443                return -ENOBUFS;
 444
 445        if (nonblock && !FREE_COND_TS)
 446                return -EWOULDBLOCK;
 447
 448        while (todo >= TS_SIZE) {
 449                if (!FREE_COND_TS) {
 450                        if (nonblock)
 451                                return count - todo;
 452                        if (wait_event_interruptible(rb->queue, FREE_COND_TS))
 453                                return count - todo;
 454                }
 455                if (copy_from_user(kb, buf, TS_SIZE))
 456                        return -EFAULT;
 457                write_ts_to_decoder(av7110, type, kb, TS_SIZE);
 458                todo -= TS_SIZE;
 459                buf += TS_SIZE;
 460        }
 461
 462        return count - todo;
 463}
 464
 465
 466#define FREE_COND (dvb_ringbuffer_free(&av7110->avout) >= 20 * 1024 && \
 467                   dvb_ringbuffer_free(&av7110->aout) >= 20 * 1024)
 468
 469static ssize_t dvb_play(struct av7110 *av7110, const char __user *buf,
 470                        unsigned long count, int nonblock, int type)
 471{
 472        unsigned long todo = count, n;
 473        dprintk(2, "av7110:%p, \n", av7110);
 474
 475        if (!av7110->kbuf[type])
 476                return -ENOBUFS;
 477
 478        if (nonblock && !FREE_COND)
 479                return -EWOULDBLOCK;
 480
 481        while (todo > 0) {
 482                if (!FREE_COND) {
 483                        if (nonblock)
 484                                return count - todo;
 485                        if (wait_event_interruptible(av7110->avout.queue,
 486                                                     FREE_COND))
 487                                return count - todo;
 488                }
 489                n = todo;
 490                if (n > IPACKS * 2)
 491                        n = IPACKS * 2;
 492                if (copy_from_user(av7110->kbuf[type], buf, n))
 493                        return -EFAULT;
 494                av7110_ipack_instant_repack(av7110->kbuf[type], n,
 495                                            &av7110->ipack[type]);
 496                todo -= n;
 497                buf += n;
 498        }
 499        return count - todo;
 500}
 501
 502static ssize_t dvb_play_kernel(struct av7110 *av7110, const u8 *buf,
 503                        unsigned long count, int nonblock, int type)
 504{
 505        unsigned long todo = count, n;
 506        dprintk(2, "av7110:%p, \n", av7110);
 507
 508        if (!av7110->kbuf[type])
 509                return -ENOBUFS;
 510
 511        if (nonblock && !FREE_COND)
 512                return -EWOULDBLOCK;
 513
 514        while (todo > 0) {
 515                if (!FREE_COND) {
 516                        if (nonblock)
 517                                return count - todo;
 518                        if (wait_event_interruptible(av7110->avout.queue,
 519                                                     FREE_COND))
 520                                return count - todo;
 521                }
 522                n = todo;
 523                if (n > IPACKS * 2)
 524                        n = IPACKS * 2;
 525                av7110_ipack_instant_repack(buf, n, &av7110->ipack[type]);
 526                todo -= n;
 527                buf += n;
 528        }
 529        return count - todo;
 530}
 531
 532static ssize_t dvb_aplay(struct av7110 *av7110, const char __user *buf,
 533                         unsigned long count, int nonblock, int type)
 534{
 535        unsigned long todo = count, n;
 536        dprintk(2, "av7110:%p, \n", av7110);
 537
 538        if (!av7110->kbuf[type])
 539                return -ENOBUFS;
 540        if (nonblock && dvb_ringbuffer_free(&av7110->aout) < 20 * 1024)
 541                return -EWOULDBLOCK;
 542
 543        while (todo > 0) {
 544                if (dvb_ringbuffer_free(&av7110->aout) < 20 * 1024) {
 545                        if (nonblock)
 546                                return count - todo;
 547                        if (wait_event_interruptible(av7110->aout.queue,
 548                                        (dvb_ringbuffer_free(&av7110->aout) >= 20 * 1024)))
 549                                return count-todo;
 550                }
 551                n = todo;
 552                if (n > IPACKS * 2)
 553                        n = IPACKS * 2;
 554                if (copy_from_user(av7110->kbuf[type], buf, n))
 555                        return -EFAULT;
 556                av7110_ipack_instant_repack(av7110->kbuf[type], n,
 557                                            &av7110->ipack[type]);
 558                todo -= n;
 559                buf += n;
 560        }
 561        return count - todo;
 562}
 563
 564void av7110_p2t_init(struct av7110_p2t *p, struct dvb_demux_feed *feed)
 565{
 566        memset(p->pes, 0, TS_SIZE);
 567        p->counter = 0;
 568        p->pos = 0;
 569        p->frags = 0;
 570        if (feed)
 571                p->feed = feed;
 572}
 573
 574static void clear_p2t(struct av7110_p2t *p)
 575{
 576        memset(p->pes, 0, TS_SIZE);
 577//      p->counter = 0;
 578        p->pos = 0;
 579        p->frags = 0;
 580}
 581
 582
 583static int find_pes_header(u8 const *buf, long int length, int *frags)
 584{
 585        int c = 0;
 586        int found = 0;
 587
 588        *frags = 0;
 589
 590        while (c < length - 3 && !found) {
 591                if (buf[c] == 0x00 && buf[c + 1] == 0x00 &&
 592                    buf[c + 2] == 0x01) {
 593                        switch ( buf[c + 3] ) {
 594                        case PROG_STREAM_MAP:
 595                        case PRIVATE_STREAM2:
 596                        case PROG_STREAM_DIR:
 597                        case ECM_STREAM     :
 598                        case EMM_STREAM     :
 599                        case PADDING_STREAM :
 600                        case DSM_CC_STREAM  :
 601                        case ISO13522_STREAM:
 602                        case PRIVATE_STREAM1:
 603                        case AUDIO_STREAM_S ... AUDIO_STREAM_E:
 604                        case VIDEO_STREAM_S ... VIDEO_STREAM_E:
 605                                found = 1;
 606                                break;
 607
 608                        default:
 609                                c++;
 610                                break;
 611                        }
 612                } else
 613                        c++;
 614        }
 615        if (c == length - 3 && !found) {
 616                if (buf[length - 1] == 0x00)
 617                        *frags = 1;
 618                if (buf[length - 2] == 0x00 &&
 619                    buf[length - 1] == 0x00)
 620                        *frags = 2;
 621                if (buf[length - 3] == 0x00 &&
 622                    buf[length - 2] == 0x00 &&
 623                    buf[length - 1] == 0x01)
 624                        *frags = 3;
 625                return -1;
 626        }
 627
 628        return c;
 629}
 630
 631void av7110_p2t_write(u8 const *buf, long int length, u16 pid, struct av7110_p2t *p)
 632{
 633        int c, c2, l, add;
 634        int check, rest;
 635
 636        c = 0;
 637        c2 = 0;
 638        if (p->frags){
 639                check = 0;
 640                switch(p->frags) {
 641                case 1:
 642                        if (buf[c] == 0x00 && buf[c + 1] == 0x01) {
 643                                check = 1;
 644                                c += 2;
 645                        }
 646                        break;
 647                case 2:
 648                        if (buf[c] == 0x01) {
 649                                check = 1;
 650                                c++;
 651                        }
 652                        break;
 653                case 3:
 654                        check = 1;
 655                }
 656                if (check) {
 657                        switch (buf[c]) {
 658                        case PROG_STREAM_MAP:
 659                        case PRIVATE_STREAM2:
 660                        case PROG_STREAM_DIR:
 661                        case ECM_STREAM     :
 662                        case EMM_STREAM     :
 663                        case PADDING_STREAM :
 664                        case DSM_CC_STREAM  :
 665                        case ISO13522_STREAM:
 666                        case PRIVATE_STREAM1:
 667                        case AUDIO_STREAM_S ... AUDIO_STREAM_E:
 668                        case VIDEO_STREAM_S ... VIDEO_STREAM_E:
 669                                p->pes[0] = 0x00;
 670                                p->pes[1] = 0x00;
 671                                p->pes[2] = 0x01;
 672                                p->pes[3] = buf[c];
 673                                p->pos = 4;
 674                                memcpy(p->pes + p->pos, buf + c, (TS_SIZE - 4) - p->pos);
 675                                c += (TS_SIZE - 4) - p->pos;
 676                                p_to_t(p->pes, (TS_SIZE - 4), pid, &p->counter, p->feed);
 677                                clear_p2t(p);
 678                                break;
 679
 680                        default:
 681                                c = 0;
 682                                break;
 683                        }
 684                }
 685                p->frags = 0;
 686        }
 687
 688        if (p->pos) {
 689                c2 = find_pes_header(buf + c, length - c, &p->frags);
 690                if (c2 >= 0 && c2 < (TS_SIZE - 4) - p->pos)
 691                        l = c2+c;
 692                else
 693                        l = (TS_SIZE - 4) - p->pos;
 694                memcpy(p->pes + p->pos, buf, l);
 695                c += l;
 696                p->pos += l;
 697                p_to_t(p->pes, p->pos, pid, &p->counter, p->feed);
 698                clear_p2t(p);
 699        }
 700
 701        add = 0;
 702        while (c < length) {
 703                c2 = find_pes_header(buf + c + add, length - c - add, &p->frags);
 704                if (c2 >= 0) {
 705                        c2 += c + add;
 706                        if (c2 > c){
 707                                p_to_t(buf + c, c2 - c, pid, &p->counter, p->feed);
 708                                c = c2;
 709                                clear_p2t(p);
 710                                add = 0;
 711                        } else
 712                                add = 1;
 713                } else {
 714                        l = length - c;
 715                        rest = l % (TS_SIZE - 4);
 716                        l -= rest;
 717                        p_to_t(buf + c, l, pid, &p->counter, p->feed);
 718                        memcpy(p->pes, buf + c + l, rest);
 719                        p->pos = rest;
 720                        c = length;
 721                }
 722        }
 723}
 724
 725
 726static int write_ts_header2(u16 pid, u8 *counter, int pes_start, u8 *buf, u8 length)
 727{
 728        int i;
 729        int c = 0;
 730        int fill;
 731        u8 tshead[4] = { 0x47, 0x00, 0x00, 0x10 };
 732
 733        fill = (TS_SIZE - 4) - length;
 734        if (pes_start)
 735                tshead[1] = 0x40;
 736        if (fill)
 737                tshead[3] = 0x30;
 738        tshead[1] |= (u8)((pid & 0x1F00) >> 8);
 739        tshead[2] |= (u8)(pid & 0x00FF);
 740        tshead[3] |= ((*counter)++ & 0x0F);
 741        memcpy(buf, tshead, 4);
 742        c += 4;
 743
 744        if (fill) {
 745                buf[4] = fill - 1;
 746                c++;
 747                if (fill > 1) {
 748                        buf[5] = 0x00;
 749                        c++;
 750                }
 751                for (i = 6; i < fill + 4; i++) {
 752                        buf[i] = 0xFF;
 753                        c++;
 754                }
 755        }
 756
 757        return c;
 758}
 759
 760
 761static void p_to_t(u8 const *buf, long int length, u16 pid, u8 *counter,
 762                   struct dvb_demux_feed *feed)
 763{
 764        int l, pes_start;
 765        u8 obuf[TS_SIZE];
 766        long c = 0;
 767
 768        pes_start = 0;
 769        if (length > 3 &&
 770             buf[0] == 0x00 && buf[1] == 0x00 && buf[2] == 0x01)
 771                switch (buf[3]) {
 772                        case PROG_STREAM_MAP:
 773                        case PRIVATE_STREAM2:
 774                        case PROG_STREAM_DIR:
 775                        case ECM_STREAM     :
 776                        case EMM_STREAM     :
 777                        case PADDING_STREAM :
 778                        case DSM_CC_STREAM  :
 779                        case ISO13522_STREAM:
 780                        case PRIVATE_STREAM1:
 781                        case AUDIO_STREAM_S ... AUDIO_STREAM_E:
 782                        case VIDEO_STREAM_S ... VIDEO_STREAM_E:
 783                                pes_start = 1;
 784                                break;
 785
 786                        default:
 787                                break;
 788                }
 789
 790        while (c < length) {
 791                memset(obuf, 0, TS_SIZE);
 792                if (length - c >= (TS_SIZE - 4)){
 793                        l = write_ts_header2(pid, counter, pes_start,
 794                                             obuf, (TS_SIZE - 4));
 795                        memcpy(obuf + l, buf + c, TS_SIZE - l);
 796                        c += TS_SIZE - l;
 797                } else {
 798                        l = write_ts_header2(pid, counter, pes_start,
 799                                             obuf, length - c);
 800                        memcpy(obuf + l, buf + c, TS_SIZE - l);
 801                        c = length;
 802                }
 803                feed->cb.ts(obuf, 188, NULL, 0, &feed->feed.ts, NULL);
 804                pes_start = 0;
 805        }
 806}
 807
 808
 809static int write_ts_to_decoder(struct av7110 *av7110, int type, const u8 *buf, size_t len)
 810{
 811        struct ipack *ipack = &av7110->ipack[type];
 812
 813        if (buf[1] & TRANS_ERROR) {
 814                av7110_ipack_reset(ipack);
 815                return -1;
 816        }
 817
 818        if (!(buf[3] & PAYLOAD))
 819                return -1;
 820
 821        if (buf[1] & PAY_START)
 822                av7110_ipack_flush(ipack);
 823
 824        if (buf[3] & ADAPT_FIELD) {
 825                len -= buf[4] + 1;
 826                buf += buf[4] + 1;
 827                if (!len)
 828                        return 0;
 829        }
 830
 831        av7110_ipack_instant_repack(buf + 4, len - 4, ipack);
 832        return 0;
 833}
 834
 835
 836int av7110_write_to_decoder(struct dvb_demux_feed *feed, const u8 *buf, size_t len)
 837{
 838        struct dvb_demux *demux = feed->demux;
 839        struct av7110 *av7110 = (struct av7110 *) demux->priv;
 840
 841        dprintk(2, "av7110:%p, \n", av7110);
 842
 843        if (av7110->full_ts && demux->dmx.frontend->source != DMX_MEMORY_FE)
 844                return 0;
 845
 846        switch (feed->pes_type) {
 847        case 0:
 848                if (av7110->audiostate.stream_source == AUDIO_SOURCE_MEMORY)
 849                        return -EINVAL;
 850                break;
 851        case 1:
 852                if (av7110->videostate.stream_source == VIDEO_SOURCE_MEMORY)
 853                        return -EINVAL;
 854                break;
 855        default:
 856                return -1;
 857        }
 858
 859        return write_ts_to_decoder(av7110, feed->pes_type, buf, len);
 860}
 861
 862
 863
 864/******************************************************************************
 865 * Video MPEG decoder events
 866 ******************************************************************************/
 867void dvb_video_add_event(struct av7110 *av7110, struct video_event *event)
 868{
 869        struct dvb_video_events *events = &av7110->video_events;
 870        int wp;
 871
 872        spin_lock_bh(&events->lock);
 873
 874        wp = (events->eventw + 1) % MAX_VIDEO_EVENT;
 875        if (wp == events->eventr) {
 876                events->overflow = 1;
 877                events->eventr = (events->eventr + 1) % MAX_VIDEO_EVENT;
 878        }
 879
 880        //FIXME: timestamp?
 881        memcpy(&events->events[events->eventw], event, sizeof(struct video_event));
 882        events->eventw = wp;
 883
 884        spin_unlock_bh(&events->lock);
 885
 886        wake_up_interruptible(&events->wait_queue);
 887}
 888
 889
 890static int dvb_video_get_event (struct av7110 *av7110, struct video_event *event, int flags)
 891{
 892        struct dvb_video_events *events = &av7110->video_events;
 893
 894        if (events->overflow) {
 895                events->overflow = 0;
 896                return -EOVERFLOW;
 897        }
 898        if (events->eventw == events->eventr) {
 899                int ret;
 900
 901                if (flags & O_NONBLOCK)
 902                        return -EWOULDBLOCK;
 903
 904                ret = wait_event_interruptible(events->wait_queue,
 905                                               events->eventw != events->eventr);
 906                if (ret < 0)
 907                        return ret;
 908        }
 909
 910        spin_lock_bh(&events->lock);
 911
 912        memcpy(event, &events->events[events->eventr],
 913               sizeof(struct video_event));
 914        events->eventr = (events->eventr + 1) % MAX_VIDEO_EVENT;
 915
 916        spin_unlock_bh(&events->lock);
 917
 918        return 0;
 919}
 920
 921/******************************************************************************
 922 * DVB device file operations
 923 ******************************************************************************/
 924
 925static __poll_t dvb_video_poll(struct file *file, poll_table *wait)
 926{
 927        struct dvb_device *dvbdev = file->private_data;
 928        struct av7110 *av7110 = dvbdev->priv;
 929        __poll_t mask = 0;
 930
 931        dprintk(2, "av7110:%p, \n", av7110);
 932
 933        if ((file->f_flags & O_ACCMODE) != O_RDONLY)
 934                poll_wait(file, &av7110->avout.queue, wait);
 935
 936        poll_wait(file, &av7110->video_events.wait_queue, wait);
 937
 938        if (av7110->video_events.eventw != av7110->video_events.eventr)
 939                mask = EPOLLPRI;
 940
 941        if ((file->f_flags & O_ACCMODE) != O_RDONLY) {
 942                if (av7110->playing) {
 943                        if (FREE_COND)
 944                                mask |= (EPOLLOUT | EPOLLWRNORM);
 945                } else {
 946                        /* if not playing: may play if asked for */
 947                        mask |= (EPOLLOUT | EPOLLWRNORM);
 948                }
 949        }
 950
 951        return mask;
 952}
 953
 954static ssize_t dvb_video_write(struct file *file, const char __user *buf,
 955                               size_t count, loff_t *ppos)
 956{
 957        struct dvb_device *dvbdev = file->private_data;
 958        struct av7110 *av7110 = dvbdev->priv;
 959        unsigned char c;
 960
 961        dprintk(2, "av7110:%p, \n", av7110);
 962
 963        if ((file->f_flags & O_ACCMODE) == O_RDONLY)
 964                return -EPERM;
 965
 966        if (av7110->videostate.stream_source != VIDEO_SOURCE_MEMORY)
 967                return -EPERM;
 968
 969        if (get_user(c, buf))
 970                return -EFAULT;
 971        if (c == 0x47 && count % TS_SIZE == 0)
 972                return ts_play(av7110, buf, count, file->f_flags & O_NONBLOCK, 1);
 973        else
 974                return dvb_play(av7110, buf, count, file->f_flags & O_NONBLOCK, 1);
 975}
 976
 977static __poll_t dvb_audio_poll(struct file *file, poll_table *wait)
 978{
 979        struct dvb_device *dvbdev = file->private_data;
 980        struct av7110 *av7110 = dvbdev->priv;
 981        __poll_t mask = 0;
 982
 983        dprintk(2, "av7110:%p, \n", av7110);
 984
 985        poll_wait(file, &av7110->aout.queue, wait);
 986
 987        if (av7110->playing) {
 988                if (dvb_ringbuffer_free(&av7110->aout) >= 20 * 1024)
 989                        mask |= (EPOLLOUT | EPOLLWRNORM);
 990        } else /* if not playing: may play if asked for */
 991                mask = (EPOLLOUT | EPOLLWRNORM);
 992
 993        return mask;
 994}
 995
 996static ssize_t dvb_audio_write(struct file *file, const char __user *buf,
 997                               size_t count, loff_t *ppos)
 998{
 999        struct dvb_device *dvbdev = file->private_data;
1000        struct av7110 *av7110 = dvbdev->priv;
1001        unsigned char c;
1002
1003        dprintk(2, "av7110:%p, \n", av7110);
1004
1005        if (av7110->audiostate.stream_source != AUDIO_SOURCE_MEMORY) {
1006                printk(KERN_ERR "not audio source memory\n");
1007                return -EPERM;
1008        }
1009
1010        if (get_user(c, buf))
1011                return -EFAULT;
1012        if (c == 0x47 && count % TS_SIZE == 0)
1013                return ts_play(av7110, buf, count, file->f_flags & O_NONBLOCK, 0);
1014        else
1015                return dvb_aplay(av7110, buf, count, file->f_flags & O_NONBLOCK, 0);
1016}
1017
1018static u8 iframe_header[] = { 0x00, 0x00, 0x01, 0xe0, 0x00, 0x00, 0x80, 0x00, 0x00 };
1019
1020#define MIN_IFRAME 400000
1021
1022static int play_iframe(struct av7110 *av7110, char __user *buf, unsigned int len, int nonblock)
1023{
1024        unsigned i, n;
1025        int progressive = 0;
1026        int match = 0;
1027
1028        dprintk(2, "av7110:%p, \n", av7110);
1029
1030        if (len == 0)
1031                return 0;
1032
1033        if (!(av7110->playing & RP_VIDEO)) {
1034                if (av7110_av_start_play(av7110, RP_VIDEO) < 0)
1035                        return -EBUSY;
1036        }
1037
1038        /* search in buf for instances of 00 00 01 b5 1? */
1039        for (i = 0; i < len; i++) {
1040                unsigned char c;
1041                if (get_user(c, buf + i))
1042                        return -EFAULT;
1043                if (match == 5) {
1044                        progressive = c & 0x08;
1045                        match = 0;
1046                }
1047                if (c == 0x00) {
1048                        match = (match == 1 || match == 2) ? 2 : 1;
1049                        continue;
1050                }
1051                switch (match++) {
1052                case 2: if (c == 0x01)
1053                                continue;
1054                        break;
1055                case 3: if (c == 0xb5)
1056                                continue;
1057                        break;
1058                case 4: if ((c & 0xf0) == 0x10)
1059                                continue;
1060                        break;
1061                }
1062                match = 0;
1063        }
1064
1065        /* setting n always > 1, fixes problems when playing stillframes
1066           consisting of I- and P-Frames */
1067        n = MIN_IFRAME / len + 1;
1068
1069        /* FIXME: nonblock? */
1070        dvb_play_kernel(av7110, iframe_header, sizeof(iframe_header), 0, 1);
1071
1072        for (i = 0; i < n; i++)
1073                dvb_play(av7110, buf, len, 0, 1);
1074
1075        av7110_ipack_flush(&av7110->ipack[1]);
1076
1077        if (progressive)
1078                return vidcom(av7110, AV_VIDEO_CMD_FREEZE, 1);
1079        else
1080                return 0;
1081}
1082
1083#ifdef CONFIG_COMPAT
1084struct compat_video_still_picture {
1085        compat_uptr_t iFrame;
1086        int32_t size;
1087};
1088#define VIDEO_STILLPICTURE32 _IOW('o', 30, struct compat_video_still_picture)
1089
1090struct compat_video_event {
1091        __s32 type;
1092        /* unused, make sure to use atomic time for y2038 if it ever gets used */
1093        compat_long_t timestamp;
1094        union {
1095                video_size_t size;
1096                unsigned int frame_rate;        /* in frames per 1000sec */
1097                unsigned char vsync_field;      /* unknown/odd/even/progressive */
1098        } u;
1099};
1100#define VIDEO_GET_EVENT32 _IOR('o', 28, struct compat_video_event)
1101
1102static int dvb_compat_video_get_event(struct av7110 *av7110,
1103                                      struct compat_video_event *event, int flags)
1104{
1105        struct video_event ev;
1106        int ret;
1107
1108        ret = dvb_video_get_event(av7110, &ev, flags);
1109
1110        *event = (struct compat_video_event) {
1111                .type = ev.type,
1112                .timestamp = ev.timestamp,
1113                .u.size = ev.u.size,
1114        };
1115
1116        return ret;
1117}
1118#endif
1119
1120static int dvb_video_ioctl(struct file *file,
1121                           unsigned int cmd, void *parg)
1122{
1123        struct dvb_device *dvbdev = file->private_data;
1124        struct av7110 *av7110 = dvbdev->priv;
1125        unsigned long arg = (unsigned long) parg;
1126        int ret = 0;
1127
1128        dprintk(1, "av7110:%p, cmd=%04x\n", av7110,cmd);
1129
1130        if ((file->f_flags & O_ACCMODE) == O_RDONLY) {
1131                if ( cmd != VIDEO_GET_STATUS && cmd != VIDEO_GET_EVENT &&
1132                     cmd != VIDEO_GET_SIZE ) {
1133                        return -EPERM;
1134                }
1135        }
1136
1137        if (mutex_lock_interruptible(&av7110->ioctl_mutex))
1138                return -ERESTARTSYS;
1139
1140        switch (cmd) {
1141        case VIDEO_STOP:
1142                av7110->videostate.play_state = VIDEO_STOPPED;
1143                if (av7110->videostate.stream_source == VIDEO_SOURCE_MEMORY)
1144                        ret = av7110_av_stop(av7110, RP_VIDEO);
1145                else
1146                        ret = vidcom(av7110, AV_VIDEO_CMD_STOP,
1147                               av7110->videostate.video_blank ? 0 : 1);
1148                if (!ret)
1149                        av7110->trickmode = TRICK_NONE;
1150                break;
1151
1152        case VIDEO_PLAY:
1153                av7110->trickmode = TRICK_NONE;
1154                if (av7110->videostate.play_state == VIDEO_FREEZED) {
1155                        av7110->videostate.play_state = VIDEO_PLAYING;
1156                        ret = vidcom(av7110, AV_VIDEO_CMD_PLAY, 0);
1157                        if (ret)
1158                                break;
1159                }
1160                if (av7110->videostate.stream_source == VIDEO_SOURCE_MEMORY) {
1161                        if (av7110->playing == RP_AV) {
1162                                ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Stop, 0);
1163                                if (ret)
1164                                        break;
1165                                av7110->playing &= ~RP_VIDEO;
1166                        }
1167                        ret = av7110_av_start_play(av7110, RP_VIDEO);
1168                }
1169                if (!ret)
1170                        ret = vidcom(av7110, AV_VIDEO_CMD_PLAY, 0);
1171                if (!ret)
1172                        av7110->videostate.play_state = VIDEO_PLAYING;
1173                break;
1174
1175        case VIDEO_FREEZE:
1176                av7110->videostate.play_state = VIDEO_FREEZED;
1177                if (av7110->playing & RP_VIDEO)
1178                        ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Pause, 0);
1179                else
1180                        ret = vidcom(av7110, AV_VIDEO_CMD_FREEZE, 1);
1181                if (!ret)
1182                        av7110->trickmode = TRICK_FREEZE;
1183                break;
1184
1185        case VIDEO_CONTINUE:
1186                if (av7110->playing & RP_VIDEO)
1187                        ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Continue, 0);
1188                if (!ret)
1189                        ret = vidcom(av7110, AV_VIDEO_CMD_PLAY, 0);
1190                if (!ret) {
1191                        av7110->videostate.play_state = VIDEO_PLAYING;
1192                        av7110->trickmode = TRICK_NONE;
1193                }
1194                break;
1195
1196        case VIDEO_SELECT_SOURCE:
1197                av7110->videostate.stream_source = (video_stream_source_t) arg;
1198                break;
1199
1200        case VIDEO_SET_BLANK:
1201                av7110->videostate.video_blank = (int) arg;
1202                break;
1203
1204        case VIDEO_GET_STATUS:
1205                memcpy(parg, &av7110->videostate, sizeof(struct video_status));
1206                break;
1207
1208#ifdef CONFIG_COMPAT
1209        case VIDEO_GET_EVENT32:
1210                ret = dvb_compat_video_get_event(av7110, parg, file->f_flags);
1211                break;
1212#endif
1213
1214        case VIDEO_GET_EVENT:
1215                ret = dvb_video_get_event(av7110, parg, file->f_flags);
1216                break;
1217
1218        case VIDEO_GET_SIZE:
1219                memcpy(parg, &av7110->video_size, sizeof(video_size_t));
1220                break;
1221
1222        case VIDEO_SET_DISPLAY_FORMAT:
1223        {
1224                video_displayformat_t format = (video_displayformat_t) arg;
1225                switch (format) {
1226                case VIDEO_PAN_SCAN:
1227                        av7110->display_panscan = VID_PAN_SCAN_PREF;
1228                        break;
1229                case VIDEO_LETTER_BOX:
1230                        av7110->display_panscan = VID_VC_AND_PS_PREF;
1231                        break;
1232                case VIDEO_CENTER_CUT_OUT:
1233                        av7110->display_panscan = VID_CENTRE_CUT_PREF;
1234                        break;
1235                default:
1236                        ret = -EINVAL;
1237                }
1238                if (ret < 0)
1239                        break;
1240                av7110->videostate.display_format = format;
1241                ret = av7110_fw_cmd(av7110, COMTYPE_ENCODER, SetPanScanType,
1242                                    1, av7110->display_panscan);
1243                break;
1244        }
1245
1246        case VIDEO_SET_FORMAT:
1247                if (arg > 1) {
1248                        ret = -EINVAL;
1249                        break;
1250                }
1251                av7110->display_ar = arg;
1252                ret = av7110_fw_cmd(av7110, COMTYPE_ENCODER, SetMonitorType,
1253                                    1, (u16) arg);
1254                break;
1255
1256#ifdef CONFIG_COMPAT
1257        case VIDEO_STILLPICTURE32:
1258        {
1259                struct compat_video_still_picture *pic =
1260                        (struct compat_video_still_picture *) parg;
1261                av7110->videostate.stream_source = VIDEO_SOURCE_MEMORY;
1262                dvb_ringbuffer_flush_spinlock_wakeup(&av7110->avout);
1263                ret = play_iframe(av7110, compat_ptr(pic->iFrame),
1264                                  pic->size, file->f_flags & O_NONBLOCK);
1265                break;
1266        }
1267#endif
1268
1269        case VIDEO_STILLPICTURE:
1270        {
1271                struct video_still_picture *pic =
1272                        (struct video_still_picture *) parg;
1273                av7110->videostate.stream_source = VIDEO_SOURCE_MEMORY;
1274                dvb_ringbuffer_flush_spinlock_wakeup(&av7110->avout);
1275                ret = play_iframe(av7110, pic->iFrame, pic->size,
1276                                  file->f_flags & O_NONBLOCK);
1277                break;
1278        }
1279
1280        case VIDEO_FAST_FORWARD:
1281                //note: arg is ignored by firmware
1282                if (av7110->playing & RP_VIDEO)
1283                        ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY,
1284                                            __Scan_I, 2, AV_PES, 0);
1285                else
1286                        ret = vidcom(av7110, AV_VIDEO_CMD_FFWD, arg);
1287                if (!ret) {
1288                        av7110->trickmode = TRICK_FAST;
1289                        av7110->videostate.play_state = VIDEO_PLAYING;
1290                }
1291                break;
1292
1293        case VIDEO_SLOWMOTION:
1294                if (av7110->playing&RP_VIDEO) {
1295                        if (av7110->trickmode != TRICK_SLOW)
1296                                ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY, __Slow, 2, 0, 0);
1297                        if (!ret)
1298                                ret = vidcom(av7110, AV_VIDEO_CMD_SLOW, arg);
1299                } else {
1300                        ret = vidcom(av7110, AV_VIDEO_CMD_PLAY, 0);
1301                        if (!ret)
1302                                ret = vidcom(av7110, AV_VIDEO_CMD_STOP, 0);
1303                        if (!ret)
1304                                ret = vidcom(av7110, AV_VIDEO_CMD_SLOW, arg);
1305                }
1306                if (!ret) {
1307                        av7110->trickmode = TRICK_SLOW;
1308                        av7110->videostate.play_state = VIDEO_PLAYING;
1309                }
1310                break;
1311
1312        case VIDEO_GET_CAPABILITIES:
1313                *(int *)parg = VIDEO_CAP_MPEG1 | VIDEO_CAP_MPEG2 |
1314                        VIDEO_CAP_SYS | VIDEO_CAP_PROG;
1315                break;
1316
1317        case VIDEO_CLEAR_BUFFER:
1318                dvb_ringbuffer_flush_spinlock_wakeup(&av7110->avout);
1319                av7110_ipack_reset(&av7110->ipack[1]);
1320                if (av7110->playing == RP_AV) {
1321                        ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY,
1322                                            __Play, 2, AV_PES, 0);
1323                        if (ret)
1324                                break;
1325                        if (av7110->trickmode == TRICK_FAST)
1326                                ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY,
1327                                                    __Scan_I, 2, AV_PES, 0);
1328                        if (av7110->trickmode == TRICK_SLOW) {
1329                                ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY,
1330                                                    __Slow, 2, 0, 0);
1331                                if (!ret)
1332                                        ret = vidcom(av7110, AV_VIDEO_CMD_SLOW, arg);
1333                        }
1334                        if (av7110->trickmode == TRICK_FREEZE)
1335                                ret = vidcom(av7110, AV_VIDEO_CMD_STOP, 1);
1336                }
1337                break;
1338
1339        case VIDEO_SET_STREAMTYPE:
1340                break;
1341
1342        default:
1343                ret = -ENOIOCTLCMD;
1344                break;
1345        }
1346
1347        mutex_unlock(&av7110->ioctl_mutex);
1348        return ret;
1349}
1350
1351static int dvb_audio_ioctl(struct file *file,
1352                           unsigned int cmd, void *parg)
1353{
1354        struct dvb_device *dvbdev = file->private_data;
1355        struct av7110 *av7110 = dvbdev->priv;
1356        unsigned long arg = (unsigned long) parg;
1357        int ret = 0;
1358
1359        dprintk(1, "av7110:%p, cmd=%04x\n", av7110,cmd);
1360
1361        if (((file->f_flags & O_ACCMODE) == O_RDONLY) &&
1362            (cmd != AUDIO_GET_STATUS))
1363                return -EPERM;
1364
1365        if (mutex_lock_interruptible(&av7110->ioctl_mutex))
1366                return -ERESTARTSYS;
1367
1368        switch (cmd) {
1369        case AUDIO_STOP:
1370                if (av7110->audiostate.stream_source == AUDIO_SOURCE_MEMORY)
1371                        ret = av7110_av_stop(av7110, RP_AUDIO);
1372                else
1373                        ret = audcom(av7110, AUDIO_CMD_MUTE);
1374                if (!ret)
1375                        av7110->audiostate.play_state = AUDIO_STOPPED;
1376                break;
1377
1378        case AUDIO_PLAY:
1379                if (av7110->audiostate.stream_source == AUDIO_SOURCE_MEMORY)
1380                        ret = av7110_av_start_play(av7110, RP_AUDIO);
1381                if (!ret)
1382                        ret = audcom(av7110, AUDIO_CMD_UNMUTE);
1383                if (!ret)
1384                        av7110->audiostate.play_state = AUDIO_PLAYING;
1385                break;
1386
1387        case AUDIO_PAUSE:
1388                ret = audcom(av7110, AUDIO_CMD_MUTE);
1389                if (!ret)
1390                        av7110->audiostate.play_state = AUDIO_PAUSED;
1391                break;
1392
1393        case AUDIO_CONTINUE:
1394                if (av7110->audiostate.play_state == AUDIO_PAUSED) {
1395                        av7110->audiostate.play_state = AUDIO_PLAYING;
1396                        ret = audcom(av7110, AUDIO_CMD_UNMUTE | AUDIO_CMD_PCM16);
1397                }
1398                break;
1399
1400        case AUDIO_SELECT_SOURCE:
1401                av7110->audiostate.stream_source = (audio_stream_source_t) arg;
1402                break;
1403
1404        case AUDIO_SET_MUTE:
1405        {
1406                ret = audcom(av7110, arg ? AUDIO_CMD_MUTE : AUDIO_CMD_UNMUTE);
1407                if (!ret)
1408                        av7110->audiostate.mute_state = (int) arg;
1409                break;
1410        }
1411
1412        case AUDIO_SET_AV_SYNC:
1413                av7110->audiostate.AV_sync_state = (int) arg;
1414                ret = audcom(av7110, arg ? AUDIO_CMD_SYNC_ON : AUDIO_CMD_SYNC_OFF);
1415                break;
1416
1417        case AUDIO_SET_BYPASS_MODE:
1418                if (FW_VERSION(av7110->arm_app) < 0x2621)
1419                        ret = -EINVAL;
1420                av7110->audiostate.bypass_mode = (int)arg;
1421                break;
1422
1423        case AUDIO_CHANNEL_SELECT:
1424                av7110->audiostate.channel_select = (audio_channel_select_t) arg;
1425                switch(av7110->audiostate.channel_select) {
1426                case AUDIO_STEREO:
1427                        ret = audcom(av7110, AUDIO_CMD_STEREO);
1428                        if (!ret) {
1429                                if (av7110->adac_type == DVB_ADAC_CRYSTAL)
1430                                        i2c_writereg(av7110, 0x20, 0x02, 0x49);
1431                                else if (av7110->adac_type == DVB_ADAC_MSP34x5)
1432                                        msp_writereg(av7110, MSP_WR_DSP, 0x0008, 0x0220);
1433                        }
1434                        break;
1435                case AUDIO_MONO_LEFT:
1436                        ret = audcom(av7110, AUDIO_CMD_MONO_L);
1437                        if (!ret) {
1438                                if (av7110->adac_type == DVB_ADAC_CRYSTAL)
1439                                        i2c_writereg(av7110, 0x20, 0x02, 0x4a);
1440                                else if (av7110->adac_type == DVB_ADAC_MSP34x5)
1441                                        msp_writereg(av7110, MSP_WR_DSP, 0x0008, 0x0200);
1442                        }
1443                        break;
1444                case AUDIO_MONO_RIGHT:
1445                        ret = audcom(av7110, AUDIO_CMD_MONO_R);
1446                        if (!ret) {
1447                                if (av7110->adac_type == DVB_ADAC_CRYSTAL)
1448                                        i2c_writereg(av7110, 0x20, 0x02, 0x45);
1449                                else if (av7110->adac_type == DVB_ADAC_MSP34x5)
1450                                        msp_writereg(av7110, MSP_WR_DSP, 0x0008, 0x0210);
1451                        }
1452                        break;
1453                default:
1454                        ret = -EINVAL;
1455                        break;
1456                }
1457                break;
1458
1459        case AUDIO_GET_STATUS:
1460                memcpy(parg, &av7110->audiostate, sizeof(struct audio_status));
1461                break;
1462
1463        case AUDIO_GET_CAPABILITIES:
1464                if (FW_VERSION(av7110->arm_app) < 0x2621)
1465                        *(unsigned int *)parg = AUDIO_CAP_LPCM | AUDIO_CAP_MP1 | AUDIO_CAP_MP2;
1466                else
1467                        *(unsigned int *)parg = AUDIO_CAP_LPCM | AUDIO_CAP_DTS | AUDIO_CAP_AC3 |
1468                                                AUDIO_CAP_MP1 | AUDIO_CAP_MP2;
1469                break;
1470
1471        case AUDIO_CLEAR_BUFFER:
1472                dvb_ringbuffer_flush_spinlock_wakeup(&av7110->aout);
1473                av7110_ipack_reset(&av7110->ipack[0]);
1474                if (av7110->playing == RP_AV)
1475                        ret = av7110_fw_cmd(av7110, COMTYPE_REC_PLAY,
1476                                            __Play, 2, AV_PES, 0);
1477                break;
1478
1479        case AUDIO_SET_ID:
1480                break;
1481
1482        case AUDIO_SET_MIXER:
1483        {
1484                struct audio_mixer *amix = (struct audio_mixer *)parg;
1485                ret = av7110_set_volume(av7110, amix->volume_left, amix->volume_right);
1486                break;
1487        }
1488
1489        case AUDIO_SET_STREAMTYPE:
1490                break;
1491
1492        default:
1493                ret = -ENOIOCTLCMD;
1494        }
1495
1496        mutex_unlock(&av7110->ioctl_mutex);
1497        return ret;
1498}
1499
1500
1501static int dvb_video_open(struct inode *inode, struct file *file)
1502{
1503        struct dvb_device *dvbdev = file->private_data;
1504        struct av7110 *av7110 = dvbdev->priv;
1505        int err;
1506
1507        dprintk(2, "av7110:%p, \n", av7110);
1508
1509        if ((err = dvb_generic_open(inode, file)) < 0)
1510                return err;
1511
1512        if ((file->f_flags & O_ACCMODE) != O_RDONLY) {
1513                dvb_ringbuffer_flush_spinlock_wakeup(&av7110->aout);
1514                dvb_ringbuffer_flush_spinlock_wakeup(&av7110->avout);
1515                av7110->video_blank = 1;
1516                av7110->audiostate.AV_sync_state = 1;
1517                av7110->videostate.stream_source = VIDEO_SOURCE_DEMUX;
1518
1519                /*  empty event queue */
1520                av7110->video_events.eventr = av7110->video_events.eventw = 0;
1521        }
1522
1523        return 0;
1524}
1525
1526static int dvb_video_release(struct inode *inode, struct file *file)
1527{
1528        struct dvb_device *dvbdev = file->private_data;
1529        struct av7110 *av7110 = dvbdev->priv;
1530
1531        dprintk(2, "av7110:%p, \n", av7110);
1532
1533        if ((file->f_flags & O_ACCMODE) != O_RDONLY) {
1534                av7110_av_stop(av7110, RP_VIDEO);
1535        }
1536
1537        return dvb_generic_release(inode, file);
1538}
1539
1540static int dvb_audio_open(struct inode *inode, struct file *file)
1541{
1542        struct dvb_device *dvbdev = file->private_data;
1543        struct av7110 *av7110 = dvbdev->priv;
1544        int err = dvb_generic_open(inode, file);
1545
1546        dprintk(2, "av7110:%p, \n", av7110);
1547
1548        if (err < 0)
1549                return err;
1550        dvb_ringbuffer_flush_spinlock_wakeup(&av7110->aout);
1551        av7110->audiostate.stream_source = AUDIO_SOURCE_DEMUX;
1552        return 0;
1553}
1554
1555static int dvb_audio_release(struct inode *inode, struct file *file)
1556{
1557        struct dvb_device *dvbdev = file->private_data;
1558        struct av7110 *av7110 = dvbdev->priv;
1559
1560        dprintk(2, "av7110:%p, \n", av7110);
1561
1562        av7110_av_stop(av7110, RP_AUDIO);
1563        return dvb_generic_release(inode, file);
1564}
1565
1566
1567
1568/******************************************************************************
1569 * driver registration
1570 ******************************************************************************/
1571
1572static const struct file_operations dvb_video_fops = {
1573        .owner          = THIS_MODULE,
1574        .write          = dvb_video_write,
1575        .unlocked_ioctl = dvb_generic_ioctl,
1576        .compat_ioctl   = dvb_generic_ioctl,
1577        .open           = dvb_video_open,
1578        .release        = dvb_video_release,
1579        .poll           = dvb_video_poll,
1580        .llseek         = noop_llseek,
1581};
1582
1583static struct dvb_device dvbdev_video = {
1584        .priv           = NULL,
1585        .users          = 6,
1586        .readers        = 5,    /* arbitrary */
1587        .writers        = 1,
1588        .fops           = &dvb_video_fops,
1589        .kernel_ioctl   = dvb_video_ioctl,
1590};
1591
1592static const struct file_operations dvb_audio_fops = {
1593        .owner          = THIS_MODULE,
1594        .write          = dvb_audio_write,
1595        .unlocked_ioctl = dvb_generic_ioctl,
1596        .compat_ioctl   = dvb_generic_ioctl,
1597        .open           = dvb_audio_open,
1598        .release        = dvb_audio_release,
1599        .poll           = dvb_audio_poll,
1600        .llseek         = noop_llseek,
1601};
1602
1603static struct dvb_device dvbdev_audio = {
1604        .priv           = NULL,
1605        .users          = 1,
1606        .writers        = 1,
1607        .fops           = &dvb_audio_fops,
1608        .kernel_ioctl   = dvb_audio_ioctl,
1609};
1610
1611
1612int av7110_av_register(struct av7110 *av7110)
1613{
1614        av7110->audiostate.AV_sync_state = 0;
1615        av7110->audiostate.mute_state = 0;
1616        av7110->audiostate.play_state = AUDIO_STOPPED;
1617        av7110->audiostate.stream_source = AUDIO_SOURCE_DEMUX;
1618        av7110->audiostate.channel_select = AUDIO_STEREO;
1619        av7110->audiostate.bypass_mode = 0;
1620
1621        av7110->videostate.video_blank = 0;
1622        av7110->videostate.play_state = VIDEO_STOPPED;
1623        av7110->videostate.stream_source = VIDEO_SOURCE_DEMUX;
1624        av7110->videostate.video_format = VIDEO_FORMAT_4_3;
1625        av7110->videostate.display_format = VIDEO_LETTER_BOX;
1626        av7110->display_ar = VIDEO_FORMAT_4_3;
1627        av7110->display_panscan = VID_VC_AND_PS_PREF;
1628
1629        init_waitqueue_head(&av7110->video_events.wait_queue);
1630        spin_lock_init(&av7110->video_events.lock);
1631        av7110->video_events.eventw = av7110->video_events.eventr = 0;
1632        av7110->video_events.overflow = 0;
1633        memset(&av7110->video_size, 0, sizeof (video_size_t));
1634
1635        dvb_register_device(&av7110->dvb_adapter, &av7110->video_dev,
1636                            &dvbdev_video, av7110, DVB_DEVICE_VIDEO, 0);
1637
1638        dvb_register_device(&av7110->dvb_adapter, &av7110->audio_dev,
1639                            &dvbdev_audio, av7110, DVB_DEVICE_AUDIO, 0);
1640
1641        return 0;
1642}
1643
1644void av7110_av_unregister(struct av7110 *av7110)
1645{
1646        dvb_unregister_device(av7110->audio_dev);
1647        dvb_unregister_device(av7110->video_dev);
1648}
1649
1650int av7110_av_init(struct av7110 *av7110)
1651{
1652        void (*play[])(u8 *, int, void *) = { play_audio_cb, play_video_cb };
1653        int i, ret;
1654
1655        for (i = 0; i < 2; i++) {
1656                struct ipack *ipack = av7110->ipack + i;
1657
1658                ret = av7110_ipack_init(ipack, IPACKS, play[i]);
1659                if (ret < 0) {
1660                        if (i)
1661                                av7110_ipack_free(--ipack);
1662                        goto out;
1663                }
1664                ipack->data = av7110;
1665        }
1666
1667        dvb_ringbuffer_init(&av7110->avout, av7110->iobuf, AVOUTLEN);
1668        dvb_ringbuffer_init(&av7110->aout, av7110->iobuf + AVOUTLEN, AOUTLEN);
1669
1670        av7110->kbuf[0] = (u8 *)(av7110->iobuf + AVOUTLEN + AOUTLEN + BMPLEN);
1671        av7110->kbuf[1] = av7110->kbuf[0] + 2 * IPACKS;
1672out:
1673        return ret;
1674}
1675
1676void av7110_av_exit(struct av7110 *av7110)
1677{
1678        av7110_ipack_free(&av7110->ipack[0]);
1679        av7110_ipack_free(&av7110->ipack[1]);
1680}
1681