Home | History | Annotate | Line # | Download | only in bktr
bktr_core.c revision 1.15
      1 /*	$NetBSD: bktr_core.c,v 1.15 2001/01/18 20:28:24 jdolecek Exp $	*/
      2 
      3 /* FreeBSD: src/sys/dev/bktr/bktr_core.c,v 1.114 2000/10/31 13:09:56 roger Exp */
      4 
      5 /*
      6  * This is part of the Driver for Video Capture Cards (Frame grabbers)
      7  * and TV Tuner cards using the Brooktree Bt848, Bt848A, Bt849A, Bt878, Bt879
      8  * chipset.
      9  * Copyright Roger Hardiman and Amancio Hasty.
     10  *
     11  * bktr_core : This deals with the Bt848/849/878/879 PCI Frame Grabber,
     12  *               Handles all the open, close, ioctl and read userland calls.
     13  *               Sets the Bt848 registers and generates RISC pograms.
     14  *               Controls the i2c bus and GPIO interface.
     15  *               Contains the interface to the kernel.
     16  *               (eg probe/attach and open/close/ioctl)
     17  *
     18  */
     19 
     20  /*
     21    The Brooktree BT848 Driver driver is based upon Mark Tinguely and
     22    Jim Lowe's driver for the Matrox Meteor PCI card . The
     23    Philips SAA 7116 and SAA 7196 are very different chipsets than
     24    the BT848.
     25 
     26    The original copyright notice by Mark and Jim is included mostly
     27    to honor their fantastic work in the Matrox Meteor driver!
     28 
     29  */
     30 
     31 /*
     32  * 1. Redistributions of source code must retain the
     33  * Copyright (c) 1997 Amancio Hasty, 1999 Roger Hardiman
     34  * All rights reserved.
     35  *
     36  * Redistribution and use in source and binary forms, with or without
     37  * modification, are permitted provided that the following conditions
     38  * are met:
     39  * 1. Redistributions of source code must retain the above copyright
     40  *    notice, this list of conditions and the following disclaimer.
     41  * 2. Redistributions in binary form must reproduce the above copyright
     42  *    notice, this list of conditions and the following disclaimer in the
     43  *    documentation and/or other materials provided with the distribution.
     44  * 3. All advertising materials mentioning features or use of this software
     45  *    must display the following acknowledgement:
     46  *	This product includes software developed by Amancio Hasty and
     47  *      Roger Hardiman
     48  * 4. The name of the author may not be used to endorse or promote products
     49  *    derived from this software without specific prior written permission.
     50  *
     51  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
     52  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
     53  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
     54  * DISCLAIMED.	IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
     55  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
     56  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
     57  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
     58  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
     59  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
     60  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
     61  * POSSIBILITY OF SUCH DAMAGE.
     62  */
     63 
     64 
     65 
     66 
     67 /*
     68  * 1. Redistributions of source code must retain the
     69  * Copyright (c) 1995 Mark Tinguely and Jim Lowe
     70  * All rights reserved.
     71  *
     72  * Redistribution and use in source and binary forms, with or without
     73  * modification, are permitted provided that the following conditions
     74  * are met:
     75  * 1. Redistributions of source code must retain the above copyright
     76  *    notice, this list of conditions and the following disclaimer.
     77  * 2. Redistributions in binary form must reproduce the above copyright
     78  *    notice, this list of conditions and the following disclaimer in the
     79  *    documentation and/or other materials provided with the distribution.
     80  * 3. All advertising materials mentioning features or use of this software
     81  *    must display the following acknowledgement:
     82  *	This product includes software developed by Mark Tinguely and Jim Lowe
     83  * 4. The name of the author may not be used to endorse or promote products
     84  *    derived from this software without specific prior written permission.
     85  *
     86  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
     87  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
     88  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
     89  * DISCLAIMED.	IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
     90  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
     91  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
     92  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
     93  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
     94  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
     95  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
     96  * POSSIBILITY OF SUCH DAMAGE.
     97  */
     98 
     99 #include "opt_bktr.h"		/* Include any kernel config options */
    100 
    101 #ifdef __FreeBSD__
    102 #include "bktr.h"
    103 #endif /* __FreeBSD__ */
    104 
    105 #if (                                                            \
    106        (defined(__FreeBSD__) && (NBKTR > 0))                     \
    107     || (defined(__bsdi__))                                       \
    108     || (defined(__OpenBSD__))                                    \
    109     || (defined(__NetBSD__))                                     \
    110     )
    111 
    112 
    113 /*******************/
    114 /* *** FreeBSD *** */
    115 /*******************/
    116 #ifdef __FreeBSD__
    117 
    118 #include <sys/param.h>
    119 #include <sys/systm.h>
    120 #include <sys/kernel.h>
    121 #include <sys/signalvar.h>
    122 #include <sys/vnode.h>
    123 
    124 #include <vm/vm.h>
    125 #include <vm/vm_kern.h>
    126 #include <vm/pmap.h>
    127 #include <vm/vm_extern.h>
    128 
    129 #if (__FreeBSD_version >=400000) || (NSMBUS > 0)
    130 #include <sys/bus.h>		/* used by smbus and newbus */
    131 #endif
    132 
    133 #if (__FreeBSD_version < 500000)
    134 #include <machine/clock.h>              /* for DELAY */
    135 #endif
    136 
    137 #include <pci/pcivar.h>
    138 
    139 #if (__FreeBSD_version >=300000)
    140 #include <machine/bus_memio.h>	/* for bus space */
    141 #include <machine/bus.h>
    142 #include <sys/bus.h>
    143 #endif
    144 
    145 #include <machine/ioctl_meteor.h>
    146 #include <machine/ioctl_bt848.h>	/* extensions to ioctl_meteor.h */
    147 #include <dev/bktr/bktr_reg.h>
    148 #include <dev/bktr/bktr_tuner.h>
    149 #include <dev/bktr/bktr_card.h>
    150 #include <dev/bktr/bktr_audio.h>
    151 #include <dev/bktr/bktr_os.h>
    152 #include <dev/bktr/bktr_core.h>
    153 #if defined(BKTR_FREEBSD_MODULE)
    154 #include <dev/bktr/bktr_mem.h>
    155 #endif
    156 
    157 #if defined(BKTR_USE_FREEBSD_SMBUS)
    158 #include <dev/bktr/bktr_i2c.h>
    159 #include <dev/smbus/smbconf.h>
    160 #include <dev/iicbus/iiconf.h>
    161 #include "smbus_if.h"
    162 #include "iicbus_if.h"
    163 #endif
    164 
    165 const char *
    166 bktr_name(bktr_ptr_t bktr)
    167 {
    168   return bktr->bktr_xname;
    169 }
    170 
    171 
    172 #if (__FreeBSD__ == 2)
    173 typedef unsigned int uintptr_t;
    174 #endif
    175 #endif  /* __FreeBSD__ */
    176 
    177 
    178 /****************/
    179 /* *** BSDI *** */
    180 /****************/
    181 #ifdef __bsdi__
    182 #endif /* __bsdi__ */
    183 
    184 
    185 /**************************/
    186 /* *** OpenBSD/NetBSD *** */
    187 /**************************/
    188 #if defined(__NetBSD__) || defined(__OpenBSD__)
    189 
    190 #include <sys/param.h>
    191 #include <sys/systm.h>
    192 #include <sys/kernel.h>
    193 #include <sys/signalvar.h>
    194 #include <sys/vnode.h>
    195 
    196 #ifdef __NetBSD__
    197 #include <uvm/uvm_extern.h>
    198 #include <dev/pci/pcidevs.h>
    199 #include <dev/pci/pcireg.h>
    200 #else
    201 #include <vm/vm.h>
    202 #include <vm/vm_kern.h>
    203 #include <vm/pmap.h>
    204 #include <vm/vm_extern.h>
    205 #endif
    206 
    207 #include <sys/inttypes.h>		/* uintptr_t */
    208 #include <dev/ic/bt8xx.h>
    209 #include <dev/pci/bktr/bktr_reg.h>
    210 #include <dev/pci/bktr/bktr_tuner.h>
    211 #include <dev/pci/bktr/bktr_card.h>
    212 #include <dev/pci/bktr/bktr_audio.h>
    213 #include <dev/pci/bktr/bktr_core.h>
    214 #include <dev/pci/bktr/bktr_os.h>
    215 
    216 static int bt848_format = -1;
    217 
    218 const char *
    219 bktr_name(bktr_ptr_t bktr)
    220 {
    221         return (bktr->bktr_dev.dv_xname);
    222 }
    223 
    224 #endif /* __NetBSD__ || __OpenBSD__ */
    225 
    226 
    227 
    228 typedef u_char bool_t;
    229 
    230 #define BKTRPRI (PZERO+8)|PCATCH
    231 #define VBIPRI  (PZERO-4)|PCATCH
    232 
    233 
    234 /*
    235  * memory allocated for DMA programs
    236  */
    237 #define DMA_PROG_ALLOC		(8 * PAGE_SIZE)
    238 
    239 /* When to split a dma transfer , the bt848 has timing as well as
    240    dma transfer size limitations so that we have to split dma
    241    transfers into two dma requests
    242    */
    243 #define DMA_BT848_SPLIT 319*2
    244 
    245 /*
    246  * Allocate enough memory for:
    247  *	768x576 RGB 16 or YUV (16 storage bits/pixel) = 884736 = 216 pages
    248  *
    249  * You may override this using the options "BROOKTREE_ALLOC_PAGES=value"
    250  * in your  kernel configuration file.
    251  */
    252 
    253 #ifndef BROOKTREE_ALLOC_PAGES
    254 #define BROOKTREE_ALLOC_PAGES	217*4
    255 #endif
    256 #define BROOKTREE_ALLOC		(BROOKTREE_ALLOC_PAGES * PAGE_SIZE)
    257 
    258 /* Definitions for VBI capture.
    259  * There are 16 VBI lines in a PAL video field (32 in a frame),
    260  * and we take 2044 samples from each line (placed in a 2048 byte buffer
    261  * for alignment).
    262  * VBI lines are held in a circular buffer before being read by a
    263  * user program from /dev/vbi.
    264  */
    265 
    266 #define MAX_VBI_LINES	      16   /* Maximum for all vidoe formats */
    267 #define VBI_LINE_SIZE         2048 /* Store upto 2048 bytes per line */
    268 #define VBI_BUFFER_ITEMS      20   /* Number of frames we buffer */
    269 #define VBI_DATA_SIZE         (VBI_LINE_SIZE * MAX_VBI_LINES * 2)
    270 #define VBI_BUFFER_SIZE       (VBI_DATA_SIZE * VBI_BUFFER_ITEMS)
    271 
    272 
    273 /*  Defines for fields  */
    274 #define ODD_F  0x01
    275 #define EVEN_F 0x02
    276 
    277 
    278 /*
    279  * Parameters describing size of transmitted image.
    280  */
    281 
    282 static const struct format_params format_params[] = {
    283 /* # define BT848_IFORM_F_AUTO             (0x0) - don't matter. */
    284   { 525, 26, 480,  910, 135, 754, 640,  780, 30, 0x68, 0x5d, BT848_IFORM_X_AUTO,
    285     12,  1600 },
    286 /* # define BT848_IFORM_F_NTSCM            (0x1) */
    287   { 525, 26, 480,  910, 135, 754, 640,  780, 30, 0x68, 0x5d, BT848_IFORM_X_XT0,
    288     12, 1600 },
    289 /* # define BT848_IFORM_F_NTSCJ            (0x2) */
    290   { 525, 22, 480,  910, 135, 754, 640,  780, 30, 0x68, 0x5d, BT848_IFORM_X_XT0,
    291     12, 1600 },
    292 /* # define BT848_IFORM_F_PALBDGHI         (0x3) */
    293   { 625, 32, 576, 1135, 186, 924, 768,  944, 25, 0x7f, 0x72, BT848_IFORM_X_XT1,
    294     16,  2044 },
    295 /* # define BT848_IFORM_F_PALM             (0x4) */
    296   { 525, 22, 480,  910, 135, 754, 640,  780, 30, 0x68, 0x5d, BT848_IFORM_X_XT0,
    297     12, 1600 },
    298 /* # define BT848_IFORM_F_PALN             (0x5) */
    299   { 625, 32, 576, 1135, 186, 924, 768,  944, 25, 0x7f, 0x72, BT848_IFORM_X_XT1,
    300     16, 2044 },
    301 /* # define BT848_IFORM_F_SECAM            (0x6) */
    302   { 625, 32, 576, 1135, 186, 924, 768,  944, 25, 0x7f, 0xa0, BT848_IFORM_X_XT1,
    303     16, 2044 },
    304 /* # define BT848_IFORM_F_RSVD             (0x7) - ???? */
    305   { 625, 32, 576, 1135, 186, 924, 768,  944, 25, 0x7f, 0x72, BT848_IFORM_X_XT0,
    306     16, 2044 },
    307 };
    308 
    309 /*
    310  * Table of supported Pixel Formats
    311  */
    312 
    313 static const struct meteor_pixfmt_internal {
    314 	struct meteor_pixfmt public;
    315 	u_int                color_fmt;
    316 } pixfmt_table[] = {
    317 
    318 { { 0, METEOR_PIXTYPE_RGB, 2, {   0x7c00,  0x03e0,  0x001f }, 0,0 }, 0x33 },
    319 { { 0, METEOR_PIXTYPE_RGB, 2, {   0x7c00,  0x03e0,  0x001f }, 1,0 }, 0x33 },
    320 
    321 { { 0, METEOR_PIXTYPE_RGB, 2, {   0xf800,  0x07e0,  0x001f }, 0,0 }, 0x22 },
    322 { { 0, METEOR_PIXTYPE_RGB, 2, {   0xf800,  0x07e0,  0x001f }, 1,0 }, 0x22 },
    323 
    324 { { 0, METEOR_PIXTYPE_RGB, 3, { 0xff0000,0x00ff00,0x0000ff }, 1,0 }, 0x11 },
    325 
    326 { { 0, METEOR_PIXTYPE_RGB, 4, { 0xff0000,0x00ff00,0x0000ff }, 0,0 }, 0x00 },
    327 { { 0, METEOR_PIXTYPE_RGB, 4, { 0xff0000,0x00ff00,0x0000ff }, 0,1 }, 0x00 },
    328 { { 0, METEOR_PIXTYPE_RGB, 4, { 0xff0000,0x00ff00,0x0000ff }, 1,0 }, 0x00 },
    329 { { 0, METEOR_PIXTYPE_RGB, 4, { 0xff0000,0x00ff00,0x0000ff }, 1,1 }, 0x00 },
    330 { { 0, METEOR_PIXTYPE_YUV, 2, { 0xff0000,0x00ff00,0x0000ff }, 1,1 }, 0x88 },
    331 { { 0, METEOR_PIXTYPE_YUV_PACKED, 2, { 0xff0000,0x00ff00,0x0000ff }, 0,1 }, 0x44 },
    332 { { 0, METEOR_PIXTYPE_YUV_12, 2, { 0xff0000,0x00ff00,0x0000ff }, 1,1 }, 0x88 },
    333 
    334 };
    335 #define PIXFMT_TABLE_SIZE ( sizeof(pixfmt_table) / sizeof(pixfmt_table[0]) )
    336 
    337 /*
    338  * Table of Meteor-supported Pixel Formats (for SETGEO compatibility)
    339  */
    340 
    341 /*  FIXME:  Also add YUV_422 and YUV_PACKED as well  */
    342 static const struct {
    343 	u_long               meteor_format;
    344 	struct meteor_pixfmt public;
    345 } meteor_pixfmt_table[] = {
    346     { METEOR_GEO_YUV_12,
    347       { 0, METEOR_PIXTYPE_YUV_12, 2, { 0xff0000,0x00ff00,0x0000ff }, 1,1 }
    348     },
    349 
    350       /* FIXME: Should byte swap flag be on for this one; negative in drvr? */
    351     { METEOR_GEO_YUV_422,
    352       { 0, METEOR_PIXTYPE_YUV, 2, { 0xff0000,0x00ff00,0x0000ff }, 1,1 }
    353     },
    354     { METEOR_GEO_YUV_PACKED,
    355       { 0, METEOR_PIXTYPE_YUV_PACKED, 2, { 0xff0000,0x00ff00,0x0000ff }, 0,1 }
    356     },
    357     { METEOR_GEO_RGB16,
    358       { 0, METEOR_PIXTYPE_RGB, 2, {   0x7c00,   0x03e0,   0x001f }, 0, 0 }
    359     },
    360     { METEOR_GEO_RGB24,
    361       { 0, METEOR_PIXTYPE_RGB, 4, { 0xff0000, 0x00ff00, 0x0000ff }, 0, 0 }
    362     },
    363 
    364 };
    365 #define METEOR_PIXFMT_TABLE_SIZE ( sizeof(meteor_pixfmt_table) / \
    366 				   sizeof(meteor_pixfmt_table[0]) )
    367 
    368 
    369 #define BSWAP (BT848_COLOR_CTL_BSWAP_ODD | BT848_COLOR_CTL_BSWAP_EVEN)
    370 #define WSWAP (BT848_COLOR_CTL_WSWAP_ODD | BT848_COLOR_CTL_WSWAP_EVEN)
    371 
    372 
    373 
    374 /* sync detect threshold */
    375 #if 0
    376 #define SYNC_LEVEL		(BT848_ADC_RESERVED |	\
    377 				 BT848_ADC_CRUSH)	/* threshold ~125 mV */
    378 #else
    379 #define SYNC_LEVEL		(BT848_ADC_RESERVED |	\
    380 				 BT848_ADC_SYNC_T)	/* threshold ~75 mV */
    381 #endif
    382 
    383 
    384 
    385 
    386 /* debug utility for holding previous INT_STAT contents */
    387 #define STATUS_SUM
    388 static u_long	status_sum = 0;
    389 
    390 /*
    391  * defines to make certain bit-fiddles understandable
    392  */
    393 #define FIFO_ENABLED		BT848_DMA_CTL_FIFO_EN
    394 #define RISC_ENABLED		BT848_DMA_CTL_RISC_EN
    395 #define FIFO_RISC_ENABLED	(BT848_DMA_CTL_FIFO_EN | BT848_DMA_CTL_RISC_EN)
    396 #define FIFO_RISC_DISABLED	0
    397 
    398 #define ALL_INTS_DISABLED	0
    399 #define ALL_INTS_CLEARED	0xffffffff
    400 #define CAPTURE_OFF		0
    401 
    402 #define BIT_SEVEN_HIGH		(1<<7)
    403 #define BIT_EIGHT_HIGH		(1<<8)
    404 
    405 #define I2C_BITS		(BT848_INT_RACK | BT848_INT_I2CDONE)
    406 #define TDEC_BITS               (BT848_INT_FDSR | BT848_INT_FBUS)
    407 
    408 
    409 
    410 static int		oformat_meteor_to_bt( u_long format );
    411 
    412 static u_int		pixfmt_swap_flags( int pixfmt );
    413 
    414 /*
    415  * bt848 RISC programming routines.
    416  */
    417 #ifdef BT848_DUMP
    418 static int	dump_bt848( bktr_ptr_t bktr );
    419 #endif
    420 
    421 static void	yuvpack_prog( bktr_ptr_t bktr, char i_flag, int cols,
    422 			      int rows,  int interlace );
    423 static void	yuv422_prog( bktr_ptr_t bktr, char i_flag, int cols,
    424 			     int rows, int interlace );
    425 static void	yuv12_prog( bktr_ptr_t bktr, char i_flag, int cols,
    426 			     int rows, int interlace );
    427 static void	rgb_prog( bktr_ptr_t bktr, char i_flag, int cols,
    428 			  int rows, int interlace );
    429 static void	rgb_vbi_prog( bktr_ptr_t bktr, char i_flag, int cols,
    430 			  int rows, int interlace );
    431 static void	build_dma_prog( bktr_ptr_t bktr, char i_flag );
    432 
    433 static bool_t   getline(bktr_reg_t *, int);
    434 static bool_t   notclipped(bktr_reg_t * , int , int);
    435 static bool_t   split(bktr_reg_t *, volatile u_long **, int, u_long, int,
    436 		      volatile u_char ** , int  );
    437 
    438 static void	start_capture( bktr_ptr_t bktr, unsigned type );
    439 static void	set_fps( bktr_ptr_t bktr, u_short fps );
    440 
    441 
    442 
    443 /*
    444  * Remote Control Functions
    445  */
    446 static void	remote_read(bktr_ptr_t bktr, struct bktr_remote *remote);
    447 
    448 
    449 /*
    450  * ioctls common to both video & tuner.
    451  */
    452 static int	common_ioctl( bktr_ptr_t bktr, ioctl_cmd_t cmd, caddr_t arg );
    453 
    454 
    455 #if !defined(BKTR_USE_FREEBSD_SMBUS)
    456 /*
    457  * i2c primitives for low level control of i2c bus. Added for MSP34xx control
    458  */
    459 static void     i2c_start( bktr_ptr_t bktr);
    460 static void     i2c_stop( bktr_ptr_t bktr);
    461 static int      i2c_write_byte( bktr_ptr_t bktr, unsigned char data);
    462 static int      i2c_read_byte( bktr_ptr_t bktr, unsigned char *data, int last );
    463 #endif
    464 
    465 
    466 
    467 /*
    468  * the common attach code, used by all OS versions.
    469  */
    470 void
    471 common_bktr_attach( bktr_ptr_t bktr, int unit, u_long pci_id, u_int rev )
    472 {
    473 #if defined(__NetBSD__)
    474 	vaddr_t		buf = 0;
    475 #else
    476 	vm_offset_t	buf = 0;
    477 #endif
    478 
    479 /***************************************/
    480 /* *** OS Specific memory routines *** */
    481 /***************************************/
    482 #if defined(__NetBSD__) || defined(__OpenBSD__)
    483         /* allocate space for dma program */
    484         bktr->dma_prog = get_bktr_mem(bktr, &bktr->dm_prog,
    485 				      DMA_PROG_ALLOC);
    486         bktr->odd_dma_prog = get_bktr_mem(bktr, &bktr->dm_oprog,
    487 					  DMA_PROG_ALLOC);
    488 
    489 	/* allocate space for the VBI buffer */
    490 	bktr->vbidata  = get_bktr_mem(bktr, &bktr->dm_vbidata,
    491 				      VBI_DATA_SIZE);
    492 	bktr->vbibuffer = get_bktr_mem(bktr, &bktr->dm_vbibuffer,
    493 				       VBI_BUFFER_SIZE);
    494 
    495         /* allocate space for pixel buffer */
    496         if ( BROOKTREE_ALLOC )
    497                 buf = get_bktr_mem(bktr, &bktr->dm_mem, BROOKTREE_ALLOC);
    498         else
    499                 buf = 0;
    500 #endif
    501 
    502 #if defined(__FreeBSD__) || defined(__bsdi__)
    503 	int		need_to_allocate_memory = 1;
    504 
    505 /* If this is a module, check if there is any currently saved contiguous memory */
    506 #if defined(BKTR_FREEBSD_MODULE)
    507 	if (bktr_has_stored_addresses(unit) == 1) {
    508 		/* recover the addresses */
    509 		bktr->dma_prog     = bktr_retrieve_address(unit, BKTR_MEM_DMA_PROG);
    510 		bktr->odd_dma_prog = bktr_retrieve_address(unit, BKTR_MEM_ODD_DMA_PROG);
    511 		bktr->vbidata      = bktr_retrieve_address(unit, BKTR_MEM_VBIDATA);
    512 		bktr->vbibuffer    = bktr_retrieve_address(unit, BKTR_MEM_VBIBUFFER);
    513 		buf                = bktr_retrieve_address(unit, BKTR_MEM_BUF);
    514 		need_to_allocate_memory = 0;
    515 	}
    516 #endif
    517 
    518 	if (need_to_allocate_memory == 1) {
    519 		/* allocate space for dma program */
    520 		bktr->dma_prog     = get_bktr_mem(unit, DMA_PROG_ALLOC);
    521 		bktr->odd_dma_prog = get_bktr_mem(unit, DMA_PROG_ALLOC);
    522 
    523 		/* allocte space for the VBI buffer */
    524 		bktr->vbidata  = get_bktr_mem(unit, VBI_DATA_SIZE);
    525 		bktr->vbibuffer = get_bktr_mem(unit, VBI_BUFFER_SIZE);
    526 
    527 		/* allocate space for pixel buffer */
    528 		if ( BROOKTREE_ALLOC )
    529 			buf = get_bktr_mem(unit, BROOKTREE_ALLOC);
    530 		else
    531 			buf = 0;
    532 	}
    533 #endif	/* FreeBSD or BSDi */
    534 
    535 
    536 /* If this is a module, save the current contiguous memory */
    537 #if defined(BKTR_FREEBSD_MODULE)
    538 bktr_store_address(unit, BKTR_MEM_DMA_PROG,     bktr->dma_prog);
    539 bktr_store_address(unit, BKTR_MEM_ODD_DMA_PROG, bktr->odd_dma_prog);
    540 bktr_store_address(unit, BKTR_MEM_VBIDATA,      bktr->vbidata);
    541 bktr_store_address(unit, BKTR_MEM_VBIBUFFER,    bktr->vbibuffer);
    542 bktr_store_address(unit, BKTR_MEM_BUF,          buf);
    543 #endif
    544 
    545 
    546 	if ( bootverbose ) {
    547 		printf("%s: buffer size %d, addr 0x%lx\n",
    548 			bktr_name(bktr), BROOKTREE_ALLOC,
    549 			(u_long) vtophys(buf));
    550 	}
    551 
    552 	if ( buf != 0 ) {
    553 		bktr->bigbuf = buf;
    554 		bktr->alloc_pages = BROOKTREE_ALLOC_PAGES;
    555 		bzero((caddr_t) bktr->bigbuf, BROOKTREE_ALLOC);
    556 	} else {
    557 		bktr->alloc_pages = 0;
    558 	}
    559 
    560 
    561 	bktr->flags = METEOR_INITALIZED | METEOR_AUTOMODE |
    562 		      METEOR_DEV0 | METEOR_RGB16;
    563 	bktr->dma_prog_loaded = FALSE;
    564 	bktr->cols = 640;
    565 	bktr->rows = 480;
    566 	bktr->frames = 1;		/* one frame */
    567 	bktr->format = METEOR_GEO_RGB16;
    568 	bktr->pixfmt = oformat_meteor_to_bt( bktr->format );
    569 	bktr->pixfmt_compat = TRUE;
    570 
    571 
    572 	bktr->vbiinsert = 0;
    573 	bktr->vbistart = 0;
    574 	bktr->vbisize = 0;
    575 	bktr->vbiflags = 0;
    576 
    577 
    578 	/* using the pci device id and revision id */
    579 	/* and determine the card type            */
    580 	if (PCI_VENDOR(pci_id) == PCI_VENDOR_BROOKTREE)
    581 	{
    582 		switch (PCI_PRODUCT(pci_id)) {
    583 		case PCI_PRODUCT_BROOKTREE_BT848:
    584 			if (rev == 0x12)
    585 				bktr->id = BROOKTREE_848A;
    586 			else
    587 				bktr->id = BROOKTREE_848;
    588 			break;
    589 		case PCI_PRODUCT_BROOKTREE_BT849:
    590 			bktr->id = BROOKTREE_849A;
    591 			break;
    592 		case PCI_PRODUCT_BROOKTREE_BT878:
    593 			bktr->id = BROOKTREE_878;
    594 			break;
    595 		case PCI_PRODUCT_BROOKTREE_BT879:
    596 			bktr->id = BROOKTREE_879;
    597 			break;
    598 		}
    599 	};
    600 
    601 	bktr->clr_on_start = FALSE;
    602 
    603 	/* defaults for the tuner section of the card */
    604 	bktr->tflags = TUNER_INITALIZED;
    605 	bktr->tuner.frequency = 0;
    606 	bktr->tuner.channel = 0;
    607 	bktr->tuner.chnlset = DEFAULT_CHNLSET;
    608 	bktr->tuner.afc = 0;
    609 	bktr->tuner.radio_mode = 0;
    610 	bktr->audio_mux_select = 0;
    611 	bktr->audio_mute_state = FALSE;
    612 	bktr->bt848_card = -1;
    613 	bktr->bt848_tuner = -1;
    614 	bktr->reverse_mute = -1;
    615 	bktr->slow_msp_audio = 0;
    616 	bktr->msp_use_mono_source = 0;
    617         bktr->msp_source_selected = -1;
    618 	bktr->audio_mux_present = 1;
    619 
    620 	probeCard( bktr, TRUE, unit );
    621 
    622 	/* Initialise any MSP34xx or TDA98xx audio chips */
    623 	init_audio_devices( bktr );
    624 
    625 }
    626 
    627 
    628 /* Copy the vbi lines from 'vbidata' into the circular buffer, 'vbibuffer'.
    629  * The circular buffer holds 'n' fixed size data blocks.
    630  * vbisize   is the number of bytes in the circular buffer
    631  * vbiread   is the point we reading data out of the circular buffer
    632  * vbiinsert is the point we insert data into the circular buffer
    633  */
    634 static void vbidecode(bktr_ptr_t bktr) {
    635         unsigned char *dest;
    636 	unsigned int *seq_dest;
    637 
    638 	/* Check if there is room in the buffer to insert the data. */
    639 	if (bktr->vbisize + VBI_DATA_SIZE > VBI_BUFFER_SIZE) return;
    640 
    641 	/* Copy the VBI data into the next free slot in the buffer. */
    642 	/* 'dest' is the point in vbibuffer where we want to insert new data */
    643         dest = (unsigned char *)bktr->vbibuffer + bktr->vbiinsert;
    644         memcpy(dest, (unsigned char*)bktr->vbidata, VBI_DATA_SIZE);
    645 
    646 	/* Write the VBI sequence number to the end of the vbi data */
    647 	/* This is used by the AleVT teletext program */
    648 	seq_dest = (unsigned int *)((unsigned char *)bktr->vbibuffer
    649 			+ bktr->vbiinsert
    650 			+ (VBI_DATA_SIZE - sizeof(bktr->vbi_sequence_number)));
    651 	*seq_dest = bktr->vbi_sequence_number;
    652 
    653 	/* And increase the VBI sequence number */
    654 	/* This can wrap around */
    655 	bktr->vbi_sequence_number++;
    656 
    657 
    658 	/* Increment the vbiinsert pointer */
    659 	/* This can wrap around */
    660 	bktr->vbiinsert += VBI_DATA_SIZE;
    661 	bktr->vbiinsert = (bktr->vbiinsert % VBI_BUFFER_SIZE);
    662 
    663 	/* And increase the amount of vbi data in the buffer */
    664 	bktr->vbisize = bktr->vbisize + VBI_DATA_SIZE;
    665 
    666 }
    667 
    668 
    669 /*
    670  * the common interrupt handler.
    671  * Returns a 0 or 1 depending on whether the interrupt has handled.
    672  * In the OS specific section, bktr_intr() is defined which calls this
    673  * common interrupt handler.
    674  */
    675 int
    676 common_bktr_intr( void *arg )
    677 {
    678 	bktr_ptr_t		bktr;
    679 	u_long			bktr_status;
    680 	u_char			dstatus;
    681 	u_long                  field;
    682 	u_long                  w_field;
    683 	u_long                  req_field;
    684 
    685 	bktr = (bktr_ptr_t) arg;
    686 
    687 	/*
    688 	 * check to see if any interrupts are unmasked on this device.  If
    689 	 * none are, then we likely got here by way of being on a PCI shared
    690 	 * interrupt dispatch list.
    691 	 */
    692 	if (INL(bktr, BKTR_INT_MASK) == ALL_INTS_DISABLED)
    693 	  	return 0;	/* bail out now, before we do something we
    694 				   shouldn't */
    695 
    696 	if (!(bktr->flags & METEOR_OPEN)) {
    697 		OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_RISC_DISABLED);
    698 		OUTL(bktr, BKTR_INT_MASK, ALL_INTS_DISABLED);
    699 		/* return; ?? */
    700 	}
    701 
    702 	/* record and clear the INTerrupt status bits */
    703 	bktr_status = INL(bktr, BKTR_INT_STAT);
    704 	OUTL(bktr, BKTR_INT_STAT, bktr_status & ~I2C_BITS);	/* don't touch i2c */
    705 
    706 	/* record and clear the device status register */
    707 	dstatus = INB(bktr, BKTR_DSTATUS);
    708 	OUTB(bktr, BKTR_DSTATUS, 0x00);
    709 
    710 #if defined( STATUS_SUM )
    711 	/* add any new device status or INTerrupt status bits */
    712 	status_sum |= (bktr_status & ~(BT848_INT_RSV0|BT848_INT_RSV1));
    713 	status_sum |= ((dstatus & (BT848_DSTATUS_COF|BT848_DSTATUS_LOF)) << 6);
    714 #endif /* STATUS_SUM */
    715 	/* printf( "%s: STATUS %x %x %x \n", bktr_name(bktr),
    716 		dstatus, bktr_status, INL(bktr, BKTR_RISC_COUNT) );
    717 	*/
    718 
    719 
    720 	/* if risc was disabled re-start process again */
    721 	/* if there was one of the following errors re-start again */
    722 	if ( !(bktr_status & BT848_INT_RISC_EN) ||
    723 	     ((bktr_status &(/* BT848_INT_FBUS   | */
    724 			     /* BT848_INT_FTRGT  | */
    725 			     /* BT848_INT_FDSR   | */
    726 			      BT848_INT_PPERR  |
    727 			      BT848_INT_RIPERR | BT848_INT_PABORT |
    728 			      BT848_INT_OCERR  | BT848_INT_SCERR) ) != 0)
    729 		|| ((INB(bktr, BKTR_TDEC) == 0) && (bktr_status & TDEC_BITS)) ) {
    730 
    731 		u_short	tdec_save = INB(bktr, BKTR_TDEC);
    732 
    733 		OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_RISC_DISABLED);
    734 		OUTB(bktr, BKTR_CAP_CTL, CAPTURE_OFF);
    735 
    736 		OUTL(bktr, BKTR_INT_MASK, ALL_INTS_DISABLED);
    737 
    738 		/*  Reset temporal decimation counter  */
    739 		OUTB(bktr, BKTR_TDEC, 0);
    740 		OUTB(bktr, BKTR_TDEC, tdec_save);
    741 
    742 		/*  Reset to no-fields captured state  */
    743 		if (bktr->flags & (METEOR_CONTIN | METEOR_SYNCAP)) {
    744 			switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
    745 			case METEOR_ONLY_ODD_FIELDS:
    746 				bktr->flags |= METEOR_WANT_ODD;
    747 				break;
    748 			case METEOR_ONLY_EVEN_FIELDS:
    749 				bktr->flags |= METEOR_WANT_EVEN;
    750 				break;
    751 			default:
    752 				bktr->flags |= METEOR_WANT_MASK;
    753 				break;
    754 			}
    755 		}
    756 
    757 		OUTL(bktr, BKTR_RISC_STRT_ADD, vtophys(bktr->dma_prog));
    758 		OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_ENABLED);
    759 		OUTW(bktr, BKTR_GPIO_DMA_CTL, bktr->capcontrol);
    760 
    761 		OUTL(bktr, BKTR_INT_MASK, BT848_INT_MYSTERYBIT |
    762 				    BT848_INT_RISCI      |
    763 				    BT848_INT_VSYNC      |
    764 				    BT848_INT_FMTCHG);
    765 
    766 		OUTB(bktr, BKTR_CAP_CTL, bktr->bktr_cap_ctl);
    767 		return 1;
    768 	}
    769 
    770 	/* If this is not a RISC program interrupt, return */
    771 	if (!(bktr_status & BT848_INT_RISCI))
    772 		return 0;
    773 
    774 /**
    775 	printf( "%s: intr status %x %x %x\n", bktr_name(bktr),
    776 		bktr_status, dstatus, INL(bktr, BKTR_RISC_COUNT) );
    777  */
    778 
    779 
    780 	/*
    781 	 * Disable future interrupts if a capture mode is not selected.
    782 	 * This can happen when we are in the process of closing or
    783 	 * changing capture modes, otherwise it shouldn't happen.
    784 	 */
    785 	if (!(bktr->flags & METEOR_CAP_MASK))
    786 		OUTB(bktr, BKTR_CAP_CTL, CAPTURE_OFF);
    787 
    788 
    789 	/* Determine which field generated this interrupt */
    790 	field = ( bktr_status & BT848_INT_FIELD ) ? EVEN_F : ODD_F;
    791 
    792 
    793 	/*
    794 	 * Process the VBI data if it is being captured. We do this once
    795 	 * both Odd and Even VBI data is captured. Therefore we do this
    796 	 * in the Even field interrupt handler.
    797 	 */
    798 	if (  (bktr->vbiflags & VBI_CAPTURE)
    799 	    &&(bktr->vbiflags & VBI_OPEN)
    800             &&(field==EVEN_F)) {
    801 		/* Put VBI data into circular buffer */
    802                	vbidecode(bktr);
    803 
    804 		/* If someone is blocked on reading from /dev/vbi, wake them */
    805 		if (bktr->vbi_read_blocked) {
    806 			bktr->vbi_read_blocked = FALSE;
    807           	     	wakeup(VBI_SLEEP);
    808 		}
    809 
    810 		/* If someone has a select() on /dev/vbi, inform them */
    811 		if (bktr->vbi_select.si_pid) {
    812 			selwakeup(&bktr->vbi_select);
    813 		}
    814 
    815 
    816 	}
    817 
    818 
    819 	/*
    820 	 *  Register the completed field
    821 	 *    (For dual-field mode, require fields from the same frame)
    822 	 */
    823 	switch ( bktr->flags & METEOR_WANT_MASK ) {
    824 		case METEOR_WANT_ODD  : w_field = ODD_F         ;  break;
    825 		case METEOR_WANT_EVEN : w_field = EVEN_F        ;  break;
    826 		default               : w_field = (ODD_F|EVEN_F);  break;
    827 	}
    828 	switch ( bktr->flags & METEOR_ONLY_FIELDS_MASK ) {
    829 		case METEOR_ONLY_ODD_FIELDS  : req_field = ODD_F  ;  break;
    830 		case METEOR_ONLY_EVEN_FIELDS : req_field = EVEN_F ;  break;
    831 		default                      : req_field = (ODD_F|EVEN_F);
    832 			                       break;
    833 	}
    834 
    835 	if (( field == EVEN_F ) && ( w_field == EVEN_F ))
    836 		bktr->flags &= ~METEOR_WANT_EVEN;
    837 	else if (( field == ODD_F ) && ( req_field == ODD_F ) &&
    838 		 ( w_field == ODD_F ))
    839 		bktr->flags &= ~METEOR_WANT_ODD;
    840 	else if (( field == ODD_F ) && ( req_field == (ODD_F|EVEN_F) ) &&
    841 		 ( w_field == (ODD_F|EVEN_F) ))
    842 		bktr->flags &= ~METEOR_WANT_ODD;
    843 	else if (( field == ODD_F ) && ( req_field == (ODD_F|EVEN_F) ) &&
    844 		 ( w_field == ODD_F )) {
    845 		bktr->flags &= ~METEOR_WANT_ODD;
    846 		bktr->flags |=  METEOR_WANT_EVEN;
    847 	}
    848 	else {
    849 		/*  We're out of sync.  Start over.  */
    850 		if (bktr->flags & (METEOR_CONTIN | METEOR_SYNCAP)) {
    851 			switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
    852 			case METEOR_ONLY_ODD_FIELDS:
    853 				bktr->flags |= METEOR_WANT_ODD;
    854 				break;
    855 			case METEOR_ONLY_EVEN_FIELDS:
    856 				bktr->flags |= METEOR_WANT_EVEN;
    857 				break;
    858 			default:
    859 				bktr->flags |= METEOR_WANT_MASK;
    860 				break;
    861 			}
    862 		}
    863 		return 1;
    864 	}
    865 
    866 	/*
    867 	 * If we have a complete frame.
    868 	 */
    869 	if (!(bktr->flags & METEOR_WANT_MASK)) {
    870 		bktr->frames_captured++;
    871 		/*
    872 		 * post the completion time.
    873 		 */
    874 		if (bktr->flags & METEOR_WANT_TS) {
    875 			struct timeval *ts;
    876 
    877 			if ((u_int) bktr->alloc_pages * PAGE_SIZE
    878 			   <= (bktr->frame_size + sizeof(struct timeval))) {
    879 				ts =(struct timeval *)bktr->bigbuf +
    880 				  bktr->frame_size;
    881 				/* doesn't work in synch mode except
    882 				 *  for first frame */
    883 				/* XXX */
    884 				microtime(ts);
    885 			}
    886 		}
    887 
    888 
    889 		/*
    890 		 * Wake up the user in single capture mode.
    891 		 */
    892 		if (bktr->flags & METEOR_SINGLE) {
    893 
    894 			/* stop dma */
    895 			OUTL(bktr, BKTR_INT_MASK, ALL_INTS_DISABLED);
    896 
    897 			/* disable risc, leave fifo running */
    898 			OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_ENABLED);
    899 			wakeup(BKTR_SLEEP);
    900 		}
    901 
    902 		/*
    903 		 * If the user requested to be notified via signal,
    904 		 * let them know the frame is complete.
    905 		 */
    906 
    907 		if (bktr->proc && !(bktr->signal & METEOR_SIG_MODE_MASK))
    908 			psignal( bktr->proc,
    909 				 bktr->signal&(~METEOR_SIG_MODE_MASK) );
    910 
    911 		/*
    912 		 * Reset the want flags if in continuous or
    913 		 * synchronous capture mode.
    914 		 */
    915 /*
    916 * XXX NOTE (Luigi):
    917 * currently we only support 3 capture modes: odd only, even only,
    918 * odd+even interlaced (odd field first). A fourth mode (non interlaced,
    919 * either even OR odd) could provide 60 (50 for PAL) pictures per
    920 * second, but it would require this routine to toggle the desired frame
    921 * each time, and one more different DMA program for the Bt848.
    922 * As a consequence, this fourth mode is currently unsupported.
    923 */
    924 
    925 		if (bktr->flags & (METEOR_CONTIN | METEOR_SYNCAP)) {
    926 			switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
    927 			case METEOR_ONLY_ODD_FIELDS:
    928 				bktr->flags |= METEOR_WANT_ODD;
    929 				break;
    930 			case METEOR_ONLY_EVEN_FIELDS:
    931 				bktr->flags |= METEOR_WANT_EVEN;
    932 				break;
    933 			default:
    934 				bktr->flags |= METEOR_WANT_MASK;
    935 				break;
    936 			}
    937 		}
    938 	}
    939 
    940 	return 1;
    941 }
    942 
    943 
    944 
    945 
    946 /*
    947  *
    948  */
    949 extern int bt848_format; /* used to set the default format, PAL or NTSC */
    950 int
    951 video_open( bktr_ptr_t bktr )
    952 {
    953 	int frame_rate, video_format=0;
    954 
    955 	if (bktr->flags & METEOR_OPEN)		/* device is busy */
    956 		return( EBUSY );
    957 
    958 	bktr->flags |= METEOR_OPEN;
    959 
    960 #ifdef BT848_DUMP
    961 	dump_bt848( bt848 );
    962 #endif
    963 
    964         bktr->clr_on_start = FALSE;
    965 
    966 	OUTB(bktr, BKTR_DSTATUS, 0x00);			/* clear device status reg. */
    967 
    968 	OUTB(bktr, BKTR_ADC, SYNC_LEVEL);
    969 
    970 #if BKTR_SYSTEM_DEFAULT == BROOKTREE_PAL
    971 	video_format = 0;
    972 #else
    973 	video_format = 1;
    974 #endif
    975 
    976 	if (bt848_format == 0 )
    977 	  video_format = 0;
    978 
    979 	if (bt848_format == 1 )
    980 	  video_format = 1;
    981 
    982 	if (video_format == 1 ) {
    983 	  OUTB(bktr, BKTR_IFORM, BT848_IFORM_F_NTSCM);
    984 	  bktr->format_params = BT848_IFORM_F_NTSCM;
    985 
    986 	} else {
    987 	  OUTB(bktr, BKTR_IFORM, BT848_IFORM_F_PALBDGHI);
    988 	  bktr->format_params = BT848_IFORM_F_PALBDGHI;
    989 
    990 	}
    991 
    992 	OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) | format_params[bktr->format_params].iform_xtsel);
    993 
    994 	/* work around for new Hauppauge 878 cards */
    995 	if ((bktr->card.card_id == CARD_HAUPPAUGE) &&
    996 	    (bktr->id==BROOKTREE_878 || bktr->id==BROOKTREE_879) )
    997 		OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) | BT848_IFORM_M_MUX3);
    998 	else
    999 		OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) | BT848_IFORM_M_MUX1);
   1000 
   1001 	OUTB(bktr, BKTR_ADELAY, format_params[bktr->format_params].adelay);
   1002 	OUTB(bktr, BKTR_BDELAY, format_params[bktr->format_params].bdelay);
   1003 	frame_rate    = format_params[bktr->format_params].frame_rate;
   1004 
   1005 	/* enable PLL mode using 28Mhz crystal for PAL/SECAM users */
   1006 	if (bktr->xtal_pll_mode == BT848_USE_PLL) {
   1007 		OUTB(bktr, BKTR_TGCTRL, 0);
   1008 		OUTB(bktr, BKTR_PLL_F_LO, 0xf9);
   1009 		OUTB(bktr, BKTR_PLL_F_HI, 0xdc);
   1010 		OUTB(bktr, BKTR_PLL_F_XCI, 0x8e);
   1011 	}
   1012 
   1013 	bktr->flags = (bktr->flags & ~METEOR_DEV_MASK) | METEOR_DEV0;
   1014 
   1015 	bktr->max_clip_node = 0;
   1016 
   1017 	OUTB(bktr, BKTR_COLOR_CTL, BT848_COLOR_CTL_GAMMA | BT848_COLOR_CTL_RGB_DED);
   1018 
   1019 	OUTB(bktr, BKTR_E_HSCALE_LO, 170);
   1020 	OUTB(bktr, BKTR_O_HSCALE_LO, 170);
   1021 
   1022 	OUTB(bktr, BKTR_E_DELAY_LO, 0x72);
   1023 	OUTB(bktr, BKTR_O_DELAY_LO, 0x72);
   1024 	OUTB(bktr, BKTR_E_SCLOOP, 0);
   1025 	OUTB(bktr, BKTR_O_SCLOOP, 0);
   1026 
   1027 	OUTB(bktr, BKTR_VBI_PACK_SIZE, 0);
   1028 	OUTB(bktr, BKTR_VBI_PACK_DEL, 0);
   1029 
   1030 	bktr->fifo_errors = 0;
   1031 	bktr->dma_errors = 0;
   1032 	bktr->frames_captured = 0;
   1033 	bktr->even_fields_captured = 0;
   1034 	bktr->odd_fields_captured = 0;
   1035 	bktr->proc = (struct proc *)0;
   1036 	set_fps(bktr, frame_rate);
   1037 	bktr->video.addr = 0;
   1038 	bktr->video.width = 0;
   1039 	bktr->video.banksize = 0;
   1040 	bktr->video.ramsize = 0;
   1041 	bktr->pixfmt_compat = TRUE;
   1042 	bktr->format = METEOR_GEO_RGB16;
   1043 	bktr->pixfmt = oformat_meteor_to_bt( bktr->format );
   1044 
   1045 	bktr->capture_area_enabled = FALSE;
   1046 
   1047 	OUTL(bktr, BKTR_INT_MASK, BT848_INT_MYSTERYBIT);	/* if you take this out triton
   1048                                                    based motherboards will
   1049 						   operate unreliably */
   1050 	return( 0 );
   1051 }
   1052 
   1053 int
   1054 vbi_open( bktr_ptr_t bktr )
   1055 {
   1056 	if (bktr->vbiflags & VBI_OPEN)		/* device is busy */
   1057 		return( EBUSY );
   1058 
   1059 	bktr->vbiflags |= VBI_OPEN;
   1060 
   1061 	/* reset the VBI circular buffer pointers and clear the buffers */
   1062 	bktr->vbiinsert = 0;
   1063 	bktr->vbistart = 0;
   1064 	bktr->vbisize = 0;
   1065 	bktr->vbi_sequence_number = 0;
   1066 	bktr->vbi_read_blocked = FALSE;
   1067 
   1068 	bzero((caddr_t) bktr->vbibuffer, VBI_BUFFER_SIZE);
   1069 	bzero((caddr_t) bktr->vbidata,  VBI_DATA_SIZE);
   1070 
   1071 	return( 0 );
   1072 }
   1073 
   1074 /*
   1075  *
   1076  */
   1077 int
   1078 tuner_open( bktr_ptr_t bktr )
   1079 {
   1080 	if ( !(bktr->tflags & TUNER_INITALIZED) )	/* device not found */
   1081 		return( ENXIO );
   1082 
   1083 	if ( bktr->tflags & TUNER_OPEN )		/* already open */
   1084 		return( 0 );
   1085 
   1086 	bktr->tflags |= TUNER_OPEN;
   1087 	bktr->tuner.frequency = 0;
   1088 	bktr->tuner.channel = 0;
   1089 	bktr->tuner.chnlset = DEFAULT_CHNLSET;
   1090 	bktr->tuner.afc = 0;
   1091 	bktr->tuner.radio_mode = 0;
   1092 
   1093 	/* enable drivers on the GPIO port that control the MUXes */
   1094 	OUTL(bktr, BKTR_GPIO_OUT_EN, INL(bktr, BKTR_GPIO_OUT_EN) | bktr->card.gpio_mux_bits);
   1095 
   1096 	/* unmute the audio stream */
   1097 	set_audio( bktr, AUDIO_UNMUTE );
   1098 
   1099 	/* Initialise any audio chips, eg MSP34xx or TDA98xx */
   1100 	init_audio_devices( bktr );
   1101 
   1102 	return( 0 );
   1103 }
   1104 
   1105 
   1106 
   1107 
   1108 /*
   1109  *
   1110  */
   1111 int
   1112 video_close( bktr_ptr_t bktr )
   1113 {
   1114 	bktr->flags &= ~(METEOR_OPEN     |
   1115 			 METEOR_SINGLE   |
   1116 			 METEOR_CAP_MASK |
   1117 			 METEOR_WANT_MASK);
   1118 
   1119 	OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_RISC_DISABLED);
   1120 	OUTB(bktr, BKTR_CAP_CTL, CAPTURE_OFF);
   1121 
   1122 	bktr->dma_prog_loaded = FALSE;
   1123 	OUTB(bktr, BKTR_TDEC, 0);
   1124 	OUTL(bktr, BKTR_INT_MASK, ALL_INTS_DISABLED);
   1125 
   1126 /** FIXME: is 0xf magic, wouldn't 0x00 work ??? */
   1127 	OUTL(bktr, BKTR_SRESET, 0xf);
   1128 	OUTL(bktr, BKTR_INT_STAT, ALL_INTS_CLEARED);
   1129 
   1130 	return( 0 );
   1131 }
   1132 
   1133 
   1134 /*
   1135  * tuner close handle,
   1136  *  place holder for tuner specific operations on a close.
   1137  */
   1138 int
   1139 tuner_close( bktr_ptr_t bktr )
   1140 {
   1141 	bktr->tflags &= ~TUNER_OPEN;
   1142 
   1143 	/* mute the audio by switching the mux */
   1144 	set_audio( bktr, AUDIO_MUTE );
   1145 
   1146 	/* disable drivers on the GPIO port that control the MUXes */
   1147 	OUTL(bktr, BKTR_GPIO_OUT_EN, INL(bktr, BKTR_GPIO_OUT_EN) & ~bktr->card.gpio_mux_bits);
   1148 
   1149 	return( 0 );
   1150 }
   1151 
   1152 int
   1153 vbi_close( bktr_ptr_t bktr )
   1154 {
   1155 
   1156 	bktr->vbiflags &= ~VBI_OPEN;
   1157 
   1158 	return( 0 );
   1159 }
   1160 
   1161 /*
   1162  *
   1163  */
   1164 int
   1165 video_read(bktr_ptr_t bktr, int unit, dev_t dev, struct uio *uio)
   1166 {
   1167         int             status;
   1168         int             count;
   1169 
   1170 
   1171 	if (bktr->bigbuf == 0)	/* no frame buffer allocated (ioctl failed) */
   1172 		return( ENOMEM );
   1173 
   1174 	if (bktr->flags & METEOR_CAP_MASK)
   1175 		return( EIO );	/* already capturing */
   1176 
   1177         OUTB(bktr, BKTR_CAP_CTL, bktr->bktr_cap_ctl);
   1178 
   1179 
   1180 	count = bktr->rows * bktr->cols *
   1181 		pixfmt_table[ bktr->pixfmt ].public.Bpp;
   1182 
   1183 	if ((int) uio->uio_iov->iov_len < count)
   1184 		return( EINVAL );
   1185 
   1186 	bktr->flags &= ~(METEOR_CAP_MASK | METEOR_WANT_MASK);
   1187 
   1188 	/* capture one frame */
   1189 	start_capture(bktr, METEOR_SINGLE);
   1190 	/* wait for capture to complete */
   1191 	OUTL(bktr, BKTR_INT_STAT, ALL_INTS_CLEARED);
   1192 	OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_ENABLED);
   1193 	OUTW(bktr, BKTR_GPIO_DMA_CTL, bktr->capcontrol);
   1194 	OUTL(bktr, BKTR_INT_MASK, BT848_INT_MYSTERYBIT |
   1195                             BT848_INT_RISCI      |
   1196                             BT848_INT_VSYNC      |
   1197                             BT848_INT_FMTCHG);
   1198 
   1199 
   1200 	status = tsleep(BKTR_SLEEP, BKTRPRI, "captur", 0);
   1201 	if (!status)		/* successful capture */
   1202 		status = uiomove((caddr_t)bktr->bigbuf, count, uio);
   1203 	else
   1204 		printf ("%s: read: tsleep error %d\n",
   1205 			bktr_name(bktr), status);
   1206 
   1207 	bktr->flags &= ~(METEOR_SINGLE | METEOR_WANT_MASK);
   1208 
   1209 	return( status );
   1210 }
   1211 
   1212 /*
   1213  * Read VBI data from the vbi circular buffer
   1214  * The buffer holds vbi data blocks which are the same size
   1215  * vbiinsert is the position we will insert the next item into the buffer
   1216  * vbistart is the actual position in the buffer we want to read from
   1217  * vbisize is the exact number of bytes in the buffer left to read
   1218  */
   1219 int
   1220 vbi_read(bktr_ptr_t bktr, struct uio *uio, int ioflag)
   1221 {
   1222 	int             readsize, readsize2;
   1223 	int             status;
   1224 
   1225 
   1226 	while(bktr->vbisize == 0) {
   1227 		if (ioflag & IO_NDELAY) {
   1228 			return EWOULDBLOCK;
   1229 		}
   1230 
   1231 		bktr->vbi_read_blocked = TRUE;
   1232 		if ((status = tsleep(VBI_SLEEP, VBIPRI, "vbi", 0))) {
   1233 			return status;
   1234 		}
   1235 	}
   1236 
   1237 	/* Now we have some data to give to the user */
   1238 
   1239 	/* We cannot read more bytes than there are in
   1240 	 * the circular buffer
   1241 	 */
   1242 	readsize = (int)uio->uio_iov->iov_len;
   1243 
   1244 	if (readsize > bktr->vbisize) readsize = bktr->vbisize;
   1245 
   1246 	/* Check if we can read this number of bytes without having
   1247 	 * to wrap around the circular buffer */
   1248 	if((bktr->vbistart + readsize) >= VBI_BUFFER_SIZE) {
   1249 		/* We need to wrap around */
   1250 
   1251 		readsize2 = VBI_BUFFER_SIZE - bktr->vbistart;
   1252                	status = uiomove((caddr_t)bktr->vbibuffer + bktr->vbistart, readsize2, uio);
   1253 		status += uiomove((caddr_t)bktr->vbibuffer, (readsize - readsize2), uio);
   1254 	} else {
   1255 		/* We do not need to wrap around */
   1256 		status = uiomove((caddr_t)bktr->vbibuffer + bktr->vbistart, readsize, uio);
   1257 	}
   1258 
   1259 	/* Update the number of bytes left to read */
   1260 	bktr->vbisize -= readsize;
   1261 
   1262 	/* Update vbistart */
   1263 	bktr->vbistart += readsize;
   1264 	bktr->vbistart = bktr->vbistart % VBI_BUFFER_SIZE; /* wrap around if needed */
   1265 
   1266 	return( status );
   1267 
   1268 }
   1269 
   1270 
   1271 
   1272 /*
   1273  * video ioctls
   1274  */
   1275 int
   1276 video_ioctl( bktr_ptr_t bktr, int unit, ioctl_cmd_t cmd, caddr_t arg, struct proc* pr )
   1277 {
   1278 	volatile u_char		c_temp;
   1279 	unsigned int		temp;
   1280 	unsigned int		temp_iform;
   1281 	unsigned int		error;
   1282 	struct meteor_geomet	*geo;
   1283 	struct meteor_counts	*counts;
   1284 	struct meteor_video	*video;
   1285 	struct bktr_capture_area *cap_area;
   1286 #if defined(__NetBSD__)
   1287 	vaddr_t			buf;
   1288 #else
   1289 	vm_offset_t		buf;
   1290 #endif
   1291 	int                     i;
   1292 	char                    char_temp;
   1293 
   1294 	switch ( cmd ) {
   1295 
   1296 	case BT848SCLIP: /* set clip region */
   1297 	    bktr->max_clip_node = 0;
   1298 	    memcpy(&bktr->clip_list, arg, sizeof(bktr->clip_list));
   1299 
   1300 	    for (i = 0; i < BT848_MAX_CLIP_NODE; i++) {
   1301 		if (bktr->clip_list[i].y_min ==  0 &&
   1302 		    bktr->clip_list[i].y_max == 0)
   1303 		    break;
   1304 	    }
   1305 	    bktr->max_clip_node = i;
   1306 
   1307 	    /* make sure that the list contains a valid clip secquence */
   1308 	    /* the clip rectangles should be sorted by x then by y as the
   1309                second order sort key */
   1310 
   1311 	    /* clip rectangle list is terminated by y_min and y_max set to 0 */
   1312 
   1313 	    /* to disable clipping set  y_min and y_max to 0 in the first
   1314                clip rectangle . The first clip rectangle is clip_list[0].
   1315              */
   1316 
   1317 
   1318 
   1319 	    if (bktr->max_clip_node == 0 &&
   1320 		(bktr->clip_list[0].y_min != 0 &&
   1321 		 bktr->clip_list[0].y_max != 0)) {
   1322 		return EINVAL;
   1323 	    }
   1324 
   1325 	    for (i = 0; i < BT848_MAX_CLIP_NODE - 1 ; i++) {
   1326 		if (bktr->clip_list[i].y_min == 0 &&
   1327 		    bktr->clip_list[i].y_max == 0) {
   1328 		    break;
   1329 		}
   1330 		if ( bktr->clip_list[i+1].y_min != 0 &&
   1331 		     bktr->clip_list[i+1].y_max != 0 &&
   1332 		     bktr->clip_list[i].x_min > bktr->clip_list[i+1].x_min ) {
   1333 
   1334 		    bktr->max_clip_node = 0;
   1335 		    return (EINVAL);
   1336 
   1337 		 }
   1338 
   1339 		if (bktr->clip_list[i].x_min >= bktr->clip_list[i].x_max ||
   1340 		    bktr->clip_list[i].y_min >= bktr->clip_list[i].y_max ||
   1341 		    bktr->clip_list[i].x_min < 0 ||
   1342 		    bktr->clip_list[i].x_max < 0 ||
   1343 		    bktr->clip_list[i].y_min < 0 ||
   1344 		    bktr->clip_list[i].y_max < 0 ) {
   1345 		    bktr->max_clip_node = 0;
   1346 		    return (EINVAL);
   1347 		}
   1348 	    }
   1349 
   1350 	    bktr->dma_prog_loaded = FALSE;
   1351 
   1352 	    break;
   1353 
   1354 	case METEORSTATUS:	/* get Bt848 status */
   1355 		c_temp = INB(bktr, BKTR_DSTATUS);
   1356 		temp = 0;
   1357 		if (!(c_temp & 0x40)) temp |= METEOR_STATUS_HCLK;
   1358 		if (!(c_temp & 0x10)) temp |= METEOR_STATUS_FIDT;
   1359 		*(u_short *)arg = temp;
   1360 		break;
   1361 
   1362 	case BT848SFMT:		/* set input format */
   1363 		temp = *(unsigned long*)arg & BT848_IFORM_FORMAT;
   1364 		temp_iform = INB(bktr, BKTR_IFORM);
   1365 		temp_iform &= ~BT848_IFORM_FORMAT;
   1366 		temp_iform &= ~BT848_IFORM_XTSEL;
   1367 		OUTB(bktr, BKTR_IFORM, (temp_iform | temp | format_params[temp].iform_xtsel));
   1368 		switch( temp ) {
   1369 		case BT848_IFORM_F_AUTO:
   1370 			bktr->flags = (bktr->flags & ~METEOR_FORM_MASK) |
   1371 			METEOR_AUTOMODE;
   1372 			break;
   1373 
   1374 		case BT848_IFORM_F_NTSCM:
   1375 		case BT848_IFORM_F_NTSCJ:
   1376 			bktr->flags = (bktr->flags & ~METEOR_FORM_MASK) |
   1377 				METEOR_NTSC;
   1378 			OUTB(bktr, BKTR_ADELAY, format_params[temp].adelay);
   1379 			OUTB(bktr, BKTR_BDELAY, format_params[temp].bdelay);
   1380 			bktr->format_params = temp;
   1381 			break;
   1382 
   1383 		case BT848_IFORM_F_PALBDGHI:
   1384 		case BT848_IFORM_F_PALN:
   1385 		case BT848_IFORM_F_SECAM:
   1386 		case BT848_IFORM_F_RSVD:
   1387 		case BT848_IFORM_F_PALM:
   1388 			bktr->flags = (bktr->flags & ~METEOR_FORM_MASK) |
   1389 				METEOR_PAL;
   1390 			OUTB(bktr, BKTR_ADELAY, format_params[temp].adelay);
   1391 			OUTB(bktr, BKTR_BDELAY, format_params[temp].bdelay);
   1392 			bktr->format_params = temp;
   1393 			break;
   1394 
   1395 		}
   1396 		bktr->dma_prog_loaded = FALSE;
   1397 		break;
   1398 
   1399 	case METEORSFMT:	/* set input format */
   1400 		temp_iform = INB(bktr, BKTR_IFORM);
   1401 		temp_iform &= ~BT848_IFORM_FORMAT;
   1402 		temp_iform &= ~BT848_IFORM_XTSEL;
   1403 		switch(*(unsigned long *)arg & METEOR_FORM_MASK ) {
   1404 		case 0:		/* default */
   1405 		case METEOR_FMT_NTSC:
   1406 			bktr->flags = (bktr->flags & ~METEOR_FORM_MASK) |
   1407 				METEOR_NTSC;
   1408 			OUTB(bktr, BKTR_IFORM, temp_iform | BT848_IFORM_F_NTSCM |
   1409 		                         format_params[BT848_IFORM_F_NTSCM].iform_xtsel);
   1410 			OUTB(bktr, BKTR_ADELAY, format_params[BT848_IFORM_F_NTSCM].adelay);
   1411 			OUTB(bktr, BKTR_BDELAY, format_params[BT848_IFORM_F_NTSCM].bdelay);
   1412 			bktr->format_params = BT848_IFORM_F_NTSCM;
   1413 			break;
   1414 
   1415 		case METEOR_FMT_PAL:
   1416 			bktr->flags = (bktr->flags & ~METEOR_FORM_MASK) |
   1417 				METEOR_PAL;
   1418 			OUTB(bktr, BKTR_IFORM, temp_iform | BT848_IFORM_F_PALBDGHI |
   1419 		                         format_params[BT848_IFORM_F_PALBDGHI].iform_xtsel);
   1420 			OUTB(bktr, BKTR_ADELAY, format_params[BT848_IFORM_F_PALBDGHI].adelay);
   1421 			OUTB(bktr, BKTR_BDELAY, format_params[BT848_IFORM_F_PALBDGHI].bdelay);
   1422 			bktr->format_params = BT848_IFORM_F_PALBDGHI;
   1423 			break;
   1424 
   1425 		case METEOR_FMT_AUTOMODE:
   1426 			bktr->flags = (bktr->flags & ~METEOR_FORM_MASK) |
   1427 				METEOR_AUTOMODE;
   1428 			OUTB(bktr, BKTR_IFORM, temp_iform | BT848_IFORM_F_AUTO |
   1429 		                         format_params[BT848_IFORM_F_AUTO].iform_xtsel);
   1430 			break;
   1431 
   1432 		default:
   1433 			return( EINVAL );
   1434 		}
   1435 		bktr->dma_prog_loaded = FALSE;
   1436 		break;
   1437 
   1438 	case METEORGFMT:	/* get input format */
   1439 		*(u_long *)arg = bktr->flags & METEOR_FORM_MASK;
   1440 		break;
   1441 
   1442 
   1443 	case BT848GFMT:		/* get input format */
   1444 	        *(u_long *)arg = INB(bktr, BKTR_IFORM) & BT848_IFORM_FORMAT;
   1445 		break;
   1446 
   1447 	case METEORSCOUNT:	/* (re)set error counts */
   1448 		counts = (struct meteor_counts *) arg;
   1449 		bktr->fifo_errors = counts->fifo_errors;
   1450 		bktr->dma_errors = counts->dma_errors;
   1451 		bktr->frames_captured = counts->frames_captured;
   1452 		bktr->even_fields_captured = counts->even_fields_captured;
   1453 		bktr->odd_fields_captured = counts->odd_fields_captured;
   1454 		break;
   1455 
   1456 	case METEORGCOUNT:	/* get error counts */
   1457 		counts = (struct meteor_counts *) arg;
   1458 		counts->fifo_errors = bktr->fifo_errors;
   1459 		counts->dma_errors = bktr->dma_errors;
   1460 		counts->frames_captured = bktr->frames_captured;
   1461 		counts->even_fields_captured = bktr->even_fields_captured;
   1462 		counts->odd_fields_captured = bktr->odd_fields_captured;
   1463 		break;
   1464 
   1465 	case METEORGVIDEO:
   1466 		video = (struct meteor_video *)arg;
   1467 		video->addr = bktr->video.addr;
   1468 		video->width = bktr->video.width;
   1469 		video->banksize = bktr->video.banksize;
   1470 		video->ramsize = bktr->video.ramsize;
   1471 		break;
   1472 
   1473 	case METEORSVIDEO:
   1474 		video = (struct meteor_video *)arg;
   1475 		bktr->video.addr = video->addr;
   1476 		bktr->video.width = video->width;
   1477 		bktr->video.banksize = video->banksize;
   1478 		bktr->video.ramsize = video->ramsize;
   1479 		break;
   1480 
   1481 	case METEORSFPS:
   1482 		set_fps(bktr, *(u_short *)arg);
   1483 		break;
   1484 
   1485 	case METEORGFPS:
   1486 		*(u_short *)arg = bktr->fps;
   1487 		break;
   1488 
   1489 	case METEORSHUE:	/* set hue */
   1490 		OUTB(bktr, BKTR_HUE, (*(u_char *) arg) & 0xff);
   1491 		break;
   1492 
   1493 	case METEORGHUE:	/* get hue */
   1494 		*(u_char *)arg = INB(bktr, BKTR_HUE);
   1495 		break;
   1496 
   1497 	case METEORSBRIG:	/* set brightness */
   1498 	        char_temp =    ( *(u_char *)arg & 0xff) - 128;
   1499 		OUTB(bktr, BKTR_BRIGHT, char_temp);
   1500 
   1501 		break;
   1502 
   1503 	case METEORGBRIG:	/* get brightness */
   1504 		*(u_char *)arg = INB(bktr, BKTR_BRIGHT);
   1505 		break;
   1506 
   1507 	case METEORSCSAT:	/* set chroma saturation */
   1508 		temp = (int)*(u_char *)arg;
   1509 
   1510 		OUTB(bktr, BKTR_SAT_U_LO, (temp << 1) & 0xff);
   1511 		OUTB(bktr, BKTR_SAT_V_LO, (temp << 1) & 0xff);
   1512 		OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL)
   1513 		                     & ~(BT848_E_CONTROL_SAT_U_MSB
   1514 					 | BT848_E_CONTROL_SAT_V_MSB));
   1515 		OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_O_CONTROL)
   1516 		                     & ~(BT848_O_CONTROL_SAT_U_MSB |
   1517 					 BT848_O_CONTROL_SAT_V_MSB));
   1518 
   1519 		if ( temp & BIT_SEVEN_HIGH ) {
   1520 		        OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL)
   1521 			                     | (BT848_E_CONTROL_SAT_U_MSB
   1522 						| BT848_E_CONTROL_SAT_V_MSB));
   1523 			OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_O_CONTROL)
   1524 			                     | (BT848_O_CONTROL_SAT_U_MSB
   1525 						| BT848_O_CONTROL_SAT_V_MSB));
   1526 		}
   1527 		break;
   1528 
   1529 	case METEORGCSAT:	/* get chroma saturation */
   1530 		temp = (INB(bktr, BKTR_SAT_V_LO) >> 1) & 0xff;
   1531 		if ( INB(bktr, BKTR_E_CONTROL) & BT848_E_CONTROL_SAT_V_MSB )
   1532 			temp |= BIT_SEVEN_HIGH;
   1533 		*(u_char *)arg = (u_char)temp;
   1534 		break;
   1535 
   1536 	case METEORSCONT:	/* set contrast */
   1537 		temp = (int)*(u_char *)arg & 0xff;
   1538 		temp <<= 1;
   1539 		OUTB(bktr, BKTR_CONTRAST_LO, temp & 0xff);
   1540 		OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL) & ~BT848_E_CONTROL_CON_MSB);
   1541 		OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_O_CONTROL) & ~BT848_O_CONTROL_CON_MSB);
   1542 		OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL) |
   1543 			(((temp & 0x100) >> 6 ) & BT848_E_CONTROL_CON_MSB));
   1544 		OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_O_CONTROL) |
   1545 			(((temp & 0x100) >> 6 ) & BT848_O_CONTROL_CON_MSB));
   1546 		break;
   1547 
   1548 	case METEORGCONT:	/* get contrast */
   1549 		temp = (int)INB(bktr, BKTR_CONTRAST_LO) & 0xff;
   1550 		temp |= ((int)INB(bktr, BKTR_O_CONTROL) & 0x04) << 6;
   1551 		*(u_char *)arg = (u_char)((temp >> 1) & 0xff);
   1552 		break;
   1553 
   1554 	case BT848SCBUF:	/* set Clear-Buffer-on-start flag */
   1555 		bktr->clr_on_start = (*(int *)arg != 0);
   1556 		break;
   1557 
   1558 	case BT848GCBUF:	/* get Clear-Buffer-on-start flag */
   1559 		*(int *)arg = (int) bktr->clr_on_start;
   1560 		break;
   1561 
   1562 	case METEORSSIGNAL:
   1563 		if(*(int *)arg == 0 || *(int *)arg >= NSIG) {
   1564 			return( EINVAL );
   1565 			break;
   1566 		}
   1567 		bktr->signal = *(int *) arg;
   1568 		bktr->proc = pr;
   1569 		break;
   1570 
   1571 	case METEORGSIGNAL:
   1572 		*(int *)arg = bktr->signal;
   1573 		break;
   1574 
   1575 	case METEORCAPTUR:
   1576 		temp = bktr->flags;
   1577 		switch (*(int *) arg) {
   1578 		case METEOR_CAP_SINGLE:
   1579 
   1580 			if (bktr->bigbuf==0)	/* no frame buffer allocated */
   1581 				return( ENOMEM );
   1582 			/* already capturing */
   1583 			if (temp & METEOR_CAP_MASK)
   1584 				return( EIO );
   1585 
   1586 
   1587 
   1588 			start_capture(bktr, METEOR_SINGLE);
   1589 
   1590 			/* wait for capture to complete */
   1591 			OUTL(bktr, BKTR_INT_STAT, ALL_INTS_CLEARED);
   1592 			OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_ENABLED);
   1593 			OUTW(bktr, BKTR_GPIO_DMA_CTL, bktr->capcontrol);
   1594 
   1595 			OUTL(bktr, BKTR_INT_MASK, BT848_INT_MYSTERYBIT |
   1596 			     		    BT848_INT_RISCI      |
   1597 					    BT848_INT_VSYNC      |
   1598 					    BT848_INT_FMTCHG);
   1599 
   1600 			OUTB(bktr, BKTR_CAP_CTL, bktr->bktr_cap_ctl);
   1601 			error = tsleep(BKTR_SLEEP, BKTRPRI, "captur", hz);
   1602 			if (error && (error != ERESTART)) {
   1603 				/*  Here if we didn't get complete frame  */
   1604 #ifdef DIAGNOSTIC
   1605 				printf( "%s: ioctl: tsleep error %d %x\n",
   1606 					bktr_name(bktr), error,
   1607 					INL(bktr, BKTR_RISC_COUNT));
   1608 #endif
   1609 
   1610 				/* stop dma */
   1611 				OUTL(bktr, BKTR_INT_MASK, ALL_INTS_DISABLED);
   1612 
   1613 				/* disable risc, leave fifo running */
   1614 				OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_ENABLED);
   1615 			}
   1616 
   1617 			bktr->flags &= ~(METEOR_SINGLE|METEOR_WANT_MASK);
   1618 			/* FIXME: should we set bt848->int_stat ??? */
   1619 			break;
   1620 
   1621 		case METEOR_CAP_CONTINOUS:
   1622 			if (bktr->bigbuf==0)	/* no frame buffer allocated */
   1623 				return( ENOMEM );
   1624 			/* already capturing */
   1625 			if (temp & METEOR_CAP_MASK)
   1626 			    return( EIO );
   1627 
   1628 
   1629 			start_capture(bktr, METEOR_CONTIN);
   1630 
   1631 			/* Clear the interrypt status register */
   1632 			OUTL(bktr, BKTR_INT_STAT, INL(bktr, BKTR_INT_STAT));
   1633 
   1634 			OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_ENABLED);
   1635 			OUTW(bktr, BKTR_GPIO_DMA_CTL, bktr->capcontrol);
   1636 			OUTB(bktr, BKTR_CAP_CTL, bktr->bktr_cap_ctl);
   1637 
   1638 			OUTL(bktr, BKTR_INT_MASK, BT848_INT_MYSTERYBIT |
   1639 					    BT848_INT_RISCI      |
   1640 			                    BT848_INT_VSYNC      |
   1641 					    BT848_INT_FMTCHG);
   1642 #ifdef BT848_DUMP
   1643 			dump_bt848( bt848 );
   1644 #endif
   1645 			break;
   1646 
   1647 		case METEOR_CAP_STOP_CONT:
   1648 			if (bktr->flags & METEOR_CONTIN) {
   1649 				/* turn off capture */
   1650 				OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_RISC_DISABLED);
   1651 				OUTB(bktr, BKTR_CAP_CTL, CAPTURE_OFF);
   1652 				OUTL(bktr, BKTR_INT_MASK, ALL_INTS_DISABLED);
   1653 				bktr->flags &=
   1654 					~(METEOR_CONTIN | METEOR_WANT_MASK);
   1655 
   1656 			}
   1657 		}
   1658 		break;
   1659 
   1660 	case METEORSETGEO:
   1661 		/* can't change parameters while capturing */
   1662 		if (bktr->flags & METEOR_CAP_MASK)
   1663 			return( EBUSY );
   1664 
   1665 
   1666 		geo = (struct meteor_geomet *) arg;
   1667 
   1668 		error = 0;
   1669 		/* Either even or odd, if even & odd, then these a zero */
   1670 		if ((geo->oformat & METEOR_GEO_ODD_ONLY) &&
   1671 			(geo->oformat & METEOR_GEO_EVEN_ONLY)) {
   1672 			printf( "%s: ioctl: Geometry odd or even only.\n",
   1673 				bktr_name(bktr));
   1674 			return( EINVAL );
   1675 		}
   1676 
   1677 		/* set/clear even/odd flags */
   1678 		if (geo->oformat & METEOR_GEO_ODD_ONLY)
   1679 			bktr->flags |= METEOR_ONLY_ODD_FIELDS;
   1680 		else
   1681 			bktr->flags &= ~METEOR_ONLY_ODD_FIELDS;
   1682 		if (geo->oformat & METEOR_GEO_EVEN_ONLY)
   1683 			bktr->flags |= METEOR_ONLY_EVEN_FIELDS;
   1684 		else
   1685 			bktr->flags &= ~METEOR_ONLY_EVEN_FIELDS;
   1686 
   1687 		if (geo->columns <= 0) {
   1688 			printf(
   1689 			"%s: ioctl: %d: columns must be greater than zero.\n",
   1690 				bktr_name(bktr), geo->columns);
   1691 			error = EINVAL;
   1692 		}
   1693 		else if ((geo->columns & 0x3fe) != geo->columns) {
   1694 			printf(
   1695 			"%s: ioctl: %d: columns too large or not even.\n",
   1696 				bktr_name(bktr), geo->columns);
   1697 			error = EINVAL;
   1698 		}
   1699 
   1700 		if (geo->rows <= 0) {
   1701 			printf(
   1702 			"%s: ioctl: %d: rows must be greater than zero.\n",
   1703 				bktr_name(bktr), geo->rows);
   1704 			error = EINVAL;
   1705 		}
   1706 		else if (((geo->rows & 0x7fe) != geo->rows) ||
   1707 			((geo->oformat & METEOR_GEO_FIELD_MASK) &&
   1708 				((geo->rows & 0x3fe) != geo->rows)) ) {
   1709 			printf(
   1710 			"%s: ioctl: %d: rows too large or not even.\n",
   1711 				bktr_name(bktr), geo->rows);
   1712 			error = EINVAL;
   1713 		}
   1714 
   1715 		if (geo->frames > 32) {
   1716 			printf("%s: ioctl: too many frames.\n",
   1717 			       bktr_name(bktr));
   1718 
   1719 			error = EINVAL;
   1720 		}
   1721 
   1722 		if (error)
   1723 			return( error );
   1724 
   1725 		bktr->dma_prog_loaded = FALSE;
   1726 		OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_RISC_DISABLED);
   1727 
   1728 		OUTL(bktr, BKTR_INT_MASK, ALL_INTS_DISABLED);
   1729 
   1730 		if ((temp=(geo->rows * geo->columns * geo->frames * 2))) {
   1731 			if (geo->oformat & METEOR_GEO_RGB24) temp = temp * 2;
   1732 
   1733 			/* meteor_mem structure for SYNC Capture */
   1734 			if (geo->frames > 1) temp += PAGE_SIZE;
   1735 
   1736 			temp = btoc(temp);
   1737 			if ((int) temp > bktr->alloc_pages
   1738 			    && bktr->video.addr == 0) {
   1739 
   1740 /*****************************/
   1741 /* *** OS Dependant code *** */
   1742 /*****************************/
   1743 #if defined(__NetBSD__) || defined(__OpenBSD__)
   1744                                 bus_dmamap_t dmamap;
   1745 
   1746                                 buf = get_bktr_mem(bktr, &dmamap,
   1747                                                    temp * PAGE_SIZE);
   1748                                 if (buf != 0) {
   1749                                         free_bktr_mem(bktr, bktr->dm_mem,
   1750                                                       bktr->bigbuf);
   1751                                         bktr->dm_mem = dmamap;
   1752 
   1753 #else
   1754                                 buf = get_bktr_mem(unit, temp*PAGE_SIZE);
   1755                                 if (buf != 0) {
   1756                                         kmem_free(kernel_map, bktr->bigbuf,
   1757                                           (bktr->alloc_pages * PAGE_SIZE));
   1758 #endif
   1759 
   1760 					bktr->bigbuf = buf;
   1761 					bktr->alloc_pages = temp;
   1762 					if (bootverbose)
   1763 						printf(
   1764 				"%s: ioctl: Allocating %d bytes\n",
   1765 							bktr_name(bktr), temp*PAGE_SIZE);
   1766 				}
   1767 				else
   1768 					error = ENOMEM;
   1769 			}
   1770 		}
   1771 
   1772 		if (error)
   1773 			return error;
   1774 
   1775 		bktr->rows = geo->rows;
   1776 		bktr->cols = geo->columns;
   1777 		bktr->frames = geo->frames;
   1778 
   1779 		/*  Pixel format (if in meteor pixfmt compatibility mode)  */
   1780 		if ( bktr->pixfmt_compat ) {
   1781 			bktr->format = METEOR_GEO_YUV_422;
   1782 			switch (geo->oformat & METEOR_GEO_OUTPUT_MASK) {
   1783 			case 0:			/* default */
   1784 			case METEOR_GEO_RGB16:
   1785 				    bktr->format = METEOR_GEO_RGB16;
   1786 				    break;
   1787 			case METEOR_GEO_RGB24:
   1788 				    bktr->format = METEOR_GEO_RGB24;
   1789 				    break;
   1790 			case METEOR_GEO_YUV_422:
   1791 				    bktr->format = METEOR_GEO_YUV_422;
   1792                                     if (geo->oformat & METEOR_GEO_YUV_12)
   1793 					bktr->format = METEOR_GEO_YUV_12;
   1794 				    break;
   1795 			case METEOR_GEO_YUV_PACKED:
   1796 				    bktr->format = METEOR_GEO_YUV_PACKED;
   1797 				    break;
   1798 			}
   1799 			bktr->pixfmt = oformat_meteor_to_bt( bktr->format );
   1800 		}
   1801 
   1802 		if (bktr->flags & METEOR_CAP_MASK) {
   1803 
   1804 			if (bktr->flags & (METEOR_CONTIN|METEOR_SYNCAP)) {
   1805 				switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
   1806 				case METEOR_ONLY_ODD_FIELDS:
   1807 					bktr->flags |= METEOR_WANT_ODD;
   1808 					break;
   1809 				case METEOR_ONLY_EVEN_FIELDS:
   1810 					bktr->flags |= METEOR_WANT_EVEN;
   1811 					break;
   1812 				default:
   1813 					bktr->flags |= METEOR_WANT_MASK;
   1814 					break;
   1815 				}
   1816 
   1817 				start_capture(bktr, METEOR_CONTIN);
   1818 				OUTL(bktr, BKTR_INT_STAT, INL(bktr, BKTR_INT_STAT));
   1819 				OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_ENABLED);
   1820 				OUTW(bktr, BKTR_GPIO_DMA_CTL, bktr->capcontrol);
   1821 				OUTL(bktr, BKTR_INT_MASK, BT848_INT_MYSTERYBIT |
   1822 						    BT848_INT_VSYNC      |
   1823 						    BT848_INT_FMTCHG);
   1824 			}
   1825 		}
   1826 		break;
   1827 	/* end of METEORSETGEO */
   1828 
   1829 	/* FIXME. The Capture Area currently has the following restrictions:
   1830 	GENERAL
   1831 	 y_offset may need to be even in interlaced modes
   1832 	RGB24 - Interlaced mode
   1833 	 x_size must be greater than or equal to 1.666*METEORSETGEO width (cols)
   1834 	 y_size must be greater than or equal to METEORSETGEO height (rows)
   1835 	RGB24 - Even Only (or Odd Only) mode
   1836 	 x_size must be greater than or equal to 1.666*METEORSETGEO width (cols)
   1837 	 y_size must be greater than or equal to 2*METEORSETGEO height (rows)
   1838 	YUV12 - Interlaced mode
   1839 	 x_size must be greater than or equal to METEORSETGEO width (cols)
   1840 	 y_size must be greater than or equal to METEORSETGEO height (rows)
   1841 	YUV12 - Even Only (or Odd Only) mode
   1842 	 x_size must be greater than or equal to METEORSETGEO width (cols)
   1843 	 y_size must be greater than or equal to 2*METEORSETGEO height (rows)
   1844 	*/
   1845 
   1846 	case BT848_SCAPAREA: /* set capture area of each video frame */
   1847 		/* can't change parameters while capturing */
   1848 		if (bktr->flags & METEOR_CAP_MASK)
   1849 			return( EBUSY );
   1850 
   1851 		cap_area = (struct bktr_capture_area *) arg;
   1852 		bktr->capture_area_x_offset = cap_area->x_offset;
   1853 		bktr->capture_area_y_offset = cap_area->y_offset;
   1854 		bktr->capture_area_x_size   = cap_area->x_size;
   1855 		bktr->capture_area_y_size   = cap_area->y_size;
   1856 		bktr->capture_area_enabled  = TRUE;
   1857 
   1858 		bktr->dma_prog_loaded = FALSE;
   1859 		break;
   1860 
   1861 	case BT848_GCAPAREA: /* get capture area of each video frame */
   1862 		cap_area = (struct bktr_capture_area *) arg;
   1863 		if (bktr->capture_area_enabled == FALSE) {
   1864 			cap_area->x_offset = 0;
   1865 			cap_area->y_offset = 0;
   1866 			cap_area->x_size   = format_params[
   1867 				bktr->format_params].scaled_hactive;
   1868 			cap_area->y_size   = format_params[
   1869 				bktr->format_params].vactive;
   1870 		} else {
   1871 			cap_area->x_offset = bktr->capture_area_x_offset;
   1872 			cap_area->y_offset = bktr->capture_area_y_offset;
   1873 			cap_area->x_size   = bktr->capture_area_x_size;
   1874 			cap_area->y_size   = bktr->capture_area_y_size;
   1875 		}
   1876 		break;
   1877 
   1878 	default:
   1879 		return common_ioctl( bktr, cmd, arg );
   1880 	}
   1881 
   1882 	return( 0 );
   1883 }
   1884 
   1885 /*
   1886  * tuner ioctls
   1887  */
   1888 int
   1889 tuner_ioctl( bktr_ptr_t bktr, int unit, ioctl_cmd_t cmd, caddr_t arg, struct proc* pr )
   1890 {
   1891 	int		tmp_int;
   1892 	unsigned int	temp, temp1;
   1893 	int		offset;
   1894 	int		count;
   1895 	u_char		*buf;
   1896 	u_long          par;
   1897 	u_char          write;
   1898 	int             i2c_addr;
   1899 	int             i2c_port;
   1900 	u_long          data;
   1901 
   1902 	switch ( cmd ) {
   1903 
   1904 	case REMOTE_GETKEY:
   1905 		/* Read the last key pressed by the Remote Control */
   1906 		if (bktr->remote_control == 0) return (EINVAL);
   1907 		remote_read(bktr, (struct bktr_remote *)arg);
   1908 		break;
   1909 
   1910 #if defined( TUNER_AFC )
   1911 	case TVTUNER_SETAFC:
   1912 		bktr->tuner.afc = (*(int *)arg != 0);
   1913 		break;
   1914 
   1915 	case TVTUNER_GETAFC:
   1916 		*(int *)arg = bktr->tuner.afc;
   1917 		/* XXX Perhaps use another bit to indicate AFC success? */
   1918 		break;
   1919 #endif /* TUNER_AFC */
   1920 
   1921 	case TVTUNER_SETCHNL:
   1922 		temp_mute( bktr, TRUE );
   1923 		temp = tv_channel( bktr, (int)*(unsigned long *)arg );
   1924 		if ( temp < 0 ) {
   1925 			temp_mute( bktr, FALSE );
   1926 			return( EINVAL );
   1927 		}
   1928 		*(unsigned long *)arg = temp;
   1929 
   1930 		/* after every channel change, we must restart the MSP34xx */
   1931 		/* audio chip to reselect NICAM STEREO or MONO audio */
   1932 		if ( bktr->card.msp3400c )
   1933 		  msp_autodetect( bktr );
   1934 
   1935 		/* after every channel change, we must restart the DPL35xx */
   1936 		if ( bktr->card.dpl3518a )
   1937 		  dpl_autodetect( bktr );
   1938 
   1939 		temp_mute( bktr, FALSE );
   1940 		break;
   1941 
   1942 	case TVTUNER_GETCHNL:
   1943 		*(unsigned long *)arg = bktr->tuner.channel;
   1944 		break;
   1945 
   1946 	case TVTUNER_SETTYPE:
   1947 		temp = *(unsigned long *)arg;
   1948 		if ( (temp < CHNLSET_MIN) || (temp > CHNLSET_MAX) )
   1949 			return( EINVAL );
   1950 		bktr->tuner.chnlset = temp;
   1951 		break;
   1952 
   1953 	case TVTUNER_GETTYPE:
   1954 		*(unsigned long *)arg = bktr->tuner.chnlset;
   1955 		break;
   1956 
   1957 	case TVTUNER_GETSTATUS:
   1958 		temp = get_tuner_status( bktr );
   1959 		*(unsigned long *)arg = temp & 0xff;
   1960 		break;
   1961 
   1962 	case TVTUNER_SETFREQ:
   1963 		temp_mute( bktr, TRUE );
   1964 		temp = tv_freq( bktr, (int)*(unsigned long *)arg, TV_FREQUENCY);
   1965 		temp_mute( bktr, FALSE );
   1966 		if ( temp < 0 ) {
   1967 			temp_mute( bktr, FALSE );
   1968 			return( EINVAL );
   1969 		}
   1970 		*(unsigned long *)arg = temp;
   1971 
   1972 		/* after every channel change, we must restart the MSP34xx */
   1973 		/* audio chip to reselect NICAM STEREO or MONO audio */
   1974 		if ( bktr->card.msp3400c )
   1975 		  msp_autodetect( bktr );
   1976 
   1977 		/* after every channel change, we must restart the DPL35xx */
   1978 		if ( bktr->card.dpl3518a )
   1979 		  dpl_autodetect( bktr );
   1980 
   1981 		temp_mute( bktr, FALSE );
   1982 		break;
   1983 
   1984 	case TVTUNER_GETFREQ:
   1985 		*(unsigned long *)arg = bktr->tuner.frequency;
   1986 		break;
   1987 
   1988 	case TVTUNER_GETCHNLSET:
   1989 		return tuner_getchnlset((struct bktr_chnlset *)arg);
   1990 
   1991 	case BT848_SAUDIO:	/* set audio channel */
   1992 		if ( set_audio( bktr, *(int*)arg ) < 0 )
   1993 			return( EIO );
   1994 		break;
   1995 
   1996 	/* hue is a 2's compliment number, -90' to +89.3' in 0.7' steps */
   1997 	case BT848_SHUE:	/* set hue */
   1998 		OUTB(bktr, BKTR_HUE, (u_char)(*(int*)arg & 0xff));
   1999 		break;
   2000 
   2001 	case BT848_GHUE:	/* get hue */
   2002 		*(int*)arg = (signed char)(INB(bktr, BKTR_HUE) & 0xff);
   2003 		break;
   2004 
   2005 	/* brightness is a 2's compliment #, -50 to +%49.6% in 0.39% steps */
   2006 	case BT848_SBRIG:	/* set brightness */
   2007 		OUTB(bktr, BKTR_BRIGHT, (u_char)(*(int *)arg & 0xff));
   2008 		break;
   2009 
   2010 	case BT848_GBRIG:	/* get brightness */
   2011 		*(int *)arg = (signed char)(INB(bktr, BKTR_BRIGHT) & 0xff);
   2012 		break;
   2013 
   2014 	/*  */
   2015 	case BT848_SCSAT:	/* set chroma saturation */
   2016 		tmp_int = *(int*)arg;
   2017 
   2018 		temp = INB(bktr, BKTR_E_CONTROL);
   2019 		temp1 = INB(bktr, BKTR_O_CONTROL);
   2020 		if ( tmp_int & BIT_EIGHT_HIGH ) {
   2021 			temp |= (BT848_E_CONTROL_SAT_U_MSB |
   2022 				 BT848_E_CONTROL_SAT_V_MSB);
   2023 			temp1 |= (BT848_O_CONTROL_SAT_U_MSB |
   2024 				  BT848_O_CONTROL_SAT_V_MSB);
   2025 		}
   2026 		else {
   2027 			temp &= ~(BT848_E_CONTROL_SAT_U_MSB |
   2028 				  BT848_E_CONTROL_SAT_V_MSB);
   2029 			temp1 &= ~(BT848_O_CONTROL_SAT_U_MSB |
   2030 				   BT848_O_CONTROL_SAT_V_MSB);
   2031 		}
   2032 
   2033 		OUTB(bktr, BKTR_SAT_U_LO, (u_char)(tmp_int & 0xff));
   2034 		OUTB(bktr, BKTR_SAT_V_LO, (u_char)(tmp_int & 0xff));
   2035 		OUTB(bktr, BKTR_E_CONTROL, temp);
   2036 		OUTB(bktr, BKTR_O_CONTROL, temp1);
   2037 		break;
   2038 
   2039 	case BT848_GCSAT:	/* get chroma saturation */
   2040 		tmp_int = (int)(INB(bktr, BKTR_SAT_V_LO) & 0xff);
   2041 		if ( INB(bktr, BKTR_E_CONTROL) & BT848_E_CONTROL_SAT_V_MSB )
   2042 			tmp_int |= BIT_EIGHT_HIGH;
   2043 		*(int*)arg = tmp_int;
   2044 		break;
   2045 
   2046 	/*  */
   2047 	case BT848_SVSAT:	/* set chroma V saturation */
   2048 		tmp_int = *(int*)arg;
   2049 
   2050 		temp = INB(bktr, BKTR_E_CONTROL);
   2051 		temp1 = INB(bktr, BKTR_O_CONTROL);
   2052 		if ( tmp_int & BIT_EIGHT_HIGH) {
   2053 			temp |= BT848_E_CONTROL_SAT_V_MSB;
   2054 			temp1 |= BT848_O_CONTROL_SAT_V_MSB;
   2055 		}
   2056 		else {
   2057 			temp &= ~BT848_E_CONTROL_SAT_V_MSB;
   2058 			temp1 &= ~BT848_O_CONTROL_SAT_V_MSB;
   2059 		}
   2060 
   2061 		OUTB(bktr, BKTR_SAT_V_LO, (u_char)(tmp_int & 0xff));
   2062 		OUTB(bktr, BKTR_E_CONTROL, temp);
   2063 		OUTB(bktr, BKTR_O_CONTROL, temp1);
   2064 		break;
   2065 
   2066 	case BT848_GVSAT:	/* get chroma V saturation */
   2067 		tmp_int = (int)INB(bktr, BKTR_SAT_V_LO) & 0xff;
   2068 		if ( INB(bktr, BKTR_E_CONTROL) & BT848_E_CONTROL_SAT_V_MSB )
   2069 			tmp_int |= BIT_EIGHT_HIGH;
   2070 		*(int*)arg = tmp_int;
   2071 		break;
   2072 
   2073 	/*  */
   2074 	case BT848_SUSAT:	/* set chroma U saturation */
   2075 		tmp_int = *(int*)arg;
   2076 
   2077 		temp = INB(bktr, BKTR_E_CONTROL);
   2078 		temp1 = INB(bktr, BKTR_O_CONTROL);
   2079 		if ( tmp_int & BIT_EIGHT_HIGH ) {
   2080 			temp |= BT848_E_CONTROL_SAT_U_MSB;
   2081 			temp1 |= BT848_O_CONTROL_SAT_U_MSB;
   2082 		}
   2083 		else {
   2084 			temp &= ~BT848_E_CONTROL_SAT_U_MSB;
   2085 			temp1 &= ~BT848_O_CONTROL_SAT_U_MSB;
   2086 		}
   2087 
   2088 		OUTB(bktr, BKTR_SAT_U_LO, (u_char)(tmp_int & 0xff));
   2089 		OUTB(bktr, BKTR_E_CONTROL, temp);
   2090 		OUTB(bktr, BKTR_O_CONTROL, temp1);
   2091 		break;
   2092 
   2093 	case BT848_GUSAT:	/* get chroma U saturation */
   2094 		tmp_int = (int)INB(bktr, BKTR_SAT_U_LO) & 0xff;
   2095 		if ( INB(bktr, BKTR_E_CONTROL) & BT848_E_CONTROL_SAT_U_MSB )
   2096 			tmp_int |= BIT_EIGHT_HIGH;
   2097 		*(int*)arg = tmp_int;
   2098 		break;
   2099 
   2100 /* lr 970528 luma notch etc - 3 high bits of e_control/o_control */
   2101 
   2102 	case BT848_SLNOTCH:	/* set luma notch */
   2103 		tmp_int = (*(int *)arg & 0x7) << 5 ;
   2104 		OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL) & ~0xe0);
   2105 		OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_O_CONTROL) & ~0xe0);
   2106 		OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL) | tmp_int);
   2107 		OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_O_CONTROL) | tmp_int);
   2108 		break;
   2109 
   2110 	case BT848_GLNOTCH:	/* get luma notch */
   2111 		*(int *)arg = (int) ( (INB(bktr, BKTR_E_CONTROL) & 0xe0) >> 5) ;
   2112 		break;
   2113 
   2114 
   2115 	/*  */
   2116 	case BT848_SCONT:	/* set contrast */
   2117 		tmp_int = *(int*)arg;
   2118 
   2119 		temp = INB(bktr, BKTR_E_CONTROL);
   2120 		temp1 = INB(bktr, BKTR_O_CONTROL);
   2121 		if ( tmp_int & BIT_EIGHT_HIGH ) {
   2122 			temp |= BT848_E_CONTROL_CON_MSB;
   2123 			temp1 |= BT848_O_CONTROL_CON_MSB;
   2124 		}
   2125 		else {
   2126 			temp &= ~BT848_E_CONTROL_CON_MSB;
   2127 			temp1 &= ~BT848_O_CONTROL_CON_MSB;
   2128 		}
   2129 
   2130 		OUTB(bktr, BKTR_CONTRAST_LO, (u_char)(tmp_int & 0xff));
   2131 		OUTB(bktr, BKTR_E_CONTROL, temp);
   2132 		OUTB(bktr, BKTR_O_CONTROL, temp1);
   2133 		break;
   2134 
   2135 	case BT848_GCONT:	/* get contrast */
   2136 		tmp_int = (int)INB(bktr, BKTR_CONTRAST_LO) & 0xff;
   2137 		if ( INB(bktr, BKTR_E_CONTROL) & BT848_E_CONTROL_CON_MSB )
   2138 			tmp_int |= BIT_EIGHT_HIGH;
   2139 		*(int*)arg = tmp_int;
   2140 		break;
   2141 
   2142 		/*  FIXME:  SCBARS and CCBARS require a valid int *        */
   2143 		/*    argument to succeed, but its not used; consider      */
   2144 		/*    using the arg to store the on/off state so           */
   2145 		/*    there's only one ioctl() needed to turn cbars on/off */
   2146 	case BT848_SCBARS:	/* set colorbar output */
   2147 		OUTB(bktr, BKTR_COLOR_CTL, INB(bktr, BKTR_COLOR_CTL) | BT848_COLOR_CTL_COLOR_BARS);
   2148 		break;
   2149 
   2150 	case BT848_CCBARS:	/* clear colorbar output */
   2151 		OUTB(bktr, BKTR_COLOR_CTL, INB(bktr, BKTR_COLOR_CTL) & ~(BT848_COLOR_CTL_COLOR_BARS));
   2152 		break;
   2153 
   2154 	case BT848_GAUDIO:	/* get audio channel */
   2155 		temp = bktr->audio_mux_select;
   2156 		if ( bktr->audio_mute_state == TRUE )
   2157 			temp |= AUDIO_MUTE;
   2158 		*(int*)arg = temp;
   2159 		break;
   2160 
   2161 	case BT848_SBTSC:	/* set audio channel */
   2162 		if ( set_BTSC( bktr, *(int*)arg ) < 0 )
   2163 			return( EIO );
   2164 		break;
   2165 
   2166 	case BT848_WEEPROM:	/* write eeprom */
   2167 		offset = (((struct eeProm *)arg)->offset);
   2168 		count = (((struct eeProm *)arg)->count);
   2169 		buf = &(((struct eeProm *)arg)->bytes[ 0 ]);
   2170 		if ( writeEEProm( bktr, offset, count, buf ) < 0 )
   2171 			return( EIO );
   2172 		break;
   2173 
   2174 	case BT848_REEPROM:	/* read eeprom */
   2175 		offset = (((struct eeProm *)arg)->offset);
   2176 		count = (((struct eeProm *)arg)->count);
   2177 		buf = &(((struct eeProm *)arg)->bytes[ 0 ]);
   2178 		if ( readEEProm( bktr, offset, count, buf ) < 0 )
   2179 			return( EIO );
   2180 		break;
   2181 
   2182 	case BT848_SIGNATURE:
   2183 		offset = (((struct eeProm *)arg)->offset);
   2184 		count = (((struct eeProm *)arg)->count);
   2185 		buf = &(((struct eeProm *)arg)->bytes[ 0 ]);
   2186 		if ( signCard( bktr, offset, count, buf ) < 0 )
   2187 			return( EIO );
   2188 		break;
   2189 
   2190         /* Ioctl's for direct gpio access */
   2191 #ifdef BKTR_GPIO_ACCESS
   2192         case BT848_GPIO_GET_EN:
   2193                 *(int*)arg = INL(bktr, BKTR_GPIO_OUT_EN);
   2194                 break;
   2195 
   2196         case BT848_GPIO_SET_EN:
   2197                 OUTL(bktr, BKTR_GPIO_OUT_EN, *(int*)arg);
   2198                 break;
   2199 
   2200         case BT848_GPIO_GET_DATA:
   2201                 *(int*)arg = INL(bktr, BKTR_GPIO_DATA);
   2202                 break;
   2203 
   2204         case BT848_GPIO_SET_DATA:
   2205                 OUTL(bktr, BKTR_GPIO_DATA, *(int*)arg);
   2206                 break;
   2207 #endif /* BKTR_GPIO_ACCESS */
   2208 
   2209 	/* Ioctl's for running the tuner device in radio mode		*/
   2210 
   2211 	case RADIO_GETMODE:
   2212             *(unsigned char *)arg = bktr->tuner.radio_mode;
   2213 	    break;
   2214 
   2215 	case RADIO_SETMODE:
   2216             bktr->tuner.radio_mode = *(unsigned char *)arg;
   2217             break;
   2218 
   2219  	case RADIO_GETFREQ:
   2220             *(unsigned long *)arg = bktr->tuner.frequency;
   2221             break;
   2222 
   2223 	case RADIO_SETFREQ:
   2224 	    /* The argument to this ioctl is NOT freq*16. It is
   2225 	    ** freq*100.
   2226 	    */
   2227 
   2228             temp=(int)*(unsigned long *)arg;
   2229 
   2230 #ifdef BKTR_RADIO_DEBUG
   2231 	    printf("%s: arg=%d temp=%d\n", bktr_name(bktr),
   2232 		   (int)*(unsigned long *)arg, temp);
   2233 #endif
   2234 
   2235 #ifndef BKTR_RADIO_NOFREQCHECK
   2236 	    /* According to the spec. sheet the band: 87.5MHz-108MHz	*/
   2237 	    /* is supported.						*/
   2238 	    if(temp<8750 || temp>10800) {
   2239 	      printf("%s: Radio frequency out of range\n", bktr_name(bktr));
   2240 	      return(EINVAL);
   2241 	      }
   2242 #endif
   2243 	    temp_mute( bktr, TRUE );
   2244 	    temp = tv_freq( bktr, temp, FM_RADIO_FREQUENCY );
   2245 	    temp_mute( bktr, FALSE );
   2246 #ifdef BKTR_RADIO_DEBUG
   2247   if(temp)
   2248     printf("%s: tv_freq returned: %d\n", bktr_name(bktr), temp);
   2249 #endif
   2250 	    if ( temp < 0 )
   2251 		    return( EINVAL );
   2252 	    *(unsigned long *)arg = temp;
   2253 	    break;
   2254 
   2255 	/* Luigi's I2CWR ioctl */
   2256 	case BT848_I2CWR:
   2257 		par = *(u_long *)arg;
   2258 		write = (par >> 24) & 0xff ;
   2259 		i2c_addr = (par >> 16) & 0xff ;
   2260 		i2c_port = (par >> 8) & 0xff ;
   2261 		data = (par) & 0xff ;
   2262 
   2263 		if (write) {
   2264 			i2cWrite( bktr, i2c_addr, i2c_port, data);
   2265 		} else {
   2266 			data = i2cRead( bktr, i2c_addr);
   2267 		}
   2268 		*(u_long *)arg = (par & 0xffffff00) | ( data & 0xff );
   2269 		break;
   2270 
   2271 
   2272 #ifdef BT848_MSP_READ
   2273 	/* I2C ioctls to allow userland access to the MSP chip */
   2274 	case BT848_MSP_READ:
   2275 		{
   2276 		struct bktr_msp_control *msp;
   2277 		msp = (struct bktr_msp_control *) arg;
   2278 		msp->data = msp_dpl_read(bktr, bktr->msp_addr,
   2279 		                         msp->function, msp->address);
   2280 		break;
   2281 		}
   2282 
   2283 	case BT848_MSP_WRITE:
   2284 		{
   2285 		struct bktr_msp_control *msp;
   2286 		msp = (struct bktr_msp_control *) arg;
   2287 		msp_dpl_write(bktr, bktr->msp_addr, msp->function,
   2288 		             msp->address, msp->data );
   2289 		break;
   2290 		}
   2291 
   2292 	case BT848_MSP_RESET:
   2293 		msp_dpl_reset(bktr, bktr->msp_addr);
   2294 		break;
   2295 #endif
   2296 
   2297 	default:
   2298 		return common_ioctl( bktr, cmd, arg );
   2299 	}
   2300 
   2301 	return( 0 );
   2302 }
   2303 
   2304 
   2305 /*
   2306  * common ioctls
   2307  */
   2308 int
   2309 common_ioctl( bktr_ptr_t bktr, ioctl_cmd_t cmd, caddr_t arg )
   2310 {
   2311         int                           pixfmt;
   2312 	unsigned int	              temp;
   2313 	struct meteor_pixfmt          *pf_pub;
   2314 
   2315 	switch (cmd) {
   2316 
   2317 	case METEORSINPUT:	/* set input device */
   2318 		/*Bt848 has 3 MUX Inputs. Bt848A/849A/878/879 has 4 MUX Inputs*/
   2319 		/* On the original bt848 boards, */
   2320 		/*   Tuner is MUX0, RCA is MUX1, S-Video is MUX2 */
   2321 		/* On the Hauppauge bt878 boards, */
   2322 		/*   Tuner is MUX0, RCA is MUX3 */
   2323 		/* Unfortunatly Meteor driver codes DEV_RCA as DEV_0, so we */
   2324 		/* stick with this system in our Meteor Emulation */
   2325 
   2326 		switch(*(unsigned long *)arg & METEOR_DEV_MASK) {
   2327 
   2328 		/* this is the RCA video input */
   2329 		case 0:		/* default */
   2330 		case METEOR_INPUT_DEV0:
   2331 		  /* METEOR_INPUT_DEV_RCA: */
   2332 		        bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
   2333 			  | METEOR_DEV0;
   2334 			OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM)
   2335 			                 & ~BT848_IFORM_MUXSEL);
   2336 
   2337 			/* work around for new Hauppauge 878 cards */
   2338 			if ((bktr->card.card_id == CARD_HAUPPAUGE) &&
   2339 				(bktr->id==BROOKTREE_878 ||
   2340 				 bktr->id==BROOKTREE_879) )
   2341 				OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) | BT848_IFORM_M_MUX3);
   2342 			else
   2343 				OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) | BT848_IFORM_M_MUX1);
   2344 
   2345 			OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL) & ~BT848_E_CONTROL_COMP);
   2346 			OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_O_CONTROL) & ~BT848_O_CONTROL_COMP);
   2347 			set_audio( bktr, AUDIO_EXTERN );
   2348 			break;
   2349 
   2350 		/* this is the tuner input */
   2351 		case METEOR_INPUT_DEV1:
   2352 			bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
   2353 				| METEOR_DEV1;
   2354 			OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) & ~BT848_IFORM_MUXSEL);
   2355 			OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) | BT848_IFORM_M_MUX0);
   2356 			OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL) & ~BT848_E_CONTROL_COMP);
   2357 			OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_O_CONTROL) & ~BT848_O_CONTROL_COMP);
   2358 			set_audio( bktr, AUDIO_TUNER );
   2359 			break;
   2360 
   2361 		/* this is the S-VHS input, but with a composite camera */
   2362 		case METEOR_INPUT_DEV2:
   2363 			bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
   2364 				| METEOR_DEV2;
   2365 			OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) & ~BT848_IFORM_MUXSEL);
   2366 			OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) | BT848_IFORM_M_MUX2);
   2367 			OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL) & ~BT848_E_CONTROL_COMP);
   2368 			OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_E_CONTROL) & ~BT848_O_CONTROL_COMP);
   2369 			set_audio( bktr, AUDIO_EXTERN );
   2370 			break;
   2371 
   2372 		/* this is the S-VHS input */
   2373 		case METEOR_INPUT_DEV_SVIDEO:
   2374 			bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
   2375 				| METEOR_DEV_SVIDEO;
   2376 			OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) & ~BT848_IFORM_MUXSEL);
   2377 			OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) | BT848_IFORM_M_MUX2);
   2378 			OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL) | BT848_E_CONTROL_COMP);
   2379 			OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_O_CONTROL) | BT848_O_CONTROL_COMP);
   2380 			set_audio( bktr, AUDIO_EXTERN );
   2381 			break;
   2382 
   2383 		case METEOR_INPUT_DEV3:
   2384 		  if ((bktr->id == BROOKTREE_848A) ||
   2385 		      (bktr->id == BROOKTREE_849A) ||
   2386 		      (bktr->id == BROOKTREE_878) ||
   2387 		      (bktr->id == BROOKTREE_879) ) {
   2388 			bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
   2389 				| METEOR_DEV3;
   2390 			OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) & ~BT848_IFORM_MUXSEL);
   2391 
   2392 			/* work around for new Hauppauge 878 cards */
   2393 			if ((bktr->card.card_id == CARD_HAUPPAUGE) &&
   2394 				(bktr->id==BROOKTREE_878 ||
   2395 				 bktr->id==BROOKTREE_879) )
   2396 				OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) | BT848_IFORM_M_MUX1);
   2397 			else
   2398 				OUTB(bktr, BKTR_IFORM, INB(bktr, BKTR_IFORM) | BT848_IFORM_M_MUX3);
   2399 
   2400 			OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL) & ~BT848_E_CONTROL_COMP);
   2401 			OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_O_CONTROL) & ~BT848_O_CONTROL_COMP);
   2402 			set_audio( bktr, AUDIO_EXTERN );
   2403 
   2404 			break;
   2405 		  }
   2406 
   2407 		default:
   2408 			return( EINVAL );
   2409 		}
   2410 		break;
   2411 
   2412 	case METEORGINPUT:	/* get input device */
   2413 		*(u_long *)arg = bktr->flags & METEOR_DEV_MASK;
   2414 		break;
   2415 
   2416 	case METEORSACTPIXFMT:
   2417 		if (( *(int *)arg < 0 ) ||
   2418 		    ( *(int *)arg >= PIXFMT_TABLE_SIZE ))
   2419 			return( EINVAL );
   2420 
   2421 		bktr->pixfmt          = *(int *)arg;
   2422 		OUTB(bktr, BKTR_COLOR_CTL, (INB(bktr, BKTR_COLOR_CTL) & 0xf0)
   2423 		     | pixfmt_swap_flags( bktr->pixfmt ));
   2424 		bktr->pixfmt_compat   = FALSE;
   2425 		break;
   2426 
   2427 	case METEORGACTPIXFMT:
   2428 		*(int *)arg = bktr->pixfmt;
   2429 		break;
   2430 
   2431 	case METEORGSUPPIXFMT :
   2432 		pf_pub = (struct meteor_pixfmt *)arg;
   2433 		pixfmt = pf_pub->index;
   2434 
   2435 		if (( pixfmt < 0 ) || ( pixfmt >= PIXFMT_TABLE_SIZE ))
   2436 			return( EINVAL );
   2437 
   2438 		memcpy( pf_pub, &pixfmt_table[ pixfmt ].public,
   2439 			sizeof( *pf_pub ) );
   2440 
   2441 		/*  Patch in our format index  */
   2442 		pf_pub->index       = pixfmt;
   2443 		break;
   2444 
   2445 #if defined( STATUS_SUM )
   2446 	case BT848_GSTATUS:	/* reap status */
   2447 		{
   2448                 DECLARE_INTR_MASK(s);
   2449 		DISABLE_INTR(s);
   2450 		temp = status_sum;
   2451 		status_sum = 0;
   2452 		ENABLE_INTR(s);
   2453 		*(u_int*)arg = temp;
   2454 		break;
   2455 		}
   2456 #endif /* STATUS_SUM */
   2457 
   2458 	default:
   2459 		return( ENOTTY );
   2460 	}
   2461 
   2462 	return( 0 );
   2463 }
   2464 
   2465 
   2466 
   2467 
   2468 /******************************************************************************
   2469  * bt848 RISC programming routines:
   2470  */
   2471 
   2472 
   2473 /*
   2474  *
   2475  */
   2476 #ifdef BT848_DEBUG
   2477 static int
   2478 dump_bt848( bktr_ptr_t bktr )
   2479 {
   2480 	int	r[60]={
   2481 			   4,    8, 0xc, 0x8c, 0x10, 0x90, 0x14, 0x94,
   2482 			0x18, 0x98, 0x1c, 0x9c, 0x20, 0xa0, 0x24, 0xa4,
   2483 			0x28, 0x2c, 0xac, 0x30, 0x34, 0x38, 0x3c, 0x40,
   2484 			0xc0, 0x48, 0x4c, 0xcc, 0x50, 0xd0, 0xd4, 0x60,
   2485 			0x64, 0x68, 0x6c, 0xec, 0xd8, 0xdc, 0xe0, 0xe4,
   2486 			0,	 0,    0,    0
   2487 		   };
   2488 	int	i;
   2489 
   2490 	for (i = 0; i < 40; i+=4) {
   2491 		printf("%s: Reg:value : \t%x:%x \t%x:%x \t %x:%x \t %x:%x\n",
   2492 		       bktr_name(bktr),
   2493 		       r[i], INL(bktr, r[i]),
   2494 		       r[i+1], INL(bktr, r[i+1]),
   2495 		       r[i+2], INL(bktr, r[i+2]),
   2496 		       r[i+3], INL(bktr, r[i+3]]));
   2497 	}
   2498 
   2499 	printf("%s: INT STAT %x \n", bktr_name(bktr),
   2500 	       INL(bktr, BKTR_INT_STAT));
   2501 	printf("%s: Reg INT_MASK %x \n", bktr_name(bktr),
   2502 	       INL(bktr, BKTR_INT_MASK));
   2503 	printf("%s: Reg GPIO_DMA_CTL %x \n", bktr_name(bktr),
   2504 	       INW(bktr, BKTR_GPIO_DMA_CTL));
   2505 
   2506 	return( 0 );
   2507 }
   2508 
   2509 #endif
   2510 
   2511 /*
   2512  * build write instruction
   2513  */
   2514 #define BKTR_FM1      0x6	/* packed data to follow */
   2515 #define BKTR_FM3      0xe	/* planar data to follow */
   2516 #define BKTR_VRE      0x4	/* Marks the end of the even field */
   2517 #define BKTR_VRO      0xC	/* Marks the end of the odd field */
   2518 #define BKTR_PXV      0x0	/* valid word (never used) */
   2519 #define BKTR_EOL      0x1	/* last dword, 4 bytes */
   2520 #define BKTR_SOL      0x2	/* first dword */
   2521 
   2522 #define OP_WRITE      (0x1 << 28)
   2523 #define OP_SKIP       (0x2 << 28)
   2524 #define OP_WRITEC     (0x5 << 28)
   2525 #define OP_JUMP	      (0x7 << 28)
   2526 #define OP_SYNC	      (0x8 << 28)
   2527 #define OP_WRITE123   (0x9 << 28)
   2528 #define OP_WRITES123  (0xb << 28)
   2529 #define OP_SOL	      (1 << 27)		/* first instr for scanline */
   2530 #define OP_EOL	      (1 << 26)
   2531 
   2532 #define BKTR_RESYNC   (1 << 15)
   2533 #define BKTR_GEN_IRQ  (1 << 24)
   2534 
   2535 /*
   2536  * The RISC status bits can be set/cleared in the RISC programs
   2537  * and tested in the Interrupt Handler
   2538  */
   2539 #define BKTR_SET_RISC_STATUS_BIT0 (1 << 16)
   2540 #define BKTR_SET_RISC_STATUS_BIT1 (1 << 17)
   2541 #define BKTR_SET_RISC_STATUS_BIT2 (1 << 18)
   2542 #define BKTR_SET_RISC_STATUS_BIT3 (1 << 19)
   2543 
   2544 #define BKTR_CLEAR_RISC_STATUS_BIT0 (1 << 20)
   2545 #define BKTR_CLEAR_RISC_STATUS_BIT1 (1 << 21)
   2546 #define BKTR_CLEAR_RISC_STATUS_BIT2 (1 << 22)
   2547 #define BKTR_CLEAR_RISC_STATUS_BIT3 (1 << 23)
   2548 
   2549 #define BKTR_TEST_RISC_STATUS_BIT0 (1 << 28)
   2550 #define BKTR_TEST_RISC_STATUS_BIT1 (1 << 29)
   2551 #define BKTR_TEST_RISC_STATUS_BIT2 (1 << 30)
   2552 #define BKTR_TEST_RISC_STATUS_BIT3 (1 << 31)
   2553 
   2554 bool_t notclipped (bktr_reg_t * bktr, int x, int width) {
   2555     int i;
   2556     bktr_clip_t * clip_node;
   2557     bktr->clip_start = -1;
   2558     bktr->last_y = 0;
   2559     bktr->y = 0;
   2560     bktr->y2 = width;
   2561     bktr->line_length = width;
   2562     bktr->yclip = -1;
   2563     bktr->yclip2 = -1;
   2564     bktr->current_col = 0;
   2565 
   2566     if (bktr->max_clip_node == 0 ) return TRUE;
   2567     clip_node = (bktr_clip_t *) &bktr->clip_list[0];
   2568 
   2569 
   2570     for (i = 0; i < bktr->max_clip_node; i++ ) {
   2571 	clip_node = (bktr_clip_t *) &bktr->clip_list[i];
   2572 	if (x >= clip_node->x_min && x <= clip_node->x_max  ) {
   2573 	    bktr->clip_start = i;
   2574 	    return FALSE;
   2575 	}
   2576     }
   2577 
   2578     return TRUE;
   2579 }
   2580 
   2581 bool_t getline(bktr_reg_t *bktr, int x ) {
   2582     int i, j;
   2583     bktr_clip_t * clip_node ;
   2584 
   2585     if (bktr->line_length == 0 ||
   2586 	bktr->current_col >= bktr->line_length) return FALSE;
   2587 
   2588     bktr->y = min(bktr->last_y, bktr->line_length);
   2589     bktr->y2 = bktr->line_length;
   2590 
   2591     bktr->yclip = bktr->yclip2 = -1;
   2592     for (i = bktr->clip_start; i < bktr->max_clip_node; i++ ) {
   2593 	clip_node = (bktr_clip_t *) &bktr->clip_list[i];
   2594 	if (x >= clip_node->x_min && x <= clip_node->x_max) {
   2595 	    if (bktr->last_y <= clip_node->y_min) {
   2596 		bktr->y =      min(bktr->last_y, bktr->line_length);
   2597 		bktr->y2 =     min(clip_node->y_min, bktr->line_length);
   2598 		bktr->yclip =  min(clip_node->y_min, bktr->line_length);
   2599 		bktr->yclip2 = min(clip_node->y_max, bktr->line_length);
   2600 		bktr->last_y = bktr->yclip2;
   2601 		bktr->clip_start = i;
   2602 
   2603 		for (j = i+1; j  < bktr->max_clip_node; j++ ) {
   2604 		    clip_node = (bktr_clip_t *) &bktr->clip_list[j];
   2605 		    if (x >= clip_node->x_min && x <= clip_node->x_max) {
   2606 			if (bktr->last_y >= clip_node->y_min) {
   2607 			    bktr->yclip2 = min(clip_node->y_max, bktr->line_length);
   2608 			    bktr->last_y = bktr->yclip2;
   2609 			    bktr->clip_start = j;
   2610 			}
   2611 		    } else break  ;
   2612 		}
   2613 		return TRUE;
   2614 	    }
   2615 	}
   2616     }
   2617 
   2618     if (bktr->current_col <= bktr->line_length) {
   2619 	bktr->current_col = bktr->line_length;
   2620 	return TRUE;
   2621     }
   2622     return FALSE;
   2623 }
   2624 
   2625 static bool_t split(bktr_reg_t * bktr, volatile u_long **dma_prog, int width ,
   2626 		    u_long operation, int pixel_width,
   2627 		    volatile u_char ** target_buffer, int cols ) {
   2628 
   2629  u_long flag, flag2;
   2630  const struct meteor_pixfmt *pf = &pixfmt_table[ bktr->pixfmt ].public;
   2631  u_int  skip, start_skip;
   2632 
   2633   /*  For RGB24, we need to align the component in FIFO Byte Lane 0         */
   2634   /*    to the 1st byte in the mem dword containing our start addr.         */
   2635   /*    BTW, we know this pixfmt's 1st byte is Blue; thus the start addr    */
   2636   /*     must be Blue.                                                      */
   2637   start_skip = 0;
   2638   if (( pf->type == METEOR_PIXTYPE_RGB ) && ( pf->Bpp == 3 ))
   2639 	  switch ( ((uintptr_t) (volatile void *) *target_buffer) % 4 ) {
   2640 	  case 2 : start_skip = 4 ; break;
   2641 	  case 1 : start_skip = 8 ; break;
   2642 	  }
   2643 
   2644  if ((width * pixel_width) < DMA_BT848_SPLIT ) {
   2645      if (  width == cols) {
   2646 	 flag = OP_SOL | OP_EOL;
   2647        } else if (bktr->current_col == 0 ) {
   2648 	    flag  = OP_SOL;
   2649        } else if (bktr->current_col == cols) {
   2650 	    flag = OP_EOL;
   2651        } else flag = 0;
   2652 
   2653      skip = 0;
   2654      if (( flag & OP_SOL ) && ( start_skip > 0 )) {
   2655 	     *(*dma_prog)++ = OP_SKIP | OP_SOL | start_skip;
   2656 	     flag &= ~OP_SOL;
   2657 	     skip = start_skip;
   2658      }
   2659 
   2660      *(*dma_prog)++ = operation | flag  | (width * pixel_width - skip);
   2661      if (operation != OP_SKIP )
   2662 	 *(*dma_prog)++ = (uintptr_t) (volatile void *) *target_buffer;
   2663 
   2664      *target_buffer += width * pixel_width;
   2665      bktr->current_col += width;
   2666 
   2667  } else {
   2668 
   2669 	if (bktr->current_col == 0 && width == cols) {
   2670 	    flag = OP_SOL ;
   2671 	    flag2 = OP_EOL;
   2672         } else if (bktr->current_col == 0 ) {
   2673 	    flag = OP_SOL;
   2674 	    flag2 = 0;
   2675 	} else if (bktr->current_col >= cols)  {
   2676 	    flag =  0;
   2677 	    flag2 = OP_EOL;
   2678 	} else {
   2679 	    flag =  0;
   2680 	    flag2 = 0;
   2681 	}
   2682 
   2683 	skip = 0;
   2684 	if (( flag & OP_SOL ) && ( start_skip > 0 )) {
   2685 		*(*dma_prog)++ = OP_SKIP | OP_SOL | start_skip;
   2686 		flag &= ~OP_SOL;
   2687 		skip = start_skip;
   2688 	}
   2689 
   2690 	*(*dma_prog)++ = operation  | flag |
   2691 	      (width * pixel_width / 2 - skip);
   2692 	if (operation != OP_SKIP )
   2693 	      *(*dma_prog)++ = (uintptr_t) (volatile void *) *target_buffer ;
   2694 	*target_buffer +=  (width * pixel_width / 2) ;
   2695 
   2696 	if ( operation == OP_WRITE )
   2697 		operation = OP_WRITEC;
   2698 	*(*dma_prog)++ = operation | flag2 |
   2699 	    (width * pixel_width / 2);
   2700 	*target_buffer +=  (width * pixel_width / 2) ;
   2701 	  bktr->current_col += width;
   2702 
   2703     }
   2704  return TRUE;
   2705 }
   2706 
   2707 
   2708 /*
   2709  * Generate the RISC instructions to capture both VBI and video images
   2710  */
   2711 static void
   2712 rgb_vbi_prog( bktr_ptr_t bktr, char i_flag, int cols, int rows, int interlace )
   2713 {
   2714 	int			i;
   2715 	volatile u_long		target_buffer, buffer, target,width;
   2716 	volatile u_long		pitch;
   2717 	volatile u_long		*dma_prog;	/* DMA prog is an array of
   2718 						32 bit RISC instructions */
   2719 	volatile u_long		*loop_point;
   2720         const struct meteor_pixfmt_internal *pf_int = &pixfmt_table[ bktr->pixfmt ];
   2721 	u_int                   Bpp = pf_int->public.Bpp;
   2722 	unsigned int            vbisamples;     /* VBI samples per line */
   2723 	unsigned int            vbilines;       /* VBI lines per field */
   2724 	unsigned int            num_dwords;     /* DWORDS per line */
   2725 
   2726 	vbisamples = format_params[bktr->format_params].vbi_num_samples;
   2727 	vbilines   = format_params[bktr->format_params].vbi_num_lines;
   2728 	num_dwords = vbisamples/4;
   2729 
   2730 	OUTB(bktr, BKTR_COLOR_FMT, pf_int->color_fmt);
   2731 	OUTB(bktr, BKTR_ADC, SYNC_LEVEL);
   2732 	OUTB(bktr, BKTR_VBI_PACK_SIZE, ((num_dwords)) & 0xff);
   2733 	OUTB(bktr, BKTR_VBI_PACK_DEL, ((num_dwords)>> 8) & 0x01); /* no hdelay    */
   2734 							    /* no ext frame */
   2735 
   2736 	OUTB(bktr, BKTR_OFORM, 0x00);
   2737 
   2738  	OUTB(bktr, BKTR_E_VSCALE_HI, INB(bktr, BKTR_E_VSCALE_HI) | 0x40); /* set chroma comb */
   2739  	OUTB(bktr, BKTR_O_VSCALE_HI, INB(bktr, BKTR_O_VSCALE_HI) | 0x40);
   2740 	OUTB(bktr, BKTR_E_VSCALE_HI, INB(bktr, BKTR_E_VSCALE_HI) & ~0x80); /* clear Ycomb */
   2741 	OUTB(bktr, BKTR_O_VSCALE_HI, INB(bktr, BKTR_O_VSCALE_HI) & ~0x80);
   2742 
   2743  	/* disable gamma correction removal */
   2744  	OUTB(bktr, BKTR_COLOR_CTL, INB(bktr, BKTR_COLOR_CTL) | BT848_COLOR_CTL_GAMMA);
   2745 
   2746 	if (cols > 385 ) {
   2747 	    OUTB(bktr, BKTR_E_VTC, 0);
   2748 	    OUTB(bktr, BKTR_O_VTC, 0);
   2749 	} else {
   2750 	    OUTB(bktr, BKTR_E_VTC, 1);
   2751 	    OUTB(bktr, BKTR_O_VTC, 1);
   2752 	}
   2753 	bktr->capcontrol = 3 << 2 |  3;
   2754 
   2755 	dma_prog = (u_long *) bktr->dma_prog;
   2756 
   2757 	/* Construct Write */
   2758 
   2759 	if (bktr->video.addr) {
   2760 		target_buffer = (u_long) bktr->video.addr;
   2761 		pitch = bktr->video.width;
   2762 	}
   2763 	else {
   2764 		target_buffer = (u_long) vtophys(bktr->bigbuf);
   2765 		pitch = cols*Bpp;
   2766 	}
   2767 
   2768 	buffer = target_buffer;
   2769 
   2770 	/* Wait for the VRE sync marking the end of the Even and
   2771 	 * the start of the Odd field. Resync here.
   2772 	 */
   2773 	*dma_prog++ = OP_SYNC | BKTR_RESYNC |BKTR_VRE;
   2774 	*dma_prog++ = 0;
   2775 
   2776 	loop_point = dma_prog;
   2777 
   2778 	/* store the VBI data */
   2779 	/* look for sync with packed data */
   2780 	*dma_prog++ = OP_SYNC | BKTR_FM1;
   2781 	*dma_prog++ = 0;
   2782 	for(i = 0; i < vbilines; i++) {
   2783 		*dma_prog++ = OP_WRITE | OP_SOL | OP_EOL | vbisamples;
   2784 		*dma_prog++ = (u_long) vtophys(bktr->vbidata +
   2785 					(i * VBI_LINE_SIZE));
   2786 	}
   2787 
   2788 	if ( (i_flag == 2/*Odd*/) || (i_flag==3) /*interlaced*/ ) {
   2789 		/* store the Odd field video image */
   2790 		/* look for sync with packed data */
   2791 		*dma_prog++ = OP_SYNC  | BKTR_FM1;
   2792 		*dma_prog++ = 0;  /* NULL WORD */
   2793 		width = cols;
   2794 		for (i = 0; i < (rows/interlace); i++) {
   2795 		    target = target_buffer;
   2796 		    if ( notclipped(bktr, i, width)) {
   2797 			split(bktr, (volatile u_long **) &dma_prog,
   2798 			      bktr->y2 - bktr->y, OP_WRITE,
   2799 			      Bpp, (volatile u_char **) &target,  cols);
   2800 
   2801 		    } else {
   2802 			while(getline(bktr, i)) {
   2803 			    if (bktr->y != bktr->y2 ) {
   2804 				split(bktr, (volatile u_long **) &dma_prog,
   2805 				      bktr->y2 - bktr->y, OP_WRITE,
   2806 				      Bpp, (volatile u_char **) &target, cols);
   2807 			    }
   2808 			    if (bktr->yclip != bktr->yclip2 ) {
   2809 				split(bktr,(volatile u_long **) &dma_prog,
   2810 				      bktr->yclip2 - bktr->yclip,
   2811 				      OP_SKIP,
   2812 				      Bpp, (volatile u_char **) &target,  cols);
   2813 			    }
   2814 			}
   2815 
   2816 		    }
   2817 
   2818 		    target_buffer += interlace * pitch;
   2819 
   2820 		}
   2821 
   2822 	} /* end if */
   2823 
   2824 	/* Grab the Even field */
   2825 	/* Look for the VRO, end of Odd field, marker */
   2826 	*dma_prog++ = OP_SYNC | BKTR_GEN_IRQ | BKTR_RESYNC | BKTR_VRO;
   2827 	*dma_prog++ = 0;  /* NULL WORD */
   2828 
   2829 	/* store the VBI data */
   2830 	/* look for sync with packed data */
   2831 	*dma_prog++ = OP_SYNC | BKTR_FM1;
   2832 	*dma_prog++ = 0;
   2833 	for(i = 0; i < vbilines; i++) {
   2834 		*dma_prog++ = OP_WRITE | OP_SOL | OP_EOL | vbisamples;
   2835 		*dma_prog++ = (u_long) vtophys(bktr->vbidata +
   2836 				((i+MAX_VBI_LINES) * VBI_LINE_SIZE));
   2837 	}
   2838 
   2839 	/* store the video image */
   2840 	if (i_flag == 1) /*Even Only*/
   2841 	        target_buffer = buffer;
   2842 	if (i_flag == 3) /*interlaced*/
   2843 	        target_buffer = buffer+pitch;
   2844 
   2845 
   2846 	if ((i_flag == 1) /*Even Only*/ || (i_flag==3) /*interlaced*/) {
   2847 		/* look for sync with packed data */
   2848 		*dma_prog++ = OP_SYNC | BKTR_FM1;
   2849 		*dma_prog++ = 0;  /* NULL WORD */
   2850 		width = cols;
   2851 		for (i = 0; i < (rows/interlace); i++) {
   2852 		    target = target_buffer;
   2853 		    if ( notclipped(bktr, i, width)) {
   2854 			split(bktr, (volatile u_long **) &dma_prog,
   2855 			      bktr->y2 - bktr->y, OP_WRITE,
   2856 			      Bpp, (volatile u_char **) &target,  cols);
   2857 		    } else {
   2858 			while(getline(bktr, i)) {
   2859 			    if (bktr->y != bktr->y2 ) {
   2860 				split(bktr, (volatile u_long **) &dma_prog,
   2861 				      bktr->y2 - bktr->y, OP_WRITE,
   2862 				      Bpp, (volatile u_char **) &target,
   2863 				      cols);
   2864 			    }
   2865 			    if (bktr->yclip != bktr->yclip2 ) {
   2866 				split(bktr, (volatile u_long **) &dma_prog,
   2867 				      bktr->yclip2 - bktr->yclip, OP_SKIP,
   2868 				      Bpp, (volatile u_char **)  &target,  cols);
   2869 			    }
   2870 
   2871 			}
   2872 
   2873 		    }
   2874 
   2875 		    target_buffer += interlace * pitch;
   2876 
   2877 		}
   2878 	}
   2879 
   2880 	/* Look for end of 'Even Field' */
   2881 	*dma_prog++ = OP_SYNC | BKTR_GEN_IRQ | BKTR_RESYNC | BKTR_VRE;
   2882 	*dma_prog++ = 0;  /* NULL WORD */
   2883 
   2884 	*dma_prog++ = OP_JUMP ;
   2885 	*dma_prog++ = (u_long ) vtophys((vaddr_t)loop_point) ;
   2886 	*dma_prog++ = 0;  /* NULL WORD */
   2887 
   2888 }
   2889 
   2890 
   2891 
   2892 
   2893 static void
   2894 rgb_prog( bktr_ptr_t bktr, char i_flag, int cols, int rows, int interlace )
   2895 {
   2896 	int			i;
   2897 	volatile u_long		target_buffer, buffer, target,width;
   2898 	volatile u_long		pitch;
   2899 	volatile  u_long	*dma_prog;
   2900         const struct meteor_pixfmt_internal *pf_int = &pixfmt_table[ bktr->pixfmt ];
   2901 	u_int                   Bpp = pf_int->public.Bpp;
   2902 
   2903 	OUTB(bktr, BKTR_COLOR_FMT, pf_int->color_fmt);
   2904 	OUTB(bktr, BKTR_VBI_PACK_SIZE, 0);
   2905 	OUTB(bktr, BKTR_VBI_PACK_DEL, 0);
   2906 	OUTB(bktr, BKTR_ADC, SYNC_LEVEL);
   2907 
   2908 	OUTB(bktr, BKTR_OFORM, 0x00);
   2909 
   2910  	OUTB(bktr, BKTR_E_VSCALE_HI, INB(bktr, BKTR_E_VSCALE_HI) | 0x40); /* set chroma comb */
   2911  	OUTB(bktr, BKTR_O_VSCALE_HI, INB(bktr, BKTR_O_VSCALE_HI) | 0x40);
   2912 	OUTB(bktr, BKTR_E_VSCALE_HI, INB(bktr, BKTR_E_VSCALE_HI) & ~0x80); /* clear Ycomb */
   2913 	OUTB(bktr, BKTR_O_VSCALE_HI, INB(bktr, BKTR_O_VSCALE_HI) & ~0x80);
   2914 
   2915  	/* disable gamma correction removal */
   2916 	OUTB(bktr, BKTR_COLOR_CTL, INB(bktr, BKTR_COLOR_CTL) | BT848_COLOR_CTL_GAMMA);
   2917 
   2918 	if (cols > 385 ) {
   2919 	    OUTB(bktr, BKTR_E_VTC, 0);
   2920 	    OUTB(bktr, BKTR_O_VTC, 0);
   2921 	} else {
   2922 	    OUTB(bktr, BKTR_E_VTC, 1);
   2923 	    OUTB(bktr, BKTR_O_VTC, 1);
   2924 	}
   2925 	bktr->capcontrol = 3 << 2 |  3;
   2926 
   2927 	dma_prog = (u_long *) bktr->dma_prog;
   2928 
   2929 	/* Construct Write */
   2930 
   2931 	if (bktr->video.addr) {
   2932 		target_buffer = (u_long) bktr->video.addr;
   2933 		pitch = bktr->video.width;
   2934 	}
   2935 	else {
   2936 		target_buffer = (u_long) vtophys(bktr->bigbuf);
   2937 		pitch = cols*Bpp;
   2938 	}
   2939 
   2940 	buffer = target_buffer;
   2941 
   2942 	/* contruct sync : for video packet format */
   2943 	*dma_prog++ = OP_SYNC  | BKTR_RESYNC | BKTR_FM1;
   2944 
   2945 	/* sync, mode indicator packed data */
   2946 	*dma_prog++ = 0;  /* NULL WORD */
   2947 	width = cols;
   2948 	for (i = 0; i < (rows/interlace); i++) {
   2949 	    target = target_buffer;
   2950 	    if ( notclipped(bktr, i, width)) {
   2951 		split(bktr, (volatile u_long **) &dma_prog,
   2952 		      bktr->y2 - bktr->y, OP_WRITE,
   2953 		      Bpp, (volatile u_char **) &target,  cols);
   2954 
   2955 	    } else {
   2956 		while(getline(bktr, i)) {
   2957 		    if (bktr->y != bktr->y2 ) {
   2958 			split(bktr, (volatile u_long **) &dma_prog,
   2959 			      bktr->y2 - bktr->y, OP_WRITE,
   2960 			      Bpp, (volatile u_char **) &target, cols);
   2961 		    }
   2962 		    if (bktr->yclip != bktr->yclip2 ) {
   2963 			split(bktr,(volatile u_long **) &dma_prog,
   2964 			      bktr->yclip2 - bktr->yclip,
   2965 			      OP_SKIP,
   2966 			      Bpp, (volatile u_char **) &target,  cols);
   2967 		    }
   2968 		}
   2969 
   2970 	    }
   2971 
   2972 	    target_buffer += interlace * pitch;
   2973 
   2974 	}
   2975 
   2976 	switch (i_flag) {
   2977 	case 1:
   2978 		/* sync vre */
   2979 		*dma_prog++ = OP_SYNC | BKTR_GEN_IRQ | BKTR_VRO;
   2980 		*dma_prog++ = 0;  /* NULL WORD */
   2981 
   2982 		*dma_prog++ = OP_JUMP;
   2983 		*dma_prog++ = (u_long ) vtophys(bktr->dma_prog);
   2984 		return;
   2985 
   2986 	case 2:
   2987 		/* sync vro */
   2988 		*dma_prog++ = OP_SYNC | BKTR_GEN_IRQ | BKTR_VRE;
   2989 		*dma_prog++ = 0;  /* NULL WORD */
   2990 
   2991 		*dma_prog++ = OP_JUMP;
   2992 		*dma_prog++ = (u_long ) vtophys(bktr->dma_prog);
   2993 		return;
   2994 
   2995 	case 3:
   2996 		/* sync vro */
   2997 		*dma_prog++ = OP_SYNC | BKTR_GEN_IRQ | BKTR_RESYNC | BKTR_VRO;
   2998 		*dma_prog++ = 0;  /* NULL WORD */
   2999 		*dma_prog++ = OP_JUMP; ;
   3000 		*dma_prog = (u_long ) vtophys(bktr->odd_dma_prog);
   3001 		break;
   3002 	}
   3003 
   3004 	if (interlace == 2) {
   3005 
   3006 	        target_buffer = buffer + pitch;
   3007 
   3008 		dma_prog = (u_long *) bktr->odd_dma_prog;
   3009 
   3010 		/* sync vre IRQ bit */
   3011 		*dma_prog++ = OP_SYNC | BKTR_RESYNC | BKTR_FM1;
   3012 		*dma_prog++ = 0;  /* NULL WORD */
   3013                 width = cols;
   3014 		for (i = 0; i < (rows/interlace); i++) {
   3015 		    target = target_buffer;
   3016 		    if ( notclipped(bktr, i, width)) {
   3017 			split(bktr, (volatile u_long **) &dma_prog,
   3018 			      bktr->y2 - bktr->y, OP_WRITE,
   3019 			      Bpp, (volatile u_char **) &target,  cols);
   3020 		    } else {
   3021 			while(getline(bktr, i)) {
   3022 			    if (bktr->y != bktr->y2 ) {
   3023 				split(bktr, (volatile u_long **) &dma_prog,
   3024 				      bktr->y2 - bktr->y, OP_WRITE,
   3025 				      Bpp, (volatile u_char **) &target,
   3026 				      cols);
   3027 			    }
   3028 			    if (bktr->yclip != bktr->yclip2 ) {
   3029 				split(bktr, (volatile u_long **) &dma_prog,
   3030 				      bktr->yclip2 - bktr->yclip, OP_SKIP,
   3031 				      Bpp, (volatile u_char **)  &target,  cols);
   3032 			    }
   3033 
   3034 			}
   3035 
   3036 		    }
   3037 
   3038 		    target_buffer += interlace * pitch;
   3039 
   3040 		}
   3041 	}
   3042 
   3043 	/* sync vre IRQ bit */
   3044 	*dma_prog++ = OP_SYNC | BKTR_GEN_IRQ | BKTR_RESYNC | BKTR_VRE;
   3045 	*dma_prog++ = 0;  /* NULL WORD */
   3046 	*dma_prog++ = OP_JUMP ;
   3047 	*dma_prog++ = (u_long ) vtophys(bktr->dma_prog) ;
   3048 	*dma_prog++ = 0;  /* NULL WORD */
   3049 }
   3050 
   3051 
   3052 /*
   3053  *
   3054  */
   3055 static void
   3056 yuvpack_prog( bktr_ptr_t bktr, char i_flag,
   3057 	      int cols, int rows, int interlace )
   3058 {
   3059 	int			i;
   3060 	volatile unsigned int	inst;
   3061 	volatile unsigned int	inst3;
   3062 	volatile u_long		target_buffer, buffer;
   3063 	volatile  u_long	*dma_prog;
   3064         const struct meteor_pixfmt_internal *pf_int = &pixfmt_table[ bktr->pixfmt ];
   3065 	int			b;
   3066 
   3067 	OUTB(bktr, BKTR_COLOR_FMT, pf_int->color_fmt);
   3068 
   3069 	OUTB(bktr, BKTR_E_SCLOOP, INB(bktr, BKTR_E_SCLOOP) | BT848_E_SCLOOP_CAGC); /* enable chroma comb */
   3070 	OUTB(bktr, BKTR_O_SCLOOP, INB(bktr, BKTR_O_SCLOOP) | BT848_O_SCLOOP_CAGC);
   3071 
   3072 	OUTB(bktr, BKTR_COLOR_CTL, INB(bktr, BKTR_COLOR_CTL) | BT848_COLOR_CTL_RGB_DED | BT848_COLOR_CTL_GAMMA);
   3073 	OUTB(bktr, BKTR_ADC, SYNC_LEVEL);
   3074 
   3075 	bktr->capcontrol =   1 << 6 | 1 << 4 | 1 << 2 | 3;
   3076 	bktr->capcontrol = 3 << 2 |  3;
   3077 
   3078 	dma_prog = (u_long *) bktr->dma_prog;
   3079 
   3080 	/* Construct Write */
   3081 
   3082 	/* write , sol, eol */
   3083 	inst = OP_WRITE	 | OP_SOL | (cols);
   3084 	/* write , sol, eol */
   3085 	inst3 = OP_WRITE | OP_EOL | (cols);
   3086 
   3087 	if (bktr->video.addr)
   3088 		target_buffer = (u_long) bktr->video.addr;
   3089 	else
   3090 		target_buffer = (u_long) vtophys(bktr->bigbuf);
   3091 
   3092 	buffer = target_buffer;
   3093 
   3094 	/* contruct sync : for video packet format */
   3095 	/* sync, mode indicator packed data */
   3096 	*dma_prog++ = OP_SYNC | 1 << 15 | BKTR_FM1;
   3097 	*dma_prog++ = 0;  /* NULL WORD */
   3098 
   3099 	b = cols;
   3100 
   3101 	for (i = 0; i < (rows/interlace); i++) {
   3102 		*dma_prog++ = inst;
   3103 		*dma_prog++ = target_buffer;
   3104 		*dma_prog++ = inst3;
   3105 		*dma_prog++ = target_buffer + b;
   3106 		target_buffer += interlace*(cols * 2);
   3107 	}
   3108 
   3109 	switch (i_flag) {
   3110 	case 1:
   3111 		/* sync vre */
   3112 		*dma_prog++ = OP_SYNC  | 1 << 24 | BKTR_VRE;
   3113 		*dma_prog++ = 0;  /* NULL WORD */
   3114 
   3115 		*dma_prog++ = OP_JUMP;
   3116 		*dma_prog++ = (u_long ) vtophys(bktr->dma_prog);
   3117 		return;
   3118 
   3119 	case 2:
   3120 		/* sync vro */
   3121 		*dma_prog++ = OP_SYNC  | 1 << 24 | BKTR_VRO;
   3122 		*dma_prog++ = 0;  /* NULL WORD */
   3123 		*dma_prog++ = OP_JUMP;
   3124 		*dma_prog++ = (u_long ) vtophys(bktr->dma_prog);
   3125 		return;
   3126 
   3127 	case 3:
   3128 		/* sync vro */
   3129 		*dma_prog++ = OP_SYNC	 | 1 << 24 | 1 << 15 | BKTR_VRO;
   3130 		*dma_prog++ = 0;  /* NULL WORD */
   3131 		*dma_prog++ = OP_JUMP  ;
   3132 		*dma_prog = (u_long ) vtophys(bktr->odd_dma_prog);
   3133 		break;
   3134 	}
   3135 
   3136 	if (interlace == 2) {
   3137 
   3138 		target_buffer =	 (u_long) buffer + cols*2;
   3139 
   3140 		dma_prog = (u_long * ) bktr->odd_dma_prog;
   3141 
   3142 		/* sync vre */
   3143 		*dma_prog++ = OP_SYNC | 1 << 24 |  1 << 15 | BKTR_FM1;
   3144 		*dma_prog++ = 0;  /* NULL WORD */
   3145 
   3146 		for (i = 0; i < (rows/interlace) ; i++) {
   3147 			*dma_prog++ = inst;
   3148 			*dma_prog++ = target_buffer;
   3149 			*dma_prog++ = inst3;
   3150 			*dma_prog++ = target_buffer + b;
   3151 			target_buffer += interlace * ( cols*2);
   3152 		}
   3153 	}
   3154 
   3155 	/* sync vro IRQ bit */
   3156 	*dma_prog++ = OP_SYNC   |  1 << 24  | 1 << 15 |  BKTR_VRE;
   3157 	*dma_prog++ = 0;  /* NULL WORD */
   3158 	*dma_prog++ = OP_JUMP ;
   3159 	*dma_prog++ = (u_long ) vtophys(bktr->dma_prog);
   3160 
   3161 	*dma_prog++ = OP_JUMP;
   3162 	*dma_prog++ = (u_long ) vtophys(bktr->dma_prog);
   3163 	*dma_prog++ = 0;  /* NULL WORD */
   3164 }
   3165 
   3166 
   3167 /*
   3168  *
   3169  */
   3170 static void
   3171 yuv422_prog( bktr_ptr_t bktr, char i_flag,
   3172 	     int cols, int rows, int interlace ){
   3173 
   3174 	int			i;
   3175 	volatile unsigned int	inst;
   3176 	volatile u_long		target_buffer, t1, buffer;
   3177 	volatile u_long		*dma_prog;
   3178         const struct meteor_pixfmt_internal *pf_int = &pixfmt_table[ bktr->pixfmt ];
   3179 
   3180 	OUTB(bktr, BKTR_COLOR_FMT, pf_int->color_fmt);
   3181 
   3182 	dma_prog = (u_long *) bktr->dma_prog;
   3183 
   3184 	bktr->capcontrol =   1 << 6 | 1 << 4 |	3;
   3185 
   3186 	OUTB(bktr, BKTR_ADC, SYNC_LEVEL);
   3187 	OUTB(bktr, BKTR_OFORM, 0x00);
   3188 
   3189 	OUTB(bktr, BKTR_E_CONTROL, INB(bktr, BKTR_E_CONTROL) | BT848_E_CONTROL_LDEC); /* disable luma decimation */
   3190 	OUTB(bktr, BKTR_O_CONTROL, INB(bktr, BKTR_O_CONTROL) | BT848_O_CONTROL_LDEC);
   3191 
   3192 	OUTB(bktr, BKTR_E_SCLOOP, INB(bktr, BKTR_E_SCLOOP) | BT848_E_SCLOOP_CAGC);	/* chroma agc enable */
   3193 	OUTB(bktr, BKTR_O_SCLOOP, INB(bktr, BKTR_O_SCLOOP) | BT848_O_SCLOOP_CAGC);
   3194 
   3195 	OUTB(bktr, BKTR_E_VSCALE_HI, INB(bktr, BKTR_E_VSCALE_HI) & ~0x80); /* clear Ycomb */
   3196 	OUTB(bktr, BKTR_O_VSCALE_HI, INB(bktr, BKTR_O_VSCALE_HI) & ~0x80);
   3197 	OUTB(bktr, BKTR_E_VSCALE_HI, INB(bktr, BKTR_E_VSCALE_HI) | ~0x40); /* set chroma comb */
   3198 	OUTB(bktr, BKTR_O_VSCALE_HI, INB(bktr, BKTR_O_VSCALE_HI) | ~0x40);
   3199 
   3200 	/* disable gamma correction removal */
   3201 	OUTB(bktr, BKTR_COLOR_CTL, INB(bktr, BKTR_COLOR_CTL) | BT848_COLOR_CTL_GAMMA);
   3202 
   3203 	/* Construct Write */
   3204 	inst  = OP_WRITE123  | OP_SOL | OP_EOL |  (cols);
   3205 	if (bktr->video.addr)
   3206 		target_buffer = (u_long) bktr->video.addr;
   3207 	else
   3208 		target_buffer = (u_long) vtophys(bktr->bigbuf);
   3209 
   3210 	buffer = target_buffer;
   3211 
   3212 	t1 = buffer;
   3213 
   3214 	/* contruct sync : for video packet format */
   3215 	*dma_prog++ = OP_SYNC  | 1 << 15 |	BKTR_FM3; /*sync, mode indicator packed data*/
   3216 	*dma_prog++ = 0;  /* NULL WORD */
   3217 
   3218 	for (i = 0; i < (rows/interlace ) ; i++) {
   3219 		*dma_prog++ = inst;
   3220 		*dma_prog++ = cols/2 | cols/2 << 16;
   3221 		*dma_prog++ = target_buffer;
   3222 		*dma_prog++ = t1 + (cols*rows) + i*cols/2 * interlace;
   3223 		*dma_prog++ = t1 + (cols*rows) + (cols*rows/2) + i*cols/2 * interlace;
   3224 		target_buffer += interlace*cols;
   3225 	}
   3226 
   3227 	switch (i_flag) {
   3228 	case 1:
   3229 		*dma_prog++ = OP_SYNC  | 1 << 24 | BKTR_VRE;  /*sync vre*/
   3230 		*dma_prog++ = 0;  /* NULL WORD */
   3231 
   3232 		*dma_prog++ = OP_JUMP ;
   3233 		*dma_prog++ = (u_long ) vtophys(bktr->dma_prog);
   3234 		return;
   3235 
   3236 	case 2:
   3237 		*dma_prog++ = OP_SYNC  | 1 << 24 | BKTR_VRO;  /*sync vre*/
   3238 		*dma_prog++ = 0;  /* NULL WORD */
   3239 
   3240 		*dma_prog++ = OP_JUMP;
   3241 		*dma_prog++ = (u_long ) vtophys(bktr->dma_prog);
   3242 		return;
   3243 
   3244 	case 3:
   3245 		*dma_prog++ = OP_SYNC	| 1 << 24 |  1 << 15 |   BKTR_VRO;
   3246 		*dma_prog++ = 0;  /* NULL WORD */
   3247 
   3248 		*dma_prog++ = OP_JUMP  ;
   3249 		*dma_prog = (u_long ) vtophys(bktr->odd_dma_prog);
   3250 		break;
   3251 	}
   3252 
   3253 	if (interlace == 2) {
   3254 
   3255 		dma_prog = (u_long * ) bktr->odd_dma_prog;
   3256 
   3257 		target_buffer  = (u_long) buffer + cols;
   3258 		t1 = buffer + cols/2;
   3259 		*dma_prog++ = OP_SYNC	|   1 << 15 | BKTR_FM3;
   3260 		*dma_prog++ = 0;  /* NULL WORD */
   3261 
   3262 		for (i = 0; i < (rows/interlace )  ; i++) {
   3263 			*dma_prog++ = inst;
   3264 			*dma_prog++ = cols/2 | cols/2 << 16;
   3265 			*dma_prog++ = target_buffer;
   3266 			*dma_prog++ = t1 + (cols*rows) + i*cols/2 * interlace;
   3267 			*dma_prog++ = t1 + (cols*rows) + (cols*rows/2) + i*cols/2 * interlace;
   3268 			target_buffer += interlace*cols;
   3269 		}
   3270 	}
   3271 
   3272 	*dma_prog++ = OP_SYNC  | 1 << 24 | 1 << 15 |   BKTR_VRE;
   3273 	*dma_prog++ = 0;  /* NULL WORD */
   3274 	*dma_prog++ = OP_JUMP ;
   3275 	*dma_prog++ = (u_long ) vtophys(bktr->dma_prog) ;
   3276 	*dma_prog++ = 0;  /* NULL WORD */
   3277 }
   3278 
   3279 
   3280 /*
   3281  *
   3282  */
   3283 static void
   3284 yuv12_prog( bktr_ptr_t bktr, char i_flag,
   3285 	     int cols, int rows, int interlace ){
   3286 
   3287 	int			i;
   3288 	volatile unsigned int	inst;
   3289 	volatile unsigned int	inst1;
   3290 	volatile u_long		target_buffer, t1, buffer;
   3291 	volatile u_long		*dma_prog;
   3292         const struct meteor_pixfmt_internal *pf_int = &pixfmt_table[ bktr->pixfmt ];
   3293 
   3294 	OUTB(bktr, BKTR_COLOR_FMT, pf_int->color_fmt);
   3295 
   3296 	dma_prog = (u_long *) bktr->dma_prog;
   3297 
   3298 	bktr->capcontrol =   1 << 6 | 1 << 4 |	3;
   3299 
   3300 	OUTB(bktr, BKTR_ADC, SYNC_LEVEL);
   3301 	OUTB(bktr, BKTR_OFORM, 0x0);
   3302 
   3303 	/* Construct Write */
   3304  	inst  = OP_WRITE123  | OP_SOL | OP_EOL |  (cols);
   3305  	inst1  = OP_WRITES123  | OP_SOL | OP_EOL |  (cols);
   3306  	if (bktr->video.addr)
   3307  		target_buffer = (u_long) bktr->video.addr;
   3308  	else
   3309  		target_buffer = (u_long) vtophys(bktr->bigbuf);
   3310 
   3311 	buffer = target_buffer;
   3312  	t1 = buffer;
   3313 
   3314  	*dma_prog++ = OP_SYNC  | 1 << 15 |	BKTR_FM3; /*sync, mode indicator packed data*/
   3315  	*dma_prog++ = 0;  /* NULL WORD */
   3316 
   3317  	for (i = 0; i < (rows/interlace )/2 ; i++) {
   3318 		*dma_prog++ = inst;
   3319  		*dma_prog++ = cols/2 | (cols/2 << 16);
   3320  		*dma_prog++ = target_buffer;
   3321  		*dma_prog++ = t1 + (cols*rows) + i*cols/2 * interlace;
   3322  		*dma_prog++ = t1 + (cols*rows) + (cols*rows/4) + i*cols/2 * interlace;
   3323  		target_buffer += interlace*cols;
   3324  		*dma_prog++ = inst1;
   3325  		*dma_prog++ = cols/2 | (cols/2 << 16);
   3326  		*dma_prog++ = target_buffer;
   3327  		target_buffer += interlace*cols;
   3328 
   3329  	}
   3330 
   3331  	switch (i_flag) {
   3332  	case 1:
   3333  		*dma_prog++ = OP_SYNC  | 1 << 24 | BKTR_VRE;  /*sync vre*/
   3334  		*dma_prog++ = 0;  /* NULL WORD */
   3335 
   3336 		*dma_prog++ = OP_JUMP;
   3337 		*dma_prog++ = (u_long ) vtophys(bktr->dma_prog);
   3338  		return;
   3339 
   3340  	case 2:
   3341  		*dma_prog++ = OP_SYNC  | 1 << 24 | BKTR_VRO;  /*sync vro*/
   3342  		*dma_prog++ = 0;  /* NULL WORD */
   3343 
   3344 		*dma_prog++ = OP_JUMP;
   3345 		*dma_prog++ = (u_long ) vtophys(bktr->dma_prog);
   3346  		return;
   3347 
   3348  	case 3:
   3349  		*dma_prog++ = OP_SYNC |  1 << 24 | 1 << 15 | BKTR_VRO;
   3350 		*dma_prog++ = 0;  /* NULL WORD */
   3351 		*dma_prog++ = OP_JUMP ;
   3352 		*dma_prog = (u_long ) vtophys(bktr->odd_dma_prog);
   3353 		break;
   3354 	}
   3355 
   3356 	if (interlace == 2) {
   3357 
   3358 		dma_prog = (u_long * ) bktr->odd_dma_prog;
   3359 
   3360 		target_buffer  = (u_long) buffer + cols;
   3361 		t1 = buffer + cols/2;
   3362 		*dma_prog++ = OP_SYNC   | 1 << 15 | BKTR_FM3;
   3363 		*dma_prog++ = 0;  /* NULL WORD */
   3364 
   3365 		for (i = 0; i < ((rows/interlace )/2 ) ; i++) {
   3366 		    *dma_prog++ = inst;
   3367 		    *dma_prog++ = cols/2 | (cols/2 << 16);
   3368          	    *dma_prog++ = target_buffer;
   3369 		    *dma_prog++ = t1 + (cols*rows) + i*cols/2 * interlace;
   3370 		    *dma_prog++ = t1 + (cols*rows) + (cols*rows/4) + i*cols/2 * interlace;
   3371 		    target_buffer += interlace*cols;
   3372 		    *dma_prog++ = inst1;
   3373 		    *dma_prog++ = cols/2 | (cols/2 << 16);
   3374 		    *dma_prog++ = target_buffer;
   3375 		    target_buffer += interlace*cols;
   3376 
   3377 		}
   3378 
   3379 
   3380 	}
   3381 
   3382 	*dma_prog++ = OP_SYNC |  1 << 24 | 1 << 15 | BKTR_VRE;
   3383 	*dma_prog++ = 0;  /* NULL WORD */
   3384 	*dma_prog++ = OP_JUMP;
   3385 	*dma_prog++ = (u_long ) vtophys(bktr->dma_prog);
   3386 	*dma_prog++ = 0;  /* NULL WORD */
   3387 }
   3388 
   3389 
   3390 
   3391 /*
   3392  *
   3393  */
   3394 static void
   3395 build_dma_prog( bktr_ptr_t bktr, char i_flag )
   3396 {
   3397 	int			rows, cols,  interlace;
   3398 	int			tmp_int;
   3399 	unsigned int		temp;
   3400 	const struct format_params	*fp;
   3401         const struct meteor_pixfmt_internal *pf_int = &pixfmt_table[ bktr->pixfmt ];
   3402 
   3403 
   3404 	fp = &format_params[bktr->format_params];
   3405 
   3406 	OUTL(bktr, BKTR_INT_MASK,  ALL_INTS_DISABLED);
   3407 
   3408 	/* disable FIFO & RISC, leave other bits alone */
   3409 	OUTW(bktr, BKTR_GPIO_DMA_CTL, INW(bktr, BKTR_GPIO_DMA_CTL) & ~FIFO_RISC_ENABLED);
   3410 
   3411 	/* set video parameters */
   3412 	if (bktr->capture_area_enabled)
   3413 	  temp = ((quad_t ) fp->htotal* (quad_t) bktr->capture_area_x_size * 4096
   3414 		  / fp->scaled_htotal / bktr->cols) -  4096;
   3415 	else
   3416 	  temp = ((quad_t ) fp->htotal* (quad_t) fp->scaled_hactive * 4096
   3417 		  / fp->scaled_htotal / bktr->cols) -  4096;
   3418 
   3419 	/* printf("%s: HSCALE value is %d\n", bktr_name(bktr), temp); */
   3420 	OUTB(bktr, BKTR_E_HSCALE_LO, temp & 0xff);
   3421 	OUTB(bktr, BKTR_O_HSCALE_LO, temp & 0xff);
   3422 	OUTB(bktr, BKTR_E_HSCALE_HI, (temp >> 8) & 0xff);
   3423 	OUTB(bktr, BKTR_O_HSCALE_HI, (temp >> 8) & 0xff);
   3424 
   3425 	/* horizontal active */
   3426 	temp = bktr->cols;
   3427 	/* printf("%s: HACTIVE value is %d\n", bktr_name(bktr), temp); */
   3428 	OUTB(bktr, BKTR_E_HACTIVE_LO, temp & 0xff);
   3429 	OUTB(bktr, BKTR_O_HACTIVE_LO, temp & 0xff);
   3430 	OUTB(bktr, BKTR_E_CROP, INB(bktr, BKTR_E_CROP) & ~0x3);
   3431 	OUTB(bktr, BKTR_O_CROP, INB(bktr, BKTR_O_CROP) & ~0x3);
   3432 	OUTB(bktr, BKTR_E_CROP, INB(bktr, BKTR_E_CROP) | ((temp >> 8) & 0x3));
   3433 	OUTB(bktr, BKTR_O_CROP, INB(bktr, BKTR_O_CROP) | ((temp >> 8) & 0x3));
   3434 
   3435 	/* horizontal delay */
   3436 	if (bktr->capture_area_enabled)
   3437 	  temp = ( (fp->hdelay* fp->scaled_hactive + bktr->capture_area_x_offset* fp->scaled_htotal)
   3438 		 * bktr->cols) / (bktr->capture_area_x_size * fp->hactive);
   3439 	else
   3440 	  temp = (fp->hdelay * bktr->cols) / fp->hactive;
   3441 
   3442 	temp = temp & 0x3fe;
   3443 
   3444 	/* printf("%s: HDELAY value is %d\n", bktr_name(bktr), temp); */
   3445 	OUTB(bktr, BKTR_E_DELAY_LO, temp & 0xff);
   3446 	OUTB(bktr, BKTR_O_DELAY_LO, temp & 0xff);
   3447 	OUTB(bktr, BKTR_E_CROP, INB(bktr, BKTR_E_CROP) & ~0xc);
   3448 	OUTB(bktr, BKTR_O_CROP, INB(bktr, BKTR_O_CROP) & ~0xc);
   3449 	OUTB(bktr, BKTR_E_CROP, INB(bktr, BKTR_E_CROP) | ((temp >> 6) & 0xc));
   3450 	OUTB(bktr, BKTR_O_CROP, INB(bktr, BKTR_O_CROP) | ((temp >> 6) & 0xc));
   3451 
   3452 	/* vertical scale */
   3453 
   3454 	if (bktr->capture_area_enabled) {
   3455 	  if (bktr->flags  & METEOR_ONLY_ODD_FIELDS ||
   3456 	      bktr->flags & METEOR_ONLY_EVEN_FIELDS)
   3457 	    tmp_int = 65536 -
   3458 	    (((bktr->capture_area_y_size  * 256 + (bktr->rows/2)) / bktr->rows) - 512);
   3459 	  else {
   3460 	    tmp_int = 65536 -
   3461 	    (((bktr->capture_area_y_size * 512 + (bktr->rows / 2)) /  bktr->rows) - 512);
   3462 	  }
   3463 	} else {
   3464 	  if (bktr->flags  & METEOR_ONLY_ODD_FIELDS ||
   3465 	      bktr->flags & METEOR_ONLY_EVEN_FIELDS)
   3466 	    tmp_int = 65536 -
   3467 	    (((fp->vactive  * 256 + (bktr->rows/2)) / bktr->rows) - 512);
   3468 	  else {
   3469 	    tmp_int = 65536  -
   3470 	    (((fp->vactive * 512 + (bktr->rows / 2)) /  bktr->rows) - 512);
   3471 	  }
   3472 	}
   3473 
   3474 	tmp_int &= 0x1fff;
   3475 	/* printf("%s: VSCALE value is %d\n", bktr_name(bktr), tmp_int); */
   3476 	OUTB(bktr, BKTR_E_VSCALE_LO, tmp_int & 0xff);
   3477 	OUTB(bktr, BKTR_O_VSCALE_LO, tmp_int & 0xff);
   3478 	OUTB(bktr, BKTR_E_VSCALE_HI, INB(bktr, BKTR_E_VSCALE_HI) & ~0x1f);
   3479 	OUTB(bktr, BKTR_O_VSCALE_HI, INB(bktr, BKTR_O_VSCALE_HI) & ~0x1f);
   3480 	OUTB(bktr, BKTR_E_VSCALE_HI, INB(bktr, BKTR_E_VSCALE_HI) | ((tmp_int >> 8) & 0x1f));
   3481 	OUTB(bktr, BKTR_O_VSCALE_HI, INB(bktr, BKTR_O_VSCALE_HI) | ((tmp_int >> 8) & 0x1f));
   3482 
   3483 
   3484 	/* vertical active */
   3485 	if (bktr->capture_area_enabled)
   3486 	  temp = bktr->capture_area_y_size;
   3487 	else
   3488 	  temp = fp->vactive;
   3489 	/* printf("%s: VACTIVE is %d\n", bktr_name(bktr), temp); */
   3490 	OUTB(bktr, BKTR_E_CROP, INB(bktr, BKTR_E_CROP) & ~0x30);
   3491 	OUTB(bktr, BKTR_E_CROP, INB(bktr, BKTR_E_CROP) | ((temp >> 4) & 0x30));
   3492 	OUTB(bktr, BKTR_E_VACTIVE_LO, temp & 0xff);
   3493 	OUTB(bktr, BKTR_O_CROP, INB(bktr, BKTR_O_CROP) & ~0x30);
   3494 	OUTB(bktr, BKTR_O_CROP, INB(bktr, BKTR_O_CROP) | ((temp >> 4) & 0x30));
   3495 	OUTB(bktr, BKTR_O_VACTIVE_LO, temp & 0xff);
   3496 
   3497 	/* vertical delay */
   3498 	if (bktr->capture_area_enabled)
   3499 	  temp = fp->vdelay + (bktr->capture_area_y_offset);
   3500 	else
   3501 	  temp = fp->vdelay;
   3502 	/* printf("%s: VDELAY is %d\n", bktr_name(bktr), temp); */
   3503 	OUTB(bktr, BKTR_E_CROP, INB(bktr, BKTR_E_CROP) & ~0xC0);
   3504 	OUTB(bktr, BKTR_E_CROP, INB(bktr, BKTR_E_CROP) | ((temp >> 2) & 0xC0));
   3505 	OUTB(bktr, BKTR_E_VDELAY_LO, temp & 0xff);
   3506 	OUTB(bktr, BKTR_O_CROP, INB(bktr, BKTR_O_CROP) & ~0xC0);
   3507 	OUTB(bktr, BKTR_O_CROP, INB(bktr, BKTR_O_CROP) | ((temp >> 2) & 0xC0));
   3508 	OUTB(bktr, BKTR_O_VDELAY_LO, temp & 0xff);
   3509 
   3510 	/* end of video params */
   3511 
   3512 	if ((bktr->xtal_pll_mode == BT848_USE_PLL)
   3513 	   && (fp->iform_xtsel==BT848_IFORM_X_XT1)) {
   3514 		OUTB(bktr, BKTR_TGCTRL, BT848_TGCTRL_TGCKI_PLL); /* Select PLL mode */
   3515 	} else {
   3516 		OUTB(bktr, BKTR_TGCTRL, BT848_TGCTRL_TGCKI_XTAL); /* Select Normal xtal 0/xtal 1 mode */
   3517 	}
   3518 
   3519 	/* capture control */
   3520 	switch (i_flag) {
   3521 	case 1:
   3522 	        bktr->bktr_cap_ctl =
   3523 		    (BT848_CAP_CTL_DITH_FRAME | BT848_CAP_CTL_EVEN);
   3524 		OUTB(bktr, BKTR_E_VSCALE_HI, INB(bktr, BKTR_E_VSCALE_HI) & ~0x20);
   3525 		OUTB(bktr, BKTR_O_VSCALE_HI, INB(bktr, BKTR_O_VSCALE_HI) & ~0x20);
   3526 		interlace = 1;
   3527 		break;
   3528 	 case 2:
   3529  	        bktr->bktr_cap_ctl =
   3530 			(BT848_CAP_CTL_DITH_FRAME | BT848_CAP_CTL_ODD);
   3531 		OUTB(bktr, BKTR_E_VSCALE_HI, INB(bktr, BKTR_E_VSCALE_HI) & ~0x20);
   3532 		OUTB(bktr, BKTR_O_VSCALE_HI, INB(bktr, BKTR_O_VSCALE_HI) & ~0x20);
   3533 		interlace = 1;
   3534 		break;
   3535 	 default:
   3536  	        bktr->bktr_cap_ctl =
   3537 			(BT848_CAP_CTL_DITH_FRAME |
   3538 			 BT848_CAP_CTL_EVEN | BT848_CAP_CTL_ODD);
   3539 		OUTB(bktr, BKTR_E_VSCALE_HI, INB(bktr, BKTR_E_VSCALE_HI) | 0x20);
   3540 		OUTB(bktr, BKTR_O_VSCALE_HI, INB(bktr, BKTR_O_VSCALE_HI) | 0x20);
   3541 		interlace = 2;
   3542 		break;
   3543 	}
   3544 
   3545 	OUTL(bktr, BKTR_RISC_STRT_ADD, vtophys(bktr->dma_prog));
   3546 
   3547 	rows = bktr->rows;
   3548 	cols = bktr->cols;
   3549 
   3550 	bktr->vbiflags &= ~VBI_CAPTURE;	/* default - no vbi capture */
   3551 
   3552 	/* RGB Grabs. If /dev/vbi is already open, or we are a PAL/SECAM */
   3553 	/* user, then use the rgb_vbi RISC program. */
   3554 	/* Otherwise, use the normal rgb RISC program */
   3555 	if (pf_int->public.type == METEOR_PIXTYPE_RGB) {
   3556 		if ( (bktr->vbiflags & VBI_OPEN)
   3557 		   ||(bktr->format_params == BT848_IFORM_F_PALBDGHI)
   3558 		   ||(bktr->format_params == BT848_IFORM_F_SECAM)
   3559                    ){
   3560 			bktr->bktr_cap_ctl |=
   3561 		                BT848_CAP_CTL_VBI_EVEN | BT848_CAP_CTL_VBI_ODD;
   3562 			bktr->vbiflags |= VBI_CAPTURE;
   3563 			rgb_vbi_prog(bktr, i_flag, cols, rows, interlace);
   3564 			return;
   3565 		} else {
   3566 			rgb_prog(bktr, i_flag, cols, rows, interlace);
   3567 			return;
   3568 		}
   3569 	}
   3570 
   3571 	if ( pf_int->public.type  == METEOR_PIXTYPE_YUV ) {
   3572 		yuv422_prog(bktr, i_flag, cols, rows, interlace);
   3573 		OUTB(bktr, BKTR_COLOR_CTL, (INB(bktr, BKTR_COLOR_CTL) & 0xf0)
   3574 		     | pixfmt_swap_flags( bktr->pixfmt ));
   3575 		return;
   3576 	}
   3577 
   3578 	if ( pf_int->public.type  == METEOR_PIXTYPE_YUV_PACKED ) {
   3579 		yuvpack_prog(bktr, i_flag, cols, rows, interlace);
   3580 		OUTB(bktr, BKTR_COLOR_CTL, (INB(bktr, BKTR_COLOR_CTL) & 0xf0)
   3581 		     | pixfmt_swap_flags( bktr->pixfmt ));
   3582 		return;
   3583 	}
   3584 
   3585 	if ( pf_int->public.type  == METEOR_PIXTYPE_YUV_12 ) {
   3586 		yuv12_prog(bktr, i_flag, cols, rows, interlace);
   3587 		OUTB(bktr, BKTR_COLOR_CTL, (INB(bktr, BKTR_COLOR_CTL) & 0xf0)
   3588 		     | pixfmt_swap_flags( bktr->pixfmt ));
   3589 		return;
   3590 	}
   3591 	return;
   3592 }
   3593 
   3594 
   3595 /******************************************************************************
   3596  * video & video capture specific routines:
   3597  */
   3598 
   3599 
   3600 /*
   3601  *
   3602  */
   3603 static void
   3604 start_capture( bktr_ptr_t bktr, unsigned type )
   3605 {
   3606 	u_char			i_flag;
   3607 	const struct format_params   *fp;
   3608 
   3609 	fp = &format_params[bktr->format_params];
   3610 
   3611 	/*  If requested, clear out capture buf first  */
   3612 	if (bktr->clr_on_start && (bktr->video.addr == 0)) {
   3613 		bzero((caddr_t)bktr->bigbuf,
   3614 		      (size_t)bktr->rows * bktr->cols * bktr->frames *
   3615 			pixfmt_table[ bktr->pixfmt ].public.Bpp);
   3616 	}
   3617 
   3618 	OUTB(bktr, BKTR_DSTATUS,  0);
   3619 	OUTL(bktr, BKTR_INT_STAT, INL(bktr, BKTR_INT_STAT));
   3620 
   3621 	bktr->flags |= type;
   3622 	bktr->flags &= ~METEOR_WANT_MASK;
   3623 	switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
   3624 	case METEOR_ONLY_EVEN_FIELDS:
   3625 		bktr->flags |= METEOR_WANT_EVEN;
   3626 		i_flag = 1;
   3627 		break;
   3628 	case METEOR_ONLY_ODD_FIELDS:
   3629 		bktr->flags |= METEOR_WANT_ODD;
   3630 		i_flag = 2;
   3631 		break;
   3632 	default:
   3633 		bktr->flags |= METEOR_WANT_MASK;
   3634 		i_flag = 3;
   3635 		break;
   3636 	}
   3637 
   3638 	/*  TDEC is only valid for continuous captures  */
   3639 	if ( type == METEOR_SINGLE ) {
   3640 		u_short	fps_save = bktr->fps;
   3641 
   3642 		set_fps(bktr, fp->frame_rate);
   3643 		bktr->fps = fps_save;
   3644 	}
   3645 	else
   3646 		set_fps(bktr, bktr->fps);
   3647 
   3648 	if (bktr->dma_prog_loaded == FALSE) {
   3649 		build_dma_prog(bktr, i_flag);
   3650 		bktr->dma_prog_loaded = TRUE;
   3651 	}
   3652 
   3653 
   3654 	OUTL(bktr, BKTR_RISC_STRT_ADD, vtophys(bktr->dma_prog));
   3655 
   3656 }
   3657 
   3658 
   3659 /*
   3660  *
   3661  */
   3662 static void
   3663 set_fps( bktr_ptr_t bktr, u_short fps )
   3664 {
   3665 	const struct format_params	*fp;
   3666 	int i_flag;
   3667 
   3668 	fp = &format_params[bktr->format_params];
   3669 
   3670 	switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
   3671 	case METEOR_ONLY_EVEN_FIELDS:
   3672 		bktr->flags |= METEOR_WANT_EVEN;
   3673 		i_flag = 1;
   3674 		break;
   3675 	case METEOR_ONLY_ODD_FIELDS:
   3676 		bktr->flags |= METEOR_WANT_ODD;
   3677 		i_flag = 1;
   3678 		break;
   3679 	default:
   3680 		bktr->flags |= METEOR_WANT_MASK;
   3681 		i_flag = 2;
   3682 		break;
   3683 	}
   3684 
   3685 	OUTW(bktr, BKTR_GPIO_DMA_CTL, FIFO_RISC_DISABLED);
   3686 	OUTL(bktr, BKTR_INT_STAT, ALL_INTS_CLEARED);
   3687 
   3688 	bktr->fps = fps;
   3689 	OUTB(bktr, BKTR_TDEC, 0);
   3690 
   3691 	if (fps < fp->frame_rate)
   3692 		OUTB(bktr, BKTR_TDEC, i_flag*(fp->frame_rate - fps) & 0x3f);
   3693 	else
   3694 		OUTB(bktr, BKTR_TDEC, 0);
   3695 	return;
   3696 
   3697 }
   3698 
   3699 
   3700 
   3701 
   3702 
   3703 /*
   3704  * Given a pixfmt index, compute the bt848 swap_flags necessary to
   3705  *   achieve the specified swapping.
   3706  * Note that without bt swapping, 2Bpp and 3Bpp modes are written
   3707  *   byte-swapped, and 4Bpp modes are byte and word swapped (see Table 6
   3708  *   and read R->L).
   3709  * Note also that for 3Bpp, we may additionally need to do some creative
   3710  *   SKIPing to align the FIFO bytelines with the target buffer (see split()).
   3711  * This is abstracted here: e.g. no swaps = RGBA; byte & short swap = ABGR
   3712  *   as one would expect.
   3713  */
   3714 
   3715 static u_int pixfmt_swap_flags( int pixfmt )
   3716 {
   3717 	const struct meteor_pixfmt *pf = &pixfmt_table[ pixfmt ].public;
   3718 	u_int		      swapf = 0;
   3719 
   3720 	switch ( pf->Bpp ) {
   3721 	case 2 : swapf = ( pf->swap_bytes ? 0 : BSWAP );
   3722 		 break;
   3723 
   3724 	case 3 : /* no swaps supported for 3bpp - makes no sense w/ bt848 */
   3725 		 break;
   3726 
   3727 	case 4 : if ( pf->swap_bytes )
   3728 			swapf = pf->swap_shorts ? 0 : WSWAP;
   3729 		 else
   3730 			swapf = pf->swap_shorts ? BSWAP : (BSWAP | WSWAP);
   3731 		 break;
   3732 	}
   3733 	return swapf;
   3734 }
   3735 
   3736 
   3737 
   3738 /*
   3739  * Converts meteor-defined pixel formats (e.g. METEOR_GEO_RGB16) into
   3740  *   our pixfmt_table indices.
   3741  */
   3742 
   3743 static int oformat_meteor_to_bt( u_long format )
   3744 {
   3745 	int    i;
   3746         const struct meteor_pixfmt *pf1, *pf2;
   3747 
   3748 	/*  Find format in compatibility table  */
   3749 	for ( i = 0; i < METEOR_PIXFMT_TABLE_SIZE; i++ )
   3750 		if ( meteor_pixfmt_table[i].meteor_format == format )
   3751 			break;
   3752 
   3753 	if ( i >= METEOR_PIXFMT_TABLE_SIZE )
   3754 		return -1;
   3755 	pf1 = &meteor_pixfmt_table[i].public;
   3756 
   3757 	/*  Match it with an entry in master pixel format table  */
   3758 	for ( i = 0; i < PIXFMT_TABLE_SIZE; i++ ) {
   3759 		pf2 = &pixfmt_table[i].public;
   3760 
   3761 		if (( pf1->type        == pf2->type        ) &&
   3762 		    ( pf1->Bpp         == pf2->Bpp         ) &&
   3763 		    !bcmp( pf1->masks, pf2->masks, sizeof( pf1->masks )) &&
   3764 		    ( pf1->swap_bytes  == pf2->swap_bytes  ) &&
   3765 		    ( pf1->swap_shorts == pf2->swap_shorts ))
   3766 			break;
   3767 	}
   3768 	if ( i >= PIXFMT_TABLE_SIZE )
   3769 		return -1;
   3770 
   3771 	return i;
   3772 }
   3773 
   3774 /******************************************************************************
   3775  * i2c primitives:
   3776  */
   3777 
   3778 /* */
   3779 #define I2CBITTIME		(0x5<<4)	/* 5 * 0.48uS */
   3780 #define I2CBITTIME_878              (1 << 7)
   3781 #define I2C_READ		0x01
   3782 #define I2C_COMMAND		(I2CBITTIME |			\
   3783 				 BT848_DATA_CTL_I2CSCL |	\
   3784 				 BT848_DATA_CTL_I2CSDA)
   3785 
   3786 #define I2C_COMMAND_878		(I2CBITTIME_878 |			\
   3787 				 BT848_DATA_CTL_I2CSCL |	\
   3788 				 BT848_DATA_CTL_I2CSDA)
   3789 
   3790 /* Select between old i2c code and new iicbus / smbus code */
   3791 #if defined(BKTR_USE_FREEBSD_SMBUS)
   3792 
   3793 /*
   3794  * The hardware interface is actually SMB commands
   3795  */
   3796 int
   3797 i2cWrite( bktr_ptr_t bktr, int addr, int byte1, int byte2 )
   3798 {
   3799 	char cmd;
   3800 
   3801 	if (bktr->id == BROOKTREE_848  ||
   3802 	    bktr->id == BROOKTREE_848A ||
   3803 	    bktr->id == BROOKTREE_849A)
   3804 		cmd = I2C_COMMAND;
   3805 	else
   3806 		cmd = I2C_COMMAND_878;
   3807 
   3808 	if (byte2 != -1) {
   3809 		if (smbus_writew(bktr->i2c_sc.smbus, addr, cmd,
   3810 			(short)(((byte2 & 0xff) << 8) | (byte1 & 0xff))))
   3811 			return (-1);
   3812 	} else {
   3813 		if (smbus_writeb(bktr->i2c_sc.smbus, addr, cmd,
   3814 			(char)(byte1 & 0xff)))
   3815 			return (-1);
   3816 	}
   3817 
   3818 	/* return OK */
   3819 	return( 0 );
   3820 }
   3821 
   3822 int
   3823 i2cRead( bktr_ptr_t bktr, int addr )
   3824 {
   3825 	char result;
   3826 	char cmd;
   3827 
   3828 	if (bktr->id == BROOKTREE_848  ||
   3829 	    bktr->id == BROOKTREE_848A ||
   3830 	    bktr->id == BROOKTREE_849A)
   3831 		cmd = I2C_COMMAND;
   3832 	else
   3833 		cmd = I2C_COMMAND_878;
   3834 
   3835 	if (smbus_readb(bktr->i2c_sc.smbus, addr, cmd, &result))
   3836 		return (-1);
   3837 
   3838 	return ((int)((unsigned char)result));
   3839 }
   3840 
   3841 #define IICBUS(bktr) ((bktr)->i2c_sc.iicbus)
   3842 
   3843 /* The MSP34xx and DPL35xx Audio chip require i2c bus writes of up */
   3844 /* to 5 bytes which the bt848 automated i2c bus controller cannot handle */
   3845 /* Therefore we need low level control of the i2c bus hardware */
   3846 
   3847 /* Write to the MSP or DPL registers */
   3848 void
   3849 msp_dpl_write(bktr_ptr_t bktr, int i2c_addr,  unsigned char dev, unsigned int addr, unsigned int data)
   3850 {
   3851 	unsigned char addr_l, addr_h, data_h, data_l ;
   3852 
   3853 	addr_h = (addr >>8) & 0xff;
   3854 	addr_l = addr & 0xff;
   3855 	data_h = (data >>8) & 0xff;
   3856 	data_l = data & 0xff;
   3857 
   3858 	iicbus_start(IICBUS(bktr), i2c_addr, 0 /* no timeout? */);
   3859 
   3860 	iicbus_write_byte(IICBUS(bktr), dev, 0);
   3861 	iicbus_write_byte(IICBUS(bktr), addr_h, 0);
   3862 	iicbus_write_byte(IICBUS(bktr), addr_l, 0);
   3863 	iicbus_write_byte(IICBUS(bktr), data_h, 0);
   3864 	iicbus_write_byte(IICBUS(bktr), data_l, 0);
   3865 
   3866 	iicbus_stop(IICBUS(bktr));
   3867 
   3868 	return;
   3869 }
   3870 
   3871 /* Read from the MSP or DPL registers */
   3872 unsigned int
   3873 msp_dpl_read(bktr_ptr_t bktr, int i2c_addr, unsigned char dev, unsigned int addr)
   3874 {
   3875 	unsigned int data;
   3876 	unsigned char addr_l, addr_h, dev_r;
   3877 	int read;
   3878 	u_char data_read[2];
   3879 
   3880 	addr_h = (addr >>8) & 0xff;
   3881 	addr_l = addr & 0xff;
   3882 	dev_r = dev+1;
   3883 
   3884 	/* XXX errors ignored */
   3885 	iicbus_start(IICBUS(bktr), i2c_addr, 0 /* no timeout? */);
   3886 
   3887 	iicbus_write_byte(IICBUS(bktr), dev_r, 0);
   3888 	iicbus_write_byte(IICBUS(bktr), addr_h, 0);
   3889 	iicbus_write_byte(IICBUS(bktr), addr_l, 0);
   3890 
   3891 	iicbus_repeated_start(IICBUS(bktr), i2c_addr +1, 0 /* no timeout? */);
   3892 	iicbus_read(IICBUS(bktr), data_read, 2, &read, IIC_LAST_READ, 0);
   3893 	iicbus_stop(IICBUS(bktr));
   3894 
   3895 	data = (data_read[0]<<8) | data_read[1];
   3896 
   3897 	return (data);
   3898 }
   3899 
   3900 /* Reset the MSP or DPL chip */
   3901 /* The user can block the reset (which is handy if you initialise the
   3902  * MSP and/or DPL audio in another operating system first (eg in Windows)
   3903  */
   3904 void
   3905 msp_dpl_reset( bktr_ptr_t bktr, int i2c_addr )
   3906 {
   3907 
   3908 #ifndef BKTR_NO_MSP_RESET
   3909 	/* put into reset mode */
   3910 	iicbus_start(IICBUS(bktr), i2c_addr, 0 /* no timeout? */);
   3911 	iicbus_write_byte(IICBUS(bktr), 0x00, 0);
   3912 	iicbus_write_byte(IICBUS(bktr), 0x80, 0);
   3913 	iicbus_write_byte(IICBUS(bktr), 0x00, 0);
   3914 	iicbus_stop(IICBUS(bktr));
   3915 
   3916 	/* put back to operational mode */
   3917 	iicbus_start(IICBUS(bktr), i2c_addr, 0 /* no timeout? */);
   3918 	iicbus_write_byte(IICBUS(bktr), 0x00, 0);
   3919 	iicbus_write_byte(IICBUS(bktr), 0x00, 0);
   3920 	iicbus_write_byte(IICBUS(bktr), 0x00, 0);
   3921 	iicbus_stop(IICBUS(bktr));
   3922 #endif
   3923 	return;
   3924 }
   3925 
   3926 static void remote_read(bktr_ptr_t bktr, struct bktr_remote *remote) {
   3927 	int read;
   3928 
   3929 	/* XXX errors ignored */
   3930 	iicbus_start(IICBUS(bktr), bktr->remote_control_addr, 0 /* no timeout? */);
   3931 	iicbus_read(IICBUS(bktr),  remote->data, 3, &read, IIC_LAST_READ, 0);
   3932 	iicbus_stop(IICBUS(bktr));
   3933 
   3934 	return;
   3935 }
   3936 
   3937 #else /* defined(BKTR_USE_FREEBSD_SMBUS) */
   3938 
   3939 /*
   3940  * Program the i2c bus directly
   3941  */
   3942 int
   3943 i2cWrite( bktr_ptr_t bktr, int addr, int byte1, int byte2 )
   3944 {
   3945 	u_long		x;
   3946 	u_long		data;
   3947 
   3948 	/* clear status bits */
   3949 	OUTL(bktr, BKTR_INT_STAT, BT848_INT_RACK | BT848_INT_I2CDONE);
   3950 
   3951 	/* build the command datum */
   3952 	if (bktr->id == BROOKTREE_848  ||
   3953 	    bktr->id == BROOKTREE_848A ||
   3954 	    bktr->id == BROOKTREE_849A) {
   3955 	  data = ((addr & 0xff) << 24) | ((byte1 & 0xff) << 16) | I2C_COMMAND;
   3956 	} else {
   3957 	  data = ((addr & 0xff) << 24) | ((byte1 & 0xff) << 16) | I2C_COMMAND_878;
   3958 	}
   3959 	if ( byte2 != -1 ) {
   3960 		data |= ((byte2 & 0xff) << 8);
   3961 		data |= BT848_DATA_CTL_I2CW3B;
   3962 	}
   3963 
   3964 	/* write the address and data */
   3965 	OUTL(bktr, BKTR_I2C_DATA_CTL, data);
   3966 
   3967 	/* wait for completion */
   3968 	for ( x = 0x7fffffff; x; --x ) {	/* safety valve */
   3969 		if ( INL(bktr, BKTR_INT_STAT) & BT848_INT_I2CDONE )
   3970 			break;
   3971 	}
   3972 
   3973 	/* check for ACK */
   3974 	if ( !x || !(INL(bktr, BKTR_INT_STAT) & BT848_INT_RACK) )
   3975 		return( -1 );
   3976 
   3977 	/* return OK */
   3978 	return( 0 );
   3979 }
   3980 
   3981 
   3982 /*
   3983  *
   3984  */
   3985 int
   3986 i2cRead( bktr_ptr_t bktr, int addr )
   3987 {
   3988 	u_long		x;
   3989 
   3990 	/* clear status bits */
   3991 	OUTL(bktr, BKTR_INT_STAT, BT848_INT_RACK | BT848_INT_I2CDONE);
   3992 
   3993 	/* write the READ address */
   3994 	/* The Bt878 and Bt879  differed on the treatment of i2c commands */
   3995 
   3996 	if (bktr->id == BROOKTREE_848  ||
   3997 	    bktr->id == BROOKTREE_848A ||
   3998 	    bktr->id == BROOKTREE_849A) {
   3999 		OUTL(bktr, BKTR_I2C_DATA_CTL, ((addr & 0xff) << 24) | I2C_COMMAND);
   4000 	} else {
   4001 		OUTL(bktr, BKTR_I2C_DATA_CTL, ((addr & 0xff) << 24) | I2C_COMMAND_878);
   4002 	}
   4003 
   4004 	/* wait for completion */
   4005 	for ( x = 0x7fffffff; x; --x ) {	/* safety valve */
   4006 		if ( INL(bktr, BKTR_INT_STAT) & BT848_INT_I2CDONE )
   4007 			break;
   4008 	}
   4009 
   4010 	/* check for ACK */
   4011 	if ( !x || !(INL(bktr, BKTR_INT_STAT) & BT848_INT_RACK) )
   4012 		return( -1 );
   4013 
   4014 	/* it was a read */
   4015 	return( (INL(bktr, BKTR_I2C_DATA_CTL) >> 8) & 0xff );
   4016 }
   4017 
   4018 /* The MSP34xx Audio chip require i2c bus writes of up to 5 bytes which the */
   4019 /* bt848 automated i2c bus controller cannot handle */
   4020 /* Therefore we need low level control of the i2c bus hardware */
   4021 /* Idea for the following functions are from elsewhere in this driver and */
   4022 /* from the Linux BTTV i2c driver by Gerd Knorr <kraxel (at) cs.tu-berlin.de> */
   4023 
   4024 #define BITD    40
   4025 static void i2c_start( bktr_ptr_t bktr) {
   4026         OUTL(bktr, BKTR_I2C_DATA_CTL, 1); DELAY( BITD ); /* release data */
   4027         OUTL(bktr, BKTR_I2C_DATA_CTL, 3); DELAY( BITD ); /* release clock */
   4028         OUTL(bktr, BKTR_I2C_DATA_CTL, 2); DELAY( BITD ); /* lower data */
   4029         OUTL(bktr, BKTR_I2C_DATA_CTL, 0); DELAY( BITD ); /* lower clock */
   4030 }
   4031 
   4032 static void i2c_stop( bktr_ptr_t bktr) {
   4033         OUTL(bktr, BKTR_I2C_DATA_CTL, 0); DELAY( BITD ); /* lower clock & data */
   4034         OUTL(bktr, BKTR_I2C_DATA_CTL, 2); DELAY( BITD ); /* release clock */
   4035         OUTL(bktr, BKTR_I2C_DATA_CTL, 3); DELAY( BITD ); /* release data */
   4036 }
   4037 
   4038 static int i2c_write_byte( bktr_ptr_t bktr, unsigned char data) {
   4039         int x;
   4040         int status;
   4041 
   4042         /* write out the byte */
   4043         for ( x = 7; x >= 0; --x ) {
   4044                 if ( data & (1<<x) ) {
   4045 			OUTL(bktr, BKTR_I2C_DATA_CTL, 1);
   4046                         DELAY( BITD );          /* assert HI data */
   4047 			OUTL(bktr, BKTR_I2C_DATA_CTL, 3);
   4048                         DELAY( BITD );          /* strobe clock */
   4049 			OUTL(bktr, BKTR_I2C_DATA_CTL, 1);
   4050                         DELAY( BITD );          /* release clock */
   4051                 }
   4052                 else {
   4053 			OUTL(bktr, BKTR_I2C_DATA_CTL, 0);
   4054                         DELAY( BITD );          /* assert LO data */
   4055 			OUTL(bktr, BKTR_I2C_DATA_CTL, 2);
   4056                         DELAY( BITD );          /* strobe clock */
   4057 			OUTL(bktr, BKTR_I2C_DATA_CTL, 0);
   4058                         DELAY( BITD );          /* release clock */
   4059                 }
   4060         }
   4061 
   4062         /* look for an ACK */
   4063 	OUTL(bktr, BKTR_I2C_DATA_CTL, 1); DELAY( BITD ); /* float data */
   4064 	OUTL(bktr, BKTR_I2C_DATA_CTL, 3); DELAY( BITD ); /* strobe clock */
   4065         status = INL(bktr, BKTR_I2C_DATA_CTL) & 1;       /* read the ACK bit */
   4066         OUTL(bktr, BKTR_I2C_DATA_CTL, 1); DELAY( BITD ); /* release clock */
   4067 
   4068         return( status );
   4069 }
   4070 
   4071 static int i2c_read_byte( bktr_ptr_t bktr, unsigned char *data, int last ) {
   4072         int x;
   4073         int bit;
   4074         int byte = 0;
   4075 
   4076         /* read in the byte */
   4077 	OUTL(bktr, BKTR_I2C_DATA_CTL, 1);
   4078         DELAY( BITD );                          /* float data */
   4079         for ( x = 7; x >= 0; --x ) {
   4080 		OUTL(bktr, BKTR_I2C_DATA_CTL, 3);
   4081                 DELAY( BITD );                  /* strobe clock */
   4082                 bit = INL(bktr, BKTR_I2C_DATA_CTL) & 1;  /* read the data bit */
   4083                 if ( bit ) byte |= (1<<x);
   4084 		OUTL(bktr, BKTR_I2C_DATA_CTL, 1);
   4085                 DELAY( BITD );                  /* release clock */
   4086         }
   4087         /* After reading the byte, send an ACK */
   4088         /* (unless that was the last byte, for which we send a NAK */
   4089         if (last) { /* send NAK - same a writing a 1 */
   4090 		OUTL(bktr, BKTR_I2C_DATA_CTL, 1);
   4091                 DELAY( BITD );                  /* set data bit */
   4092 		OUTL(bktr, BKTR_I2C_DATA_CTL, 3);
   4093                 DELAY( BITD );                  /* strobe clock */
   4094 		OUTL(bktr, BKTR_I2C_DATA_CTL, 1);
   4095                 DELAY( BITD );                  /* release clock */
   4096         } else { /* send ACK - same as writing a 0 */
   4097 		OUTL(bktr, BKTR_I2C_DATA_CTL, 0);
   4098                 DELAY( BITD );                  /* set data bit */
   4099 		OUTL(bktr, BKTR_I2C_DATA_CTL, 2);
   4100                 DELAY( BITD );                  /* strobe clock */
   4101 		OUTL(bktr, BKTR_I2C_DATA_CTL, 0);
   4102                 DELAY( BITD );                  /* release clock */
   4103         }
   4104 
   4105         *data=byte;
   4106 	return 0;
   4107 }
   4108 #undef BITD
   4109 
   4110 /* Write to the MSP or DPL registers */
   4111 void msp_dpl_write( bktr_ptr_t bktr, int i2c_addr, unsigned char dev, unsigned int addr,
   4112 		    unsigned int data){
   4113 	unsigned int msp_w_addr = i2c_addr;
   4114 	unsigned char addr_l, addr_h, data_h, data_l ;
   4115 	addr_h = (addr >>8) & 0xff;
   4116 	addr_l = addr & 0xff;
   4117 	data_h = (data >>8) & 0xff;
   4118 	data_l = data & 0xff;
   4119 
   4120 	i2c_start(bktr);
   4121 	i2c_write_byte(bktr, msp_w_addr);
   4122 	i2c_write_byte(bktr, dev);
   4123 	i2c_write_byte(bktr, addr_h);
   4124 	i2c_write_byte(bktr, addr_l);
   4125 	i2c_write_byte(bktr, data_h);
   4126 	i2c_write_byte(bktr, data_l);
   4127 	i2c_stop(bktr);
   4128 }
   4129 
   4130 /* Read from the MSP or DPL registers */
   4131 unsigned int msp_dpl_read(bktr_ptr_t bktr, int i2c_addr, unsigned char dev, unsigned int addr){
   4132 	unsigned int data;
   4133 	unsigned char addr_l, addr_h, data_1, data_2, dev_r ;
   4134 	addr_h = (addr >>8) & 0xff;
   4135 	addr_l = addr & 0xff;
   4136 	dev_r = dev+1;
   4137 
   4138 	i2c_start(bktr);
   4139 	i2c_write_byte(bktr,i2c_addr);
   4140 	i2c_write_byte(bktr,dev_r);
   4141 	i2c_write_byte(bktr,addr_h);
   4142 	i2c_write_byte(bktr,addr_l);
   4143 
   4144 	i2c_start(bktr);
   4145 	i2c_write_byte(bktr,i2c_addr+1);
   4146 	i2c_read_byte(bktr,&data_1, 0);
   4147 	i2c_read_byte(bktr,&data_2, 1);
   4148 	i2c_stop(bktr);
   4149 	data = (data_1<<8) | data_2;
   4150 	return data;
   4151 }
   4152 
   4153 /* Reset the MSP or DPL chip */
   4154 /* The user can block the reset (which is handy if you initialise the
   4155  * MSP audio in another operating system first (eg in Windows)
   4156  */
   4157 void msp_dpl_reset( bktr_ptr_t bktr, int i2c_addr ) {
   4158 
   4159 #ifndef BKTR_NO_MSP_RESET
   4160 	/* put into reset mode */
   4161 	i2c_start(bktr);
   4162 	i2c_write_byte(bktr, i2c_addr);
   4163 	i2c_write_byte(bktr, 0x00);
   4164 	i2c_write_byte(bktr, 0x80);
   4165 	i2c_write_byte(bktr, 0x00);
   4166 	i2c_stop(bktr);
   4167 
   4168 	/* put back to operational mode */
   4169 	i2c_start(bktr);
   4170 	i2c_write_byte(bktr, i2c_addr);
   4171 	i2c_write_byte(bktr, 0x00);
   4172 	i2c_write_byte(bktr, 0x00);
   4173 	i2c_write_byte(bktr, 0x00);
   4174 	i2c_stop(bktr);
   4175 #endif
   4176 	return;
   4177 
   4178 }
   4179 
   4180 static void remote_read(bktr_ptr_t bktr, struct bktr_remote *remote) {
   4181 
   4182 	/* XXX errors ignored */
   4183 	i2c_start(bktr);
   4184 	i2c_write_byte(bktr,bktr->remote_control_addr);
   4185 	i2c_read_byte(bktr,&(remote->data[0]), 0);
   4186 	i2c_read_byte(bktr,&(remote->data[1]), 0);
   4187 	i2c_read_byte(bktr,&(remote->data[2]), 0);
   4188 	i2c_stop(bktr);
   4189 
   4190 	return;
   4191 }
   4192 
   4193 #endif /* defined(BKTR_USE_FREEBSD_SMBUS) */
   4194 
   4195 
   4196 #if defined( I2C_SOFTWARE_PROBE )
   4197 
   4198 /*
   4199  * we are keeping this around for any parts that we need to probe
   4200  * but that CANNOT be probed via an i2c read.
   4201  * this is necessary because the hardware i2c mechanism
   4202  * cannot be programmed for 1 byte writes.
   4203  * currently there are no known i2c parts that we need to probe
   4204  * and that cannot be safely read.
   4205  */
   4206 static int	i2cProbe( bktr_ptr_t bktr, int addr );
   4207 #define BITD		40
   4208 #define EXTRA_START
   4209 
   4210 /*
   4211  * probe for an I2C device at addr.
   4212  */
   4213 static int
   4214 i2cProbe( bktr_ptr_t bktr, int addr )
   4215 {
   4216 	int		x, status;
   4217 
   4218 	/* the START */
   4219 #if defined( EXTRA_START )
   4220 	OUTL(bktr, BKTR_I2C_DATA_CTL, 1); DELAY( BITD );	/* release data */
   4221 	OUTL(bktr, BKTR_I2C_DATA_CTL, 3); DELAY( BITD );	/* release clock */
   4222 #endif /* EXTRA_START */
   4223 	OUTL(bktr, BKTR_I2C_DATA_CTL, 2); DELAY( BITD );	/* lower data */
   4224 	OUTL(bktr, BKTR_I2C_DATA_CTL, 0); DELAY( BITD );	/* lower clock */
   4225 
   4226 	/* write addr */
   4227 	for ( x = 7; x >= 0; --x ) {
   4228 		if ( addr & (1<<x) ) {
   4229 			OUTL(bktr, BKTR_I2C_DATA_CTL, 1);
   4230 			DELAY( BITD );		/* assert HI data */
   4231 			OUTL(bktr, BKTR_I2C_DATA_CTL, 3);
   4232 			DELAY( BITD );		/* strobe clock */
   4233 			OUTL(bktr, BKTR_I2C_DATA_CTL, 1);
   4234 			DELAY( BITD );		/* release clock */
   4235 		}
   4236 		else {
   4237 			OUTL(bktr, BKTR_I2C_DATA_CTL, 0);
   4238 			DELAY( BITD );		/* assert LO data */
   4239 			OUTL(bktr, BKTR_I2C_DATA_CTL, 2);
   4240 			DELAY( BITD );		/* strobe clock */
   4241 			OUTL(bktr, BKTR_I2C_DATA_CTL, 0);
   4242 			DELAY( BITD );		/* release clock */
   4243 		}
   4244 	}
   4245 
   4246 	/* look for an ACK */
   4247 	OUTL(bktr, BKTR_I2C_DATA_CTL, 1); DELAY( BITD );	/* float data */
   4248 	OUTL(bktr, BKTR_I2C_DATA_CTL, 3); DELAY( BITD );	/* strobe clock */
   4249 	status = INL(bktr, BKTR_I2C_DATA_CTL) & 1;	/* read the ACK bit */
   4250 	OUTL(bktr, BKTR_I2C_DATA_CTL, 1); DELAY( BITD );	/* release clock */
   4251 
   4252 	/* the STOP */
   4253 	OUTL(bktr, BKTR_I2C_DATA_CTL, 0); DELAY( BITD );	/* lower clock & data */
   4254 	OUTL(bktr, BKTR_I2C_DATA_CTL, 2); DELAY( BITD );	/* release clock */
   4255 	OUTL(bktr, BKTR_I2C_DATA_CTL, 3); DELAY( BITD );	/* release data */
   4256 
   4257 	return( status );
   4258 }
   4259 #undef EXTRA_START
   4260 #undef BITD
   4261 
   4262 #endif /* I2C_SOFTWARE_PROBE */
   4263 
   4264 
   4265 #define ABSENT		(-1)
   4266 
   4267 #endif /* FreeBSD, BSDI, NetBSD, OpenBSD */
   4268 
   4269