summaryrefslogtreecommitdiffstats
path: root/sys
diff options
context:
space:
mode:
authorfsmp <fsmp@FreeBSD.org>1997-03-25 04:18:24 +0000
committerfsmp <fsmp@FreeBSD.org>1997-03-25 04:18:24 +0000
commit1d259aacb1ff4478129e73dfad294abf0f82fdd1 (patch)
treef1450ff4813d3b32e440ba9b5ecfb9fca7099e38 /sys
parent48fd2f3385ee5e6987a0e076cb0c22e06976a8b8 (diff)
downloadFreeBSD-src-1d259aacb1ff4478129e73dfad294abf0f82fdd1.zip
FreeBSD-src-1d259aacb1ff4478129e73dfad294abf0f82fdd1.tar.gz
"Louis A. Mamakos" <louie@TransSys.COM> new bt848 struct
Randall Hopper <rhh@ct.picker.com> GHUE/GBRIGHT bug Louis Mamakos made a new bt848 struct, including massive changes to the entire body of code, substituting array offsets with struct members. Randall Hopper aadded fixes of BT848_GHUE & BT848_GBRIG. I (fsmp): added polled hardware i2c routines, removed all existing software i2c routines. added eeprom support.
Diffstat (limited to 'sys')
-rw-r--r--sys/dev/bktr/bktr_core.c2092
-rw-r--r--sys/dev/bktr/bktr_reg.h158
-rw-r--r--sys/pci/README.bt84820
-rw-r--r--sys/pci/brktree_reg.h158
-rw-r--r--sys/pci/brooktree848.c2092
5 files changed, 2400 insertions, 2120 deletions
diff --git a/sys/dev/bktr/bktr_core.c b/sys/dev/bktr/bktr_core.c
index 1b10e50..444014f 100644
--- a/sys/dev/bktr/bktr_core.c
+++ b/sys/dev/bktr/bktr_core.c
@@ -122,10 +122,24 @@
1.7 3/19/97 fsmp@freefall.org
added audio support submitted by:
Michael Petry <petry@netwolf.NetMasters.com>
+
1.8 3/20/97 fsmp@freefall.org
extended audio support.
card auto-detection.
major cleanup, order of routines, declarations, etc.
+
+1.9 3/22/97 fsmp@freefall.org
+ merged in Amancio's minor unit for tuner control
+ mods.
+ misc. cleanup, especially in the _intr routine.
+ made AUDIO_SUPPORT mainline code.
+
+1.10 3/23/97 fsmp@freefall.org
+ added polled hardware i2c routines,
+ removed all existing software i2c routines.
+ created software i2cProbe() routine.
+ Randall Hopper's fixes of BT848_GHUE & BT848_GBRIG.
+ eeprom support.
*/
#include "bktr.h"
@@ -156,58 +170,6 @@
#include <vm/pmap.h>
#include <vm/vm_extern.h>
-
-/*
- * This is for start-up convenience only, NOT mandatory.
- * XXX: we need to support additional sets of frequencies.
- *
- * this selects the set of frequencies used by the tuner.
- * in your kernel config file set one of:
-options DEFAULT_CHNLSET=1 # CHNLSET_NABCST
-options DEFAULT_CHNLSET=2 # CHNLSET_CABLEIRC
- *
- * alternately, in this file, you can select one of:
- *
-#define DEFAULT_CHNLSET CHNLSET_NABCST
-#define DEFAULT_CHNLSET CHNLSET_CABLEIRC
- */
-#if !defined( DEFAULT_CHNLSET )
-#define DEFAULT_CHNLSET CHNLSET_NABCST
-#endif
-
-/*
- * the recognized cards.
- * used as indexes of several tables.
- */
-#define CARD_UNKNOWN 0
-#define CARD_MIRO 1
-#define CARD_HAUPPAUGE 2
-#define CARD_STB 3
-#define CARD_INTEL 4
-
-
-/*
- * XXX: hack to allow multiple programs to open the device,
- * ie., a tv client and a remote control
- * we need to make this a MINOR UNIT type thing someday...
- */
-#define MULTIPLE_OPENS
-
-/* XXX Fixme: remove me??? */
-#define ORIGINAL_DELAYS_NOT
-
-/* XXX Fixme: anomolies still exist in the i2c code */
-#define EXTRA_START
-#define FUNNY_HI
-#define REALLY_ACK
-
-/* XXX attempt to hold sync on marginal signals, experimental */
-#define LOW_SYNC_NOT
-
-/* srart of audio support */
-#define AUDIO_SUPPORT
-
-
#include "pci.h"
#if NPCI > 0
@@ -275,23 +237,72 @@ static struct cdevsw bktr_cdevsw =
/*
+ * This is for start-up convenience only, NOT mandatory.
+ */
+#if !defined( DEFAULT_CHNLSET )
+#define DEFAULT_CHNLSET CHNLSET_NABCST
+#endif
+
+/*
+ * the recognized cards.
+ * used as indexes of several tables.
+ */
+#define CARD_UNKNOWN 0
+#define CARD_MIRO 1
+#define CARD_HAUPPAUGE 2
+#define CARD_STB 3
+#define CARD_INTEL 4
+
+/*
+ * i2c things:
+ */
+
+/* XXX FIXME: experimental code, use with caution! */
+#define EEPROM_SUPPORT
+
+/* guaranteed address for any TSA5522/3 (PLL on all(?) tuners) */
+#define TSA5522_WADDR 0xc2
+#define TSA5522_RADDR 0xc3
+
+#define TEMIC_TSA5522_RADDR 0xc1
+#define PHILIPS_TSA5523_RADDR 0xc7
+
+/* address of BTSC/SAP decoder chip */
+#define TDA9850_WADDR 0xb6
+#define TDA9850_RADDR 0xb7
+
+/* EEProm (128 * 8) on an STB card */
+#define X24C01_WADDR 0xae
+#define X24C01_RADDR 0xaf
+
+/* EEProm (256 * 8) on a Hauppauge card */
+#define PFC8582_WADDR 0xa0
+#define PFC8582_RADDR 0xa1
+
+/* debug utility for holding previous INT_STAT contents */
+#define STATUS
+static u_long status_sum = 0;
+
+/* FIXME: magic#s sync detect threashold */
+#if 1
+#define SYNC_LEVEL 0x81 /* threashold ~125 mV */
+#else
+#define SYNC_LEVEL 0xa1 /* threashold ~75 mV */
+#endif
+
+
+/*
* misc. support routines.
*/
-struct CARDTYPE {
- char* name;
- u_char tuner;
- u_char dbx;
- u_char audiomuxs[4]; /* tuner, external, internal/unused, mute */
-};
-static struct CARDTYPE card_types[];
-static int probe_card( bktr_reg_t *bktr, int verbose );
-static vm_offset_t get_bktr_mem( int unit, unsigned size );
+static struct CARDTYPE card_types[];
+static int probe_card( bktr_reg_t *bktr, int verbose );
+static vm_offset_t get_bktr_mem( int unit, unsigned size );
/*
* bt848 RISC programming routines.
*/
-static int dump_bt848( volatile u_char *bt848 );
+static int dump_bt848( bt848_reg_t bt848 );
static void yuvpack_prog( bktr_reg_t * bktr, char i_flag, int cols,
int rows, int interlace) ;
@@ -306,6 +317,11 @@ static void build_dma_prog( bktr_reg_t * bktr, char i_flag);
/*
* video & video capture specific routines.
*/
+static int video_open( bktr_reg_t *bktr );
+static int video_close( bktr_reg_t *bktr );
+static int video_ioctl( bktr_reg_t* bktr, int unit,
+ int cmd, caddr_t arg, struct proc* pr );
+
static void start_capture( bktr_reg_t *bktr, unsigned type );
static void set_fps( bktr_reg_t *bktr, u_short fps );
@@ -313,18 +329,38 @@ static void set_fps( bktr_reg_t *bktr, u_short fps );
/*
* tuner specific functions.
*/
+static int tuner_open( bktr_reg_t* bktr );
+static int tuner_close( bktr_reg_t* bktr );
+static int tuner_ioctl( bktr_reg_t* bktr, int unit,
+ int cmd, caddr_t arg, struct proc* pr );
+
static int tv_channel( bktr_reg_t* bktr, int channel );
static int tv_freq( bktr_reg_t* bktr, int frequency );
-static int tuner_status( bktr_reg_t* bktr );
-#if defined( AUDIO_SUPPORT )
/*
* audio specific functions.
*/
static int set_audio( bktr_reg_t * bktr, int mode );
static int set_BTSC( bktr_reg_t * bktr, int control );
-#endif /* AUDIO_SUPPORT */
+
+
+/*
+ *
+ */
+static int common_ioctl( bktr_reg_t* bktr, bt848_reg_t bt848,
+ int cmd, caddr_t arg );
+
+
+/*
+ * i2c primitives
+ */
+static int i2cWrite( bktr_reg_t *bktr, int addr, int byte1, int byte2 );
+static int i2cRead( bktr_reg_t *bktr, int addr );
+#if defined( EEPROM_SUPPORT )
+static int readEEProm( bktr_reg_t* bktr, int offset, int count,
+ u_char* data );
+#endif /* EEPROM_SUPPORT */
/*
@@ -343,160 +379,6 @@ bktr_probe( pcici_t tag, pcidi_t type )
/*
- * interrupt handling routine complete bktr_read() if using interrupts.
- */
-static void
-bktr_intr( void *arg )
-{
- bktr_reg_t *bktr = (bktr_reg_t *) arg;
- volatile u_long *btl_reg, t_pc;
- volatile u_char *bt848, *bt_reg, s_status;
- volatile u_short *bts_reg;
- u_long bktr_status, *bktr_pc;
-
-#if 0
-/* XXX: what is this for??? */
- u_long next_base = (u_long)(vtophys(bktr->bigbuf)), stat;
-#endif
-
- bt848 = bktr->base;
- bt_reg = (u_char *) &bt848;
- s_status = *bt_reg;
- *bt_reg = 0;
-
- if (!(bktr->flags & METEOR_OPEN)) {
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
- }
-
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- bktr_status = *btl_reg ;
- *btl_reg = *btl_reg;
- *btl_reg = 0;
- if (*btl_reg & (1 << 25))
- *btl_reg |= 1 << 8;
- bktr_pc = (u_long *) &bt848[BKTR_RISC_COUNT];
- t_pc = *bktr_pc;
-
- /* printf(" STATUS %x %x %x \n", s_status, bktr_status, t_pc); */
-
- if (!((bktr_status & 0x800) || (bktr_status & 1 << 19 ))) {
- btl_status_prev = bktr_status;
- /* return; */
- }
-
- /* if risc was disabled re-start process again */
- if (!(bktr_status & (1 << 27)) || ((bktr_status & 0xff000) != 0) ) {
-
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = *btl_reg;
-
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
-
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
-
- btl_reg = (u_long *) &bt848[BKTR_RISC_STRT_ADD] ;
- *btl_reg = vtophys(bktr->dma_prog);
-
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 1;
- *bts_reg = bktr->capcontrol;
-
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 1 << 23 | 1 << 11 | 2 | 1;
- bt848[BKTR_CAP_CTL] = bktr->bktr_cap_ctl;
-
- return;
- }
-
- btl_reg = (u_long *) &bt848[BKTR_CAP_CTL];
- if (!(bktr_status & (1 << 11))) return;
-
- bktr_pc = (u_long *) &bt848[BKTR_RISC_COUNT];
-
- /*printf("intr status %x %x %x\n", bktr_status, s_status, *bktr_pc);*/
-
- /*
- * Disable future interrupts if a capture mode is not selected.
- * This can happen when we are in the process of closing or
- * changing capture modes, otherwise it shouldn't happen.
- */
- if (!(bktr->flags & METEOR_CAP_MASK))
- *btl_reg = 0;
-
- /*
- * If we have a complete frame.
- */
- if (!(bktr->flags & METEOR_WANT_MASK)) {
- bktr->frames_captured++;
- /*
- * post the completion time.
- */
- if (bktr->flags & METEOR_WANT_TS) {
- struct timeval *ts;
-
- if ((u_int) bktr->alloc_pages * PAGE_SIZE
- <= (bktr->frame_size + sizeof(struct timeval))) {
- ts =(struct timeval *)bktr->bigbuf +
- bktr->frame_size;
- /* doesn't work in synch mode except
- * for first frame */
- /* XXX */
- microtime(ts);
- }
- }
-
- /*
- * Wake up the user in single capture mode.
- */
- if (bktr->flags & METEOR_SINGLE) {
-
- if (!(bktr_status & (1 << 24)))
- return;
-
- /* stop dma */
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 1; /* disable risc and fifo */
- wakeup((caddr_t)bktr);
- }
-
- /*
- * If the user requested to be notified via signal,
- * let them know the frame is complete.
- */
- if (bktr->proc && !(bktr->signal & METEOR_SIG_MODE_MASK))
- psignal(bktr->proc, bktr->signal&(~METEOR_SIG_MODE_MASK));
-
- /*
- * Reset the want flags if in continuous or
- * synchronous capture mode.
- */
- if (bktr->flags & (METEOR_CONTIN|METEOR_SYNCAP)) {
- switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
- case METEOR_ONLY_ODD_FIELDS:
- bktr->flags |= METEOR_WANT_ODD;
- break;
- case METEOR_ONLY_EVEN_FIELDS:
- bktr->flags |= METEOR_WANT_EVEN;
- break;
- default:
- bktr->flags |= METEOR_WANT_MASK;
- break;
- }
- }
- }
-
- return;
-}
-
-
-/*
* what should we do here?
*/
static void
@@ -513,8 +395,7 @@ static void
bktr_attach( pcici_t tag, int unit )
{
bktr_reg_t *bktr;
- volatile u_char *bt848;
- volatile u_long *btl_reg;
+ bt848_reg_t bt848;
#ifdef BROOKTREE_IRQ
u_long old_irq, new_irq;
#endif
@@ -615,9 +496,8 @@ end of setup up dma risc program
bktr->depth = 2; /* two bytes per pixel */
bktr->frames = 1; /* one frame */
bt848 = bktr->base;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
- bt848[BKTR_GPIO_DMA_CTL] = 0;
+ bt848->int_mask = 0;
+ bt848->gpio_dma_ctl = 0;
}
/* defaults for the tuner section of the card */
@@ -633,7 +513,167 @@ end of setup up dma risc program
#endif /* DEVFS */
}
-#define UNIT(x) ((x) & 0x07)
+
+/*
+ * interrupt handling routine complete bktr_read() if using interrupts.
+ */
+static void
+bktr_intr( void *arg )
+{
+
+ bktr_reg_t *bktr = (bktr_reg_t *) arg;
+ volatile u_long *bktr_pc;
+ bt848_reg_t bt848;
+ u_long bktr_status;
+ u_char dstatus;
+
+ bt848 = bktr->base;
+
+ /*
+ * check to see if any interrupts are unmasked on this device. If
+ * none are, then we likely got here by way of being on a PCI shared
+ * interrupt dispatch list.
+ */
+ if ( bt848->int_mask == 0 )
+ return; /* bail out now, before we do something we
+ shouldn't */
+
+ if (!(bktr->flags & METEOR_OPEN)) {
+ bt848->gpio_dma_ctl = 0;
+ bt848->int_mask = 0;
+ /* return; ?? */
+ }
+
+ /* record and clear the INTerrupt status bits */
+ bktr_status = bt848->int_stat;
+ bt848->int_stat = bt848->int_stat;
+
+ /* record and clear the device status register */
+ dstatus = bt848->dstatus;
+ bt848->dstatus = 0;
+
+#if defined( STATUS )
+ /* add any new device status or INTerrupt status bits */
+ status_sum |= (bktr_status & ~0xc0); /* clear 2 resv bits */
+ status_sum |= ((dstatus & 0x03) << 6); /* device LOF/COF */
+#endif /* STATUS */
+
+#if 0
+ /* check i2c status */
+ if (bt848->int_stat & (1 << 25)) /* XXX bug, already cleared above */
+ bt848->int_stat |= 1 << 8;
+#endif
+
+#if 0
+ bktr_pc = bt848->risc_count;
+ printf( " STATUS %x %x %x \n", dstatus, bktr_status, *bktr_pc );
+#endif
+
+ if (!((bktr_status & 0x800) || (bktr_status & 1 << 19 ))) {
+ btl_status_prev = bktr_status;
+ /* return; */
+ }
+
+ /* if risc was disabled re-start process again */
+ if (!(bktr_status & (1 << 27)) || ((bktr_status & 0xff000) != 0) ) {
+
+/* XXX isn't this redundant ??? */
+ bt848->int_stat = bt848->int_stat;
+
+ bt848->gpio_dma_ctl = 0;
+
+ bt848->int_mask = 0;
+
+ bt848->risc_strt_add = vtophys(bktr->dma_prog);
+
+ bt848->gpio_dma_ctl = 1;
+ bt848->gpio_dma_ctl = bktr->capcontrol;
+
+ bt848->int_mask = 1 << 23 | 1 << 11 | 2 | 1;
+ bt848->cap_ctl = bktr->bktr_cap_ctl;
+
+ return;
+ }
+
+ if (!(bktr_status & (1 << 11)))
+ return;
+#if 0
+ printf( "intr status %x %x %x\n", bktr_status, dstatus,
+ bt848->risc_count);
+#endif
+
+ /*
+ * Disable future interrupts if a capture mode is not selected.
+ * This can happen when we are in the process of closing or
+ * changing capture modes, otherwise it shouldn't happen.
+ */
+ if (!(bktr->flags & METEOR_CAP_MASK))
+ bt848->cap_ctl = 0;
+
+ /*
+ * If we have a complete frame.
+ */
+ if (!(bktr->flags & METEOR_WANT_MASK)) {
+ bktr->frames_captured++;
+ /*
+ * post the completion time.
+ */
+ if (bktr->flags & METEOR_WANT_TS) {
+ struct timeval *ts;
+
+ if ((u_int) bktr->alloc_pages * PAGE_SIZE
+ <= (bktr->frame_size + sizeof(struct timeval))) {
+ ts =(struct timeval *)bktr->bigbuf +
+ bktr->frame_size;
+ /* doesn't work in synch mode except
+ * for first frame */
+ /* XXX */
+ microtime(ts);
+ }
+ }
+
+ /*
+ * Wake up the user in single capture mode.
+ */
+ if (bktr->flags & METEOR_SINGLE) {
+
+ if (!(bktr_status & (1 << 24)))
+ return;
+
+ /* stop dma */
+ bt848->int_mask = 0;
+ bt848->gpio_dma_ctl = 1; /* disable risc and fifo */
+ wakeup((caddr_t)bktr);
+ }
+
+ /*
+ * If the user requested to be notified via signal,
+ * let them know the frame is complete.
+ */
+ if (bktr->proc && !(bktr->signal & METEOR_SIG_MODE_MASK))
+ psignal(bktr->proc, bktr->signal&(~METEOR_SIG_MODE_MASK));
+
+ /*
+ * Reset the want flags if in continuous or
+ * synchronous capture mode.
+ */
+ if (bktr->flags & (METEOR_CONTIN|METEOR_SYNCAP)) {
+ switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
+ case METEOR_ONLY_ODD_FIELDS:
+ bktr->flags |= METEOR_WANT_ODD;
+ break;
+ case METEOR_ONLY_EVEN_FIELDS:
+ bktr->flags |= METEOR_WANT_EVEN;
+ break;
+ default:
+ bktr->flags |= METEOR_WANT_MASK;
+ break;
+ }
+ }
+ }
+
+ return;
+}
/*---------------------------------------------------------
@@ -644,6 +684,9 @@ end of setup up dma risc program
*/
+#define UNIT(x) ((x) & 0x0f)
+#define MINOR(x) ((x) & 0xf0)
+
/*
*
*/
@@ -651,11 +694,9 @@ int
bktr_open( dev_t dev, int flags, int fmt, struct proc *p )
{
bktr_reg_t *bktr;
- int unit;
+ int unit, minor;
int i;
- volatile u_char *bt848;
- volatile u_char *bt_reg;
- volatile u_long *btl_reg;
+ bt848_reg_t bt848;
unit = UNIT(minor(dev));
if (unit >= NBKTR) /* unit out of range */
@@ -666,46 +707,51 @@ bktr_open( dev_t dev, int flags, int fmt, struct proc *p )
if (!(bktr->flags & METEOR_INITALIZED)) /* device not found */
return(ENXIO);
-#if defined( MULTIPLE_OPENS )
- if (bktr->flags & METEOR_OPEN) /* device already open */
- return 0;
-#else
+ if ( minor(dev) & 0x0010 )
+ return tuner_open( bktr );
+ else
+ return video_open( bktr );
+}
+
+
+/*
+ *
+ */
+static int
+video_open( bktr_reg_t *bktr )
+{
+ bt848_reg_t bt848;
+
if (bktr->flags & METEOR_OPEN) /* device is busy */
return(EBUSY);
-#endif /* MULTIPLE_OPENS */
bktr->flags |= METEOR_OPEN;
-
+
bt848 = bktr->base;
#if 0
dump_bt848( bt848 );
#endif /* 0 */
- *bt848 = 0x3; /* bt848[ 0 ] */
- *bt848 = 0xc0;
+ bt848->dstatus = 0x00; /* bt848[ DSTATUS ] */
-#if defined( LOW_SYNC )
- bt848[BKTR_ADC] = 0xa1;
-#else
- bt848[BKTR_ADC] = 0x81;
-#endif /* LOW_SYNC */
+ bt848->adc = SYNC_LEVEL;
- bt848[BKTR_IFORM] = 0x69;
+ bt848->iform = 0x69;
bktr->flags = (bktr->flags & ~METEOR_DEV_MASK) | METEOR_DEV0;
- bt848[BKTR_COLOR_CTL] = 0x20;
+ bt848->color_ctl = 0x20;
- bt848[BKTR_E_HSCALE_LO] = 0xaa;
- bt848[BKTR_O_HSCALE_LO] = 0xaa;
+ bt848->e_hscale_lo = 0xaa;
+ bt848->o_hscale_lo = 0xaa;
- bt848[BKTR_E_DELAY_LO] = 0x72;
- bt848[BKTR_O_DELAY_LO] = 0x72;
- bt848[BKTR_E_SCLOOP] = 0;
- bt848[BKTR_O_SCLOOP] = 0;
+ bt848->e_delay_lo = 0x72;
+ bt848->o_delay_lo = 0x72;
+ bt848->e_scloop = 0;
+ bt848->o_scloop = 0;
- bt848[BKTR_VBI_PACK_SIZE] = 0;
- bt848[BKTR_VBI_PACK_DEL] = 0;
+ bt848->vbi_pack_size = 0;
+ bt848->vbi_pack_del = 0;
bzero((u_char *) bktr->bigbuf, 640*480*4);
bktr->fifo_errors = 0;
@@ -720,16 +766,28 @@ bktr_open( dev_t dev, int flags, int fmt, struct proc *p )
bktr->video.banksize = 0;
bktr->video.ramsize = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 1 << 23;
+ bt848->int_mask = 1 << 23; /* ? */
+
+ return( 0 );
+}
+
+
+/*
+ *
+ */
+static int
+tuner_open( bktr_reg_t *bktr )
+{
+ bt848_reg_t bt848 = bktr->base;
+
+#define GPIO_AUDIOMUX_BITS 0x07
+ bt848->gpio_out_en = GPIO_AUDIOMUX_BITS; /* drive low 3 bits */
-#if defined( AUDIO_SUPPORT )
set_audio( bktr, AUDIO_UNMUTE );
- if ( card_types[ bktr->card_type ].dbx )
- set_BTSC( bktr, 0 ); /* enable the stereo chip */
-#endif /* AUDIO_SUPPORT */
+ if ( bktr->card->dbx )
+ set_BTSC( bktr, 0 ); /* enable stereo */
- return(0);
+ return( 0 );
}
@@ -741,9 +799,8 @@ bktr_close( dev_t dev, int flags, int fmt, struct proc *p )
{
bktr_reg_t *bktr;
int unit;
- volatile u_char *bt848;
- volatile u_long *btl_reg;
- u_short *bts_reg;
+ bt848_reg_t bt848;
+
#ifdef METEOR_DEALLOC_ABOVE
int temp;
#endif
@@ -754,29 +811,55 @@ bktr_close( dev_t dev, int flags, int fmt, struct proc *p )
bktr = &(brooktree[unit]);
+ if ( minor(dev) & 0x0010 )
+ return tuner_close( bktr );
+ else
+ return video_close( bktr );
+}
+
+
+/*
+ *
+ */
+static int
+video_close( bktr_reg_t *bktr )
+{
+ bt848_reg_t bt848;
+
bktr->flags &= ~METEOR_OPEN;
bktr->flags &= ~(METEOR_SINGLE | METEOR_WANT_MASK);
bktr->flags &= ~(METEOR_CAP_MASK|METEOR_WANT_MASK);
+
bt848 = bktr->base;
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
- bt848[BKTR_CAP_CTL] = 0;
+ bt848->gpio_dma_ctl = 0;
+ bt848->cap_ctl = 0;
bktr->dma_prog_loaded = 0;
- bt848[BKTR_TDEC] = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
+ bt848->tdec = 0;
+ bt848->int_mask = 0;
- bt848[BKTR_SRESET] = 0xf;
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT] ;
- *btl_reg = 0xffffffff;
+ bt848->sreset = 0xf;
+ bt848->int_stat = 0xffffffff;
+
+ return( 0 );
+}
+
+
+/*
+ * tuner close handle,
+ * place holder for tuner specific operations on a close.
+ */
+static int
+tuner_close( bktr_reg_t *bktr )
+{
+ bt848_reg_t bt848 = bktr->base;
-#if defined( AUDIO_SUPPORT )
/* mute the audio by switching the mux */
set_audio( bktr, AUDIO_MUTE );
-#endif /* AUDIO_SUPPORT */
- return(0);
+ bt848->gpio_out_en = 0; /* float low 3 bits */
+
+ return( 0 );
}
@@ -790,9 +873,9 @@ bktr_read( dev_t dev, struct uio *uio, int ioflag )
int unit;
int status;
int count;
- volatile u_char *bt848;
- u_short *bts_reg;
-
+ bt848_reg_t bt848;
+
+ if (minor(dev) > 0 ) return(ENXIO);
unit = UNIT(minor(dev));
if (unit >= NBKTR) /* unit out of range */
return(ENXIO);
@@ -804,7 +887,7 @@ bktr_read( dev_t dev, struct uio *uio, int ioflag )
if (bktr->flags & METEOR_CAP_MASK)
return(EIO); /* already capturing */
- bt848 = (u_char *) bktr->base;
+ bt848 = bktr->base;
count = bktr->rows * bktr->cols * bktr->depth;
@@ -813,9 +896,8 @@ bktr_read( dev_t dev, struct uio *uio, int ioflag )
bktr->flags &= ~(METEOR_CAP_MASK|METEOR_WANT_MASK);
/* Start capture */
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0x1;
- *bts_reg = 0x3;
+ bt848->gpio_dma_ctl = 0x1;
+ bt848->gpio_dma_ctl = 0x3;
status=tsleep((caddr_t)bktr, METPRI, "capturing", 0);
if (!status) /* successful capture */
@@ -835,7 +917,7 @@ bktr_read( dev_t dev, struct uio *uio, int ioflag )
int
bktr_write( dev_t dev, struct uio *uio, int ioflag )
{
- return(0);
+ return( 0 );
}
@@ -843,166 +925,73 @@ bktr_write( dev_t dev, struct uio *uio, int ioflag )
*
*/
int
-bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
+bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc* pr )
{
- bktr_reg_t *bktr;
- int unit;
- int status;
- int count;
- int tmp_int;
- volatile u_char *bt848, c_temp;
- volatile u_short *bts_reg, s_temp;
- volatile u_long *btl_reg;
- unsigned int temp, temp1;
- unsigned int error;
- struct meteor_geomet *geo;
- struct meteor_counts *cnt;
- struct meteor_video *video;
- vm_offset_t buf;
+ bktr_reg_t* bktr;
+ int unit;
unit = UNIT(minor(dev));
if (unit >= NBKTR) /* unit out of range */
- return(ENXIO);
+ return( ENXIO );
+ bktr = &(brooktree[ unit ]);
- bktr = &(brooktree[unit]);
if (bktr->bigbuf == 0) /* no frame buffer allocated (ioctl failed) */
- return(ENOMEM);
-
- bt848 = bktr->base;
- switch (cmd) {
-
- case TVTUNER_SETCHNL:
-#if defined( AUDIO_SUPPORT )
- set_audio( bktr, AUDIO_MUTE );
-#endif /* AUDIO_SUPPORT */
- temp = tv_channel( bktr, (int)*(unsigned long *)arg );
-#if defined( AUDIO_SUPPORT )
- set_audio( bktr, AUDIO_UNMUTE );
-#endif /* AUDIO_SUPPORT */
- if ( temp < 0 )
- return EINVAL;
- *(unsigned long *)arg = temp;
- break;
-
- case TVTUNER_GETCHNL:
- *(unsigned long *)arg = bktr->tuner.channel;
- break;
+ return( ENOMEM );
- case TVTUNER_SETTYPE:
- temp = *(unsigned long *)arg;
- if ( (temp < CHNLSET_MIN) || (temp > CHNLSET_MAX) )
- return EINVAL;
- bktr->tuner.chnlset = temp;
- break;
+ if ( minor(dev) & 0x0010 )
+ return tuner_ioctl( bktr, unit, cmd, arg, pr );
+ else
+ return video_ioctl( bktr, unit, cmd, arg, pr );
+}
- case TVTUNER_GETTYPE:
- *(unsigned long *)arg = bktr->tuner.chnlset;
- break;
- case TVTUNER_GETSTATUS:
- temp = tuner_status( bktr );
- *(unsigned long *)arg = temp & 0xff;
- break;
+/*
+ * video ioctls
+ */
+static int
+video_ioctl( bktr_reg_t* bktr, int unit,
+ int cmd, caddr_t arg, struct proc* pr )
+{
+ int status;
+ int count;
+ int tmp_int;
+ bt848_reg_t bt848;
+ volatile u_char c_temp;
+ volatile u_short s_temp;
+ unsigned int temp, temp1;
+ unsigned int error;
+ struct meteor_geomet *geo;
+ struct meteor_counts *cnt;
+ struct meteor_video *video;
+ vm_offset_t buf;
- case TVTUNER_SETFREQ:
-#if defined( AUDIO_SUPPORT_XXX )
- set_audio( bktr, AUDIO_MUTE );
-#endif /* AUDIO_SUPPORT */
- temp = tv_freq( bktr, (int)*(unsigned long *)arg );
-#if defined( AUDIO_SUPPORT_XXX )
- set_audio( bktr, AUDIO_UNMUTE );
-#endif /* AUDIO_SUPPORT */
- if ( temp < 0 )
- return EINVAL;
- *(unsigned long *)arg = temp;
- break;
+ bt848 = bktr->base;
- case TVTUNER_GETFREQ:
- *(unsigned long *)arg = bktr->tuner.frequency;
- break;
+ switch ( cmd ) {
- case METEORSTATUS: /* get 7196 status */
- c_temp = bt848[0];
+ case METEORSTATUS: /* get Bt848 status */
+ c_temp = bt848->dstatus;
temp = 0;
if (!(c_temp & 0x40)) temp |= METEOR_STATUS_HCLK;
if (!(c_temp & 0x10)) temp |= METEOR_STATUS_FIDT;
*(u_short *)arg = temp;
break;
- case METEORSINPUT: /* set input device */
- switch(*(unsigned long *)arg & METEOR_DEV_MASK) {
-
- /* this is the RCA video input */
- case 0: /* default */
- case METEOR_INPUT_DEV0:
- bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
- | METEOR_DEV0;
- bt848[BKTR_IFORM] &= ~0x60;
- bt848[BKTR_IFORM] |= 0x60;
- bt848[BKTR_E_CONTROL] &= ~0x40;
- bt848[BKTR_O_CONTROL] &= ~0x40;
-#if defined( AUDIO_SUPPORT )
- set_audio( bktr, AUDIO_MUTE );
- set_audio( bktr, AUDIO_EXTERN );
- set_audio( bktr, AUDIO_UNMUTE );
-#endif /* AUDIO_SUPPORT */
- break;
-
- /* this is the tuner input */
- case METEOR_INPUT_DEV1:
- bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
- | METEOR_DEV1;
- bt848[BKTR_IFORM] &= ~0x60;
- bt848[BKTR_IFORM] |= 0x40;
- bt848[BKTR_E_CONTROL] &= ~0x40;
- bt848[BKTR_O_CONTROL] &= ~0x40;
-#if defined( AUDIO_SUPPORT )
- set_audio( bktr, AUDIO_MUTE );
- set_audio( bktr, AUDIO_TUNER );
- set_audio( bktr, AUDIO_UNMUTE );
-#endif /* AUDIO_SUPPORT */
- break;
-
- /* this is the S-VHS input */
- case METEOR_INPUT_DEV2:
- case METEOR_INPUT_DEV_SVIDEO:
- bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
- | METEOR_DEV2;
- bt848[BKTR_IFORM] &= ~0x60;
- bt848[BKTR_IFORM] |= 0x20;
- bt848[BKTR_E_CONTROL] |= 0x40;
- bt848[BKTR_O_CONTROL] |= 0x40;
-#if defined( AUDIO_SUPPORT )
- set_audio( bktr, AUDIO_MUTE );
- set_audio( bktr, AUDIO_EXTERN );
- set_audio( bktr, AUDIO_UNMUTE );
-#endif /* AUDIO_SUPPORT */
- break;
-
- default:
- return EINVAL;
- }
- break;
-
- case METEORGINPUT: /* get input device */
- *(u_long *)arg = bktr->flags & METEOR_DEV_MASK;
- break;
-
case METEORSFMT: /* set input format */
switch(*(unsigned long *)arg & METEOR_FORM_MASK ) {
case 0: /* default */
case METEOR_FMT_NTSC:
bktr->flags = (bktr->flags & ~METEOR_FORM_MASK) |
METEOR_NTSC;
- bt848[BKTR_IFORM] &= ~0x3;
- bt848[BKTR_IFORM] |= 1;
+ bt848->iform &= ~0x3;
+ bt848->iform |= 1;
break;
case METEOR_FMT_AUTOMODE:
bktr->flags = (bktr->flags & ~METEOR_FORM_MASK) |
METEOR_AUTOMODE;
- bt848[BKTR_IFORM] &= ~0x3;
+ bt848->iform &= ~0x3;
break;
default:
@@ -1057,39 +1046,39 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
break;
case METEORSHUE: /* set hue */
- bt848[BKTR_HUE] = (*(u_char *) arg) & 0xff;
+ bt848->hue = (*(u_char *) arg) & 0xff;
break;
case METEORGHUE: /* get hue */
- *(u_char *)arg = bt848[BKTR_HUE];
+ *(u_char *)arg = bt848->hue;
break;
case METEORSBRIG: /* set brightness */
- bt848[BKTR_BRIGHT] = *(u_char *)arg & 0xff;
+ bt848->bright = *(u_char *)arg & 0xff;
break;
case METEORGBRIG: /* get brightness */
- *(u_char *)arg = bt848[BKTR_BRIGHT];
+ *(u_char *)arg = bt848->bright;
break;
case METEORSCSAT: /* set chroma saturation */
temp = (int)*(u_char *)arg;
- bt848[BKTR_SAT_U_LO] = bt848[BKTR_SAT_V_LO] =
+ bt848->sat_u_lo = bt848->sat_v_lo =
(temp << 1) & 0xff;
- bt848[BKTR_E_CONTROL] &= ~0x3; /* clear U/V MSBs */
- bt848[BKTR_O_CONTROL] &= ~0x3; /* clear U/V MSBs */
+ bt848->e_control &= ~0x3; /* clear U/V MSBs */
+ bt848->o_control &= ~0x3; /* clear U/V MSBs */
if ( temp & 0x80 ) {
- bt848[BKTR_E_CONTROL] |= 0x3;
- bt848[BKTR_O_CONTROL] |= 0x3;
+ bt848->e_control |= 0x3;
+ bt848->o_control |= 0x3;
}
break;
case METEORGCSAT: /* get chroma saturation */
- temp = (bt848[BKTR_SAT_V_LO] >> 1) & 0xff;
- if ( bt848[BKTR_E_CONTROL] & 0x01 )
+ temp = (bt848->sat_v_lo >> 1) & 0xff;
+ if ( bt848->e_control & 0x01 )
temp |= 0x80;
*(u_char *)arg = (u_char)temp;
break;
@@ -1097,157 +1086,19 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
case METEORSCONT: /* set contrast */
temp = (int)*(u_char *)arg & 0xff;
temp <<= 1;
- bt848[BKTR_CONTRAST_LO] = temp & 0xff;
- bt848[BKTR_E_CONTROL] &= ~0x4;
- bt848[BKTR_O_CONTROL] &= ~0x4;
- bt848[BKTR_E_CONTROL] |= ((temp & 0x100) >> 6 ) & 0x4 ;
- bt848[BKTR_O_CONTROL] |= ((temp & 0x100) >> 6 ) & 0x4 ;
+ bt848->contrast_lo = temp & 0xff;
+ bt848->e_control &= ~0x4;
+ bt848->o_control &= ~0x4;
+ bt848->e_control |= ((temp & 0x100) >> 6 ) & 0x4 ;
+ bt848->o_control |= ((temp & 0x100) >> 6 ) & 0x4 ;
break;
case METEORGCONT: /* get contrast */
- temp = (int)bt848[BKTR_CONTRAST_LO] & 0xff;
- temp |= ((int)bt848[BKTR_O_CONTROL] & 0x04) << 6;
+ temp = (int)bt848->contrast_lo & 0xff;
+ temp |= ((int)bt848->o_control & 0x04) << 6;
*(u_char *)arg = (u_char)((temp >> 1) & 0xff);
break;
- /* hue is a 2's compliment number, -90' to +89.3' in 0.7' steps */
- case BT848_SHUE: /* set hue */
- bt848[BKTR_HUE] = (u_char)(*(int*)arg & 0xff);
- break;
-
- case BT848_GHUE: /* get hue */
- *(int*)arg = bt848[BKTR_HUE] & 0xff;
- break;
-
- /* brightness is a 2's compliment #, -50 to +%49.6% in 0.39% steps */
- case BT848_SBRIG: /* set brightness */
- bt848[BKTR_BRIGHT] = (u_char)(*(int *)arg & 0xff);
- break;
-
- case BT848_GBRIG: /* get brightness */
- *(int *)arg = bt848[BKTR_BRIGHT] & 0xff;
- break;
-
- /* */
- case BT848_SCSAT: /* set chroma saturation */
- tmp_int = *(int*)arg;
-
- temp = bt848[BKTR_E_CONTROL] & 0xfc;
- temp1 = bt848[BKTR_O_CONTROL] & 0xfc;
- if ( tmp_int & 0x100 ) {
- temp |= 0x03;
- temp1 |= 0x03;
- }
-
- bt848[BKTR_SAT_U_LO] = (u_char)(tmp_int & 0xff);
- bt848[BKTR_SAT_V_LO] = (u_char)(tmp_int & 0xff);
- bt848[BKTR_E_CONTROL] = temp;
- bt848[BKTR_O_CONTROL] = temp1;
- break;
-
- case BT848_GCSAT: /* get chroma saturation */
- tmp_int = (int)bt848[BKTR_SAT_V_LO] & 0xff;
- if ( bt848[BKTR_E_CONTROL] & 0x01 )
- tmp_int |= 0x0100;
- *(int*)arg = tmp_int;
- break;
-
- /* */
- case BT848_SVSAT: /* set chroma V saturation */
- tmp_int = *(int*)arg;
-
- temp = bt848[BKTR_E_CONTROL] & 0xfe;
- temp1 = bt848[BKTR_O_CONTROL] & 0xfe;
- if ( tmp_int & 0x100 ) {
- temp |= 0x01;
- temp1 |= 0x01;
- }
-
- bt848[BKTR_SAT_V_LO] = (u_char)(tmp_int & 0xff);
- bt848[BKTR_E_CONTROL] = temp;
- bt848[BKTR_O_CONTROL] = temp1;
- break;
-
- case BT848_GVSAT: /* get chroma V saturation */
- tmp_int = (int)bt848[BKTR_SAT_V_LO] & 0xff;
- if ( bt848[BKTR_E_CONTROL] & 0x01 )
- tmp_int |= 0x0100;
- *(int*)arg = tmp_int;
- break;
-
- /* */
- case BT848_SUSAT: /* set chroma U saturation */
- tmp_int = *(int*)arg;
-
- temp = bt848[BKTR_E_CONTROL] & 0xfd;
- temp1 = bt848[BKTR_O_CONTROL] & 0xfd;
- if ( tmp_int & 0x100 ) {
- temp |= 0x02;
- temp1 |= 0x02;
- }
-
- bt848[BKTR_SAT_U_LO] = (u_char)(tmp_int & 0xff);
- bt848[BKTR_E_CONTROL] = temp;
- bt848[BKTR_O_CONTROL] = temp1;
- break;
-
- case BT848_GUSAT: /* get chroma U saturation */
- tmp_int = (int)bt848[BKTR_SAT_U_LO] & 0xff;
- if ( bt848[BKTR_E_CONTROL] & 0x02 )
- tmp_int |= 0x0100;
- *(int*)arg = tmp_int;
- break;
-
- /* */
- case BT848_SCONT: /* set contrast */
- tmp_int = *(int*)arg;
-
- temp = bt848[BKTR_E_CONTROL] & 0xfb;
- temp1 = bt848[BKTR_O_CONTROL] & 0xfb;
- if ( tmp_int & 0x100 ) {
- temp |= 0x04;
- temp1 |= 0x04;
- }
-
- bt848[BKTR_CONTRAST_LO] = (u_char)(tmp_int & 0xff);
- bt848[BKTR_E_CONTROL] = temp;
- bt848[BKTR_O_CONTROL] = temp1;
- break;
-
- case BT848_GCONT: /* get contrast */
- tmp_int = (int)bt848[BKTR_CONTRAST_LO] & 0xff;
- if ( bt848[BKTR_E_CONTROL] & 0x04 )
- tmp_int |= 0x0100;
- *(int*)arg = tmp_int;
- break;
-
- case BT848_SCBARS: /* set colorbar output */
- bt848[BKTR_COLOR_CTL] |= 0x40;
- break;
-
- case BT848_CCBARS: /* clear colorbar output */
- bt848[BKTR_COLOR_CTL] &= ~0x40;
- break;
-
-#if defined( AUDIO_SUPPORT )
- case BT848_SAUDIO: /* set audio channel */
- if ( set_audio( bktr, *(int*)arg ) < 0 )
- return EIO;
- break;
-
- case BT848_GAUDIO: /* get audio channel */
- temp = bktr->audio_mux_select;
- if ( bktr->audio_mute_state == TRUE )
- temp |= AUDIO_MUTE;
- *(int*)arg = temp;
- break;
-
- case BT848_SBTSC: /* set audio channel */
- if ( set_BTSC( bktr, *(int*)arg ) < 0 )
- return EIO;
- break;
-#endif /* AUDIO_SUPPORT */
-
case METEORSSIGNAL:
bktr->signal = *(int *) arg;
bktr->proc = pr;
@@ -1273,29 +1124,25 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
bktr->flags &= ~METEOR_WANT_MASK;
/* wait for capture to complete */
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = 0xffffffff;
-
- btl_reg = (u_long *) &bt848[BKTR_GPIO_OUT_EN];
- *btl_reg = 1;
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0x1;
- *bts_reg = bktr->capcontrol;
+ bt848->int_stat = 0xffffffff;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
+#if 0
+XXX why was this done???
+ bt848->gpio_out_en = 1;
+#endif
+ bt848->gpio_dma_ctl = 0x1;
+ bt848->gpio_dma_ctl = bktr->capcontrol;
- *btl_reg = 1 << 23 | 1 << 11 | 2 | 1;
+ bt848->int_mask = 1 << 23 | 1 << 11 | 2 | 1;
error=tsleep((caddr_t)bktr, METPRI, "capturing", hz);
if (error) {
- btl_reg = (u_long *) &bt848[BKTR_RISC_COUNT];
-
printf("bktr%d: ioctl: tsleep error %d %x\n",
- unit, error, *btl_reg);
+ unit, error, bt848->risc_count);
}
bktr->flags &= ~(METEOR_SINGLE|METEOR_WANT_MASK);
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
+ /* bt848->int_stat; ?? */
break;
case METEOR_CAP_CONTINOUS:
@@ -1306,16 +1153,12 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
return(EIO); /* already capturing */
start_capture(bktr, METEOR_CONTIN);
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = *btl_reg;
-
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
+ bt848->int_stat = bt848->int_stat;
- *bts_reg = 1;
- *bts_reg = bktr->capcontrol;
+ bt848->gpio_dma_ctl = 1;
+ bt848->gpio_dma_ctl = bktr->capcontrol;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 1 << 23 | 1 << 11 | 2 | 1;
+ bt848->int_mask = 1 << 23 | 1 << 11 | 2 | 1;
#if 0
dump_bt848( bt848 );
@@ -1326,12 +1169,10 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
case METEOR_CAP_STOP_CONT:
if (bktr->flags & METEOR_CONTIN) {
/* turn off capture */
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
- bts_reg = (u_short *)&bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
-
- bktr->flags &= ~(METEOR_CONTIN|METEOR_WANT_MASK);
+ bt848->int_mask = 0;
+ bt848->gpio_dma_ctl = 0;
+ bktr->flags &=
+ ~(METEOR_CONTIN|METEOR_WANT_MASK);
}
}
break;
@@ -1385,13 +1226,12 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
error = EINVAL;
}
- if (error) return error;
+ if (error)
+ return error;
bktr->dma_prog_loaded = 0;
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
+ bt848->gpio_dma_ctl = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
+ bt848->int_mask = 0;
if (temp=geo->rows * geo->columns * geo->frames * 2) {
if (geo->oformat & METEOR_GEO_RGB24) temp = temp * 2;
@@ -1431,30 +1271,30 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
temp = ((910.0/( (float) bktr->cols *1.21875)) - 1.0) * 4096.0;
/* temp = ((754.0/(float) bktr->cols) - 1 ) * 4096.0;*/
- bt848[BKTR_E_HSCALE_LO] = temp & 0xff;
- bt848[BKTR_O_HSCALE_LO] = temp & 0xff;
- bt848[BKTR_E_HSCALE_HI] = ( temp >> 8 ) & 0xff;
- bt848[BKTR_O_HSCALE_HI] = ( temp >> 8 ) & 0xff;
+ bt848->e_hscale_lo = temp & 0xff;
+ bt848->o_hscale_lo = temp & 0xff;
+ bt848->e_hscale_hi = ( temp >> 8 ) & 0xff;
+ bt848->o_hscale_hi = ( temp >> 8 ) & 0xff;
/* horizontal active */
temp = bktr->cols;
- bt848[BKTR_E_HACTIVE_LO] = temp & 0xff;
- bt848[BKTR_O_HACTIVE_LO] = temp & 0xff;
- bt848[BKTR_EVEN_CROP] &= ~0x3;
- bt848[BKTR_ODD_CROP] &= ~0x3;
- bt848[BKTR_EVEN_CROP] |= (temp >> 8 ) & 0x3;
- bt848[BKTR_ODD_CROP] |= (temp >> 8 ) & 0x3;
+ bt848->e_hactive_lo = temp & 0xff;
+ bt848->o_hactive_lo = temp & 0xff;
+ bt848->e_crop &= ~0x3;
+ bt848->o_crop &= ~0x3;
+ bt848->e_crop |= (temp >> 8 ) & 0x3;
+ bt848->o_crop |= (temp >> 8 ) & 0x3;
/* horizontal delay */
temp = ((135.0/754.0) * (float) bktr->cols) ;
temp = temp + 2;
temp = temp & 0x3fe;
- bt848[BKTR_E_DELAY_LO] = temp & 0xff;
- bt848[BKTR_O_DELAY_LO] = temp & 0xff;
- bt848[BKTR_EVEN_CROP] &= ~0xc;
- bt848[BKTR_ODD_CROP] &= ~0xc;
- bt848[BKTR_EVEN_CROP] |= (temp >> 6) & 0xc;
- bt848[BKTR_ODD_CROP] |= (temp >> 6) & 0xc;
+ bt848->e_delay_lo = temp & 0xff;
+ bt848->o_delay_lo = temp & 0xff;
+ bt848->e_crop &= ~0xc;
+ bt848->o_crop &= ~0xc;
+ bt848->e_crop |= (temp >> 6) & 0xc;
+ bt848->o_crop |= (temp >> 6) & 0xc;
/* vscale */
if (geo->oformat & METEOR_GEO_ODD_ONLY ||
@@ -1466,12 +1306,12 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
tmp_int &= 0x1fff;
/* Vertical scaling */
- bt848[BKTR_E_VSCALE_LO] = tmp_int & 0xff;
- bt848[BKTR_O_VSCALE_LO] = tmp_int & 0xff;
- bt848[BKTR_E_VSCALE_HI] &= ~0x1f;
- bt848[BKTR_O_VSCALE_HI] &= ~0x1f;
- bt848[BKTR_E_VSCALE_HI] |= (tmp_int >> 8) & 0x1f;
- bt848[BKTR_O_VSCALE_HI] |= (tmp_int >> 8) & 0x1f;
+ bt848->e_vscale_lo = tmp_int & 0xff;
+ bt848->o_vscale_lo = tmp_int & 0xff;
+ bt848->e_vscale_hi &= ~0x1f;
+ bt848->o_vscale_hi &= ~0x1f;
+ bt848->e_vscale_hi |= (tmp_int >> 8) & 0x1f;
+ bt848->o_vscale_hi |= (tmp_int >> 8) & 0x1f;
bktr->format = METEOR_GEO_YUV_422;
switch (geo->oformat & METEOR_GEO_OUTPUT_MASK) {
@@ -1515,20 +1355,17 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
}
start_capture(bktr, METEOR_CONTIN);
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = *btl_reg;
- bts_reg = (u_short *)&bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0x1;
- *bts_reg = bktr->capcontrol;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 1 << 23 | 2 | 1;
+ bt848->int_stat = bt848->int_stat;
+ bt848->gpio_dma_ctl = 0x1;
+ bt848->gpio_dma_ctl = bktr->capcontrol;
+ bt848->int_mask = 1 << 23 | 2 | 1;
}
}
break;
/* end of METEORSETGEO */
default:
- return ENODEV;
+ return common_ioctl( bktr, bt848, cmd, arg );
}
return 0;
@@ -1536,6 +1373,312 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
/*
+ * tuner ioctls
+ */
+static int
+tuner_ioctl( bktr_reg_t* bktr, int unit,
+ int cmd, caddr_t arg, struct proc* pr )
+{
+ bt848_reg_t bt848;
+ int status;
+ int tmp_int;
+ unsigned int temp, temp1;
+#if defined( EEPROM_SUPPORT )
+ int offset;
+ int count;
+ u_char *buf;
+#endif /* EEPROM_SUPPORT */
+
+ bt848 = bktr->base;
+
+ switch ( cmd ) {
+
+ case TVTUNER_SETCHNL:
+ tmp_int = bktr->audio_mute_state;
+ set_audio( bktr, AUDIO_MUTE ); /* prevent 'click' */
+ temp = tv_channel( bktr, (int)*(unsigned long *)arg );
+ tsleep((caddr_t)bktr, PZERO, "tuning", hz/8 );
+ if ( tmp_int == FALSE )
+ set_audio( bktr, AUDIO_UNMUTE );
+ if ( temp < 0 )
+ return EINVAL;
+ *(unsigned long *)arg = temp;
+ break;
+
+ case TVTUNER_GETCHNL:
+ *(unsigned long *)arg = bktr->tuner.channel;
+ break;
+
+ case TVTUNER_SETTYPE:
+ temp = *(unsigned long *)arg;
+ if ( (temp < CHNLSET_MIN) || (temp > CHNLSET_MAX) )
+ return EINVAL;
+ bktr->tuner.chnlset = temp;
+ break;
+
+ case TVTUNER_GETTYPE:
+ *(unsigned long *)arg = bktr->tuner.chnlset;
+ break;
+
+ case TVTUNER_GETSTATUS:
+ temp = i2cRead( bktr, TSA5522_RADDR );
+ *(unsigned long *)arg = temp & 0xff;
+ break;
+
+ case TVTUNER_SETFREQ:
+#if defined( AUDIO_SUPPORT_XXX )
+ tmp_int = bktr->audio_mute_state;
+ set_audio( bktr, AUDIO_MUTE ); /* prevent 'click' */
+#endif /* AUDIO_SUPPORT */
+ temp = tv_freq( bktr, (int)*(unsigned long *)arg );
+#if defined( AUDIO_SUPPORT_XXX )
+ tsleep((caddr_t)bktr, PZERO, "tuning", hz/8 );
+ if ( tmp_int == FALSE )
+ set_audio( bktr, AUDIO_UNMUTE );
+#endif /* AUDIO_SUPPORT */
+ if ( temp < 0 )
+ return EINVAL;
+ *(unsigned long *)arg = temp;
+ break;
+
+ case TVTUNER_GETFREQ:
+ *(unsigned long *)arg = bktr->tuner.frequency;
+ break;
+
+ case BT848_SAUDIO: /* set audio channel */
+ if ( set_audio( bktr, *(int*)arg ) < 0 )
+ return EIO;
+ break;
+
+ /* hue is a 2's compliment number, -90' to +89.3' in 0.7' steps */
+ case BT848_SHUE: /* set hue */
+ bt848->hue = (u_char)(*(int*)arg & 0xff);
+ break;
+
+ case BT848_GHUE: /* get hue */
+ *(int*)arg = (signed char)(bt848->hue & 0xff);
+ break;
+
+ /* brightness is a 2's compliment #, -50 to +%49.6% in 0.39% steps */
+ case BT848_SBRIG: /* set brightness */
+ bt848->bright = (u_char)(*(int *)arg & 0xff);
+ break;
+
+ case BT848_GBRIG: /* get brightness */
+ *(int *)arg = (signed char)(bt848->bright & 0xff);
+ break;
+
+ /* */
+ case BT848_SCSAT: /* set chroma saturation */
+ tmp_int = *(int*)arg;
+
+ temp = bt848->e_control & 0xfc;
+ temp1 = bt848->o_control & 0xfc;
+ if ( tmp_int & 0x100 ) {
+ temp |= 0x03;
+ temp1 |= 0x03;
+ }
+
+ bt848->sat_u_lo = (u_char)(tmp_int & 0xff);
+ bt848->sat_v_lo = (u_char)(tmp_int & 0xff);
+ bt848->e_control = temp;
+ bt848->o_control = temp1;
+ break;
+
+ case BT848_GCSAT: /* get chroma saturation */
+ tmp_int = (int)(bt848->sat_v_lo & 0xff);
+ if ( bt848->e_control & 0x01 )
+ tmp_int |= 0x0100;
+ *(int*)arg = tmp_int;
+ break;
+
+ /* */
+ case BT848_SVSAT: /* set chroma V saturation */
+ tmp_int = *(int*)arg;
+
+ temp = bt848->e_control & 0xfe;
+ temp1 = bt848->o_control & 0xfe;
+ if ( tmp_int & 0x100 ) {
+ temp |= 0x01;
+ temp1 |= 0x01;
+ }
+
+ bt848->sat_v_lo = (u_char)(tmp_int & 0xff);
+ bt848->e_control = temp;
+ bt848->o_control = temp1;
+ break;
+
+ case BT848_GVSAT: /* get chroma V saturation */
+ tmp_int = (int)bt848->sat_v_lo & 0xff;
+ if ( bt848->e_control & 0x01 )
+ tmp_int |= 0x0100;
+ *(int*)arg = tmp_int;
+ break;
+
+ /* */
+ case BT848_SUSAT: /* set chroma U saturation */
+ tmp_int = *(int*)arg;
+
+ temp = bt848->e_control & 0xfd;
+ temp1 = bt848->o_control & 0xfd;
+ if ( tmp_int & 0x100 ) {
+ temp |= 0x02;
+ temp1 |= 0x02;
+ }
+
+ bt848->sat_u_lo = (u_char)(tmp_int & 0xff);
+ bt848->e_control = temp;
+ bt848->o_control = temp1;
+ break;
+
+ case BT848_GUSAT: /* get chroma U saturation */
+ tmp_int = (int)bt848->sat_u_lo & 0xff;
+ if ( bt848->e_control & 0x02 )
+ tmp_int |= 0x0100;
+ *(int*)arg = tmp_int;
+ break;
+
+ /* */
+ case BT848_SCONT: /* set contrast */
+ tmp_int = *(int*)arg;
+
+ temp = bt848->e_control & 0xfb;
+ temp1 = bt848->o_control & 0xfb;
+ if ( tmp_int & 0x100 ) {
+ temp |= 0x04;
+ temp1 |= 0x04;
+ }
+
+ bt848->contrast_lo = (u_char)(tmp_int & 0xff);
+ bt848->e_control = temp;
+ bt848->o_control = temp1;
+ break;
+
+ case BT848_GCONT: /* get contrast */
+ tmp_int = (int)bt848->contrast_lo & 0xff;
+ if ( bt848->e_control & 0x04 )
+ tmp_int |= 0x0100;
+ *(int*)arg = tmp_int;
+ break;
+
+ case BT848_SCBARS: /* set colorbar output */
+ bt848->color_ctl |= 0x40;
+ break;
+
+ case BT848_CCBARS: /* clear colorbar output */
+ bt848->color_ctl &= ~0x40;
+ break;
+
+ case BT848_GAUDIO: /* get audio channel */
+ temp = bktr->audio_mux_select;
+ if ( bktr->audio_mute_state == TRUE )
+ temp |= AUDIO_MUTE;
+ *(int*)arg = temp;
+ break;
+
+ case BT848_SBTSC: /* set audio channel */
+ if ( set_BTSC( bktr, *(int*)arg ) < 0 )
+ return EIO;
+ break;
+
+#if defined( EEPROM_SUPPORT )
+ case BT848_WEEPROM: /* write eeprom */
+ return EINVAL;
+
+ case BT848_REEPROM: /* read eeprom */
+ offset = (((struct eeProm *)arg)->offset);
+ count = (((struct eeProm *)arg)->count);
+ buf = &(((struct eeProm *)arg)->bytes[ 0 ]);
+ if ( readEEProm( bktr, offset, count, buf ) < 0 )
+ return EIO;
+ break;
+#endif /* EEPROM_SUPPORT */
+
+ default:
+ return common_ioctl( bktr, bt848, cmd, arg );
+ }
+
+ return( 0 );
+}
+
+
+/*
+ * common ioctls
+ */
+int
+common_ioctl( bktr_reg_t* bktr, bt848_reg_t bt848, int cmd, caddr_t arg )
+{
+ int status;
+ unsigned int temp;
+
+ switch (cmd) {
+
+ case METEORSINPUT: /* set input device */
+ switch(*(unsigned long *)arg & METEOR_DEV_MASK) {
+
+ /* this is the RCA video input */
+ case 0: /* default */
+ case METEOR_INPUT_DEV0:
+ bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
+ | METEOR_DEV0;
+ bt848->iform &= ~0x60;
+ bt848->iform |= 0x60;
+ bt848->e_control &= ~0x40;
+ bt848->o_control &= ~0x40;
+ set_audio( bktr, AUDIO_EXTERN );
+ break;
+
+ /* this is the tuner input */
+ case METEOR_INPUT_DEV1:
+ bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
+ | METEOR_DEV1;
+ bt848->iform &= ~0x60;
+ bt848->iform |= 0x40;
+ bt848->e_control &= ~0x40;
+ bt848->o_control &= ~0x40;
+ set_audio( bktr, AUDIO_TUNER );
+ break;
+
+ /* this is the S-VHS input */
+ case METEOR_INPUT_DEV2:
+ case METEOR_INPUT_DEV_SVIDEO:
+ bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
+ | METEOR_DEV2;
+ bt848->iform &= ~0x60;
+ bt848->iform |= 0x20;
+ bt848->e_control |= 0x40;
+ bt848->o_control |= 0x40;
+ set_audio( bktr, AUDIO_EXTERN );
+ break;
+
+ default:
+ return EINVAL;
+ }
+ break;
+
+ case METEORGINPUT: /* get input device */
+ *(u_long *)arg = bktr->flags & METEOR_DEV_MASK;
+ break;
+
+#if defined( STATUS )
+ case BT848_GSTATUS: /* reap status */
+ disable_intr();
+ temp = status_sum;
+ status_sum = 0;
+ enable_intr();
+ *(u_int*)arg = temp;
+ break;
+#endif /* STATUS */
+
+ default:
+ return ENODEV;
+ }
+
+ return( 0 );
+}
+
+
+/*
*
*/
int
@@ -1546,9 +1689,10 @@ bktr_mmap( dev_t dev, int offset, int nprot )
unit = UNIT(minor(dev));
- if (unit >= NBKTR) /* at this point could this happen? */
+ if (unit >= NBKTR || minor(dev) > 0 ) /* at this point could this happen? */
return(-1);
+
bktr = &(brooktree[unit]);
if (nprot & PROT_EXEC)
@@ -1570,10 +1714,9 @@ bktr_mmap( dev_t dev, int offset, int nprot )
*
*/
static int
-dump_bt848( volatile u_char *bt848 )
+dump_bt848( bt848_reg_t bt848 )
{
- u_long *bt_long;
- u_short *bt_short;
+ volatile u_char *bt848r = (u_char *)bt848;
int r[60]={
4, 8, 0xc, 0x8c, 0x10, 0x90, 0x14, 0x94,
0x18, 0x98, 0x1c, 0x9c, 0x20, 0xa0, 0x24, 0xa4,
@@ -1586,20 +1729,15 @@ dump_bt848( volatile u_char *bt848 )
for (i = 0; i < 40; i+=4) {
printf(" Reg:value : \t%x:%x \t%x:%x \t %x:%x \t %x:%x\n",
- r[i], bt848[r[i]],
- r[i+1], bt848[r[i+1]],
- r[i+2], bt848[r[i+2]],
- r[i+3], bt848[r[i+3]]);
+ r[i], bt848r[r[i]],
+ r[i+1], bt848r[r[i+1]],
+ r[i+2], bt848r[r[i+2]],
+ r[i+3], bt848r[r[i+3]]);
}
- bt_long = (u_long *) &bt848[BKTR_INT_STAT];
- printf(" Reg 100 %x \n", *bt_long);
-
- bt_long = (u_long *) &bt848[BKTR_INT_MASK];
- printf(" Reg 104 %x \n", *bt_long);
-
- bt_long = (u_long *) &bt848[BKTR_GPIO_DMA_CTL];
- printf(" Reg 10C %x \n", *bt_long);
+ printf(" INT STAT %x \n", bt848->int_stat);
+ printf(" Reg INT_MASK %x \n", bt848->int_mask);
+ printf(" Reg GPIO_DMA_CTL %x \n", bt848->gpio_dma_ctl);
return 0;
}
@@ -1616,14 +1754,14 @@ dump_bt848( volatile u_char *bt848 )
#define BKTR_EOL 0x1
#define BKTR_SOL 0x2
-#define OP_WRITE 0x1 << 28
-#define OP_WRITEC 0x5 << 28
-#define OP_JUMP 0x7 << 28
-#define OP_SYNC 0x8 << 28
-#define OP_WRITE123 0x9 << 28
-#define OP_WRITES123 0xb << 28
-#define OP_SOL 1 << 27
-#define OP_EOL 1 << 26
+#define OP_WRITE (0x1 << 28)
+#define OP_WRITEC (0x5 << 28)
+#define OP_JUMP (0x7 << 28)
+#define OP_SYNC (0x8 << 28)
+#define OP_WRITE123 (0x9 << 28)
+#define OP_WRITES123 (0xb << 28)
+#define OP_SOL (1 << 27)
+#define OP_EOL (1 << 26)
static void
rgb_prog( bktr_reg_t * bktr, char i_flag, int cols,
@@ -1631,40 +1769,39 @@ rgb_prog( bktr_reg_t * bktr, char i_flag, int cols,
{
int i;
int byte_count;
+ bt848_reg_t bt848;
volatile unsigned int inst;
volatile unsigned int inst2;
volatile unsigned int inst3;
volatile u_long target_buffer, buffer;
- volatile u_char *bt848, *bt_reg;
- volatile u_short *bts_reg;
volatile u_long pitch;
- volatile u_long *dma_prog, *btl_reg, *t_test;
+ volatile u_long *dma_prog, *t_test;
int b, c;
bt848 = bktr->base;
/* color format : rgb32 */
if (bktr->depth == 4)
- bt848[BKTR_COLOR_FMT] = 0;
+ bt848->color_fmt = 0;
else
- bt848[BKTR_COLOR_FMT] = 0x33;
+ bt848->color_fmt = 0x33;
- bt848[BKTR_COLOR_CTL] = 0x40;
- bt848[BKTR_COLOR_CTL] = 0x10;
+ bt848->color_ctl = 0x40;
+ bt848->color_ctl = 0x10;
#if 0
- bt848[0x10] = 0x1C;
- bt848[0x90] = 0x1C;
+ bt848->e_vdelay_low = 0x1C;
+ bt848->o_vdelay_low = 0x1C;
#endif
- bt848[BKTR_VBI_PACK_SIZE] = 0;
- bt848[BKTR_VBI_PACK_DEL] = 0;
+ bt848->vbi_pack_size = 0;
+ bt848->vbi_pack_del = 0;
- bt848[BKTR_ADC] = 0x81;
- bt848[BKTR_COLOR_CTL] = 0x20;
+ bt848->adc = SYNC_LEVEL;
+ bt848->color_ctl = 0x20;
- bt848[BKTR_E_VSCALE_HI] |= 0xc0;
- bt848[BKTR_O_VSCALE_HI] |= 0xc0;
+ bt848->e_vscale_hi |= 0xc0;
+ bt848->o_vscale_hi |= 0xc0;
bktr->capcontrol = 3 << 2 | 3;
@@ -1775,21 +1912,20 @@ yuvpack_prog( bktr_reg_t *bktr, char i_flag,
volatile unsigned int inst2;
volatile unsigned int inst3;
volatile u_long target_buffer, buffer;
- volatile u_char *bt848, *bt_reg;
- volatile u_short *bts_reg;
- volatile u_long *dma_prog, *btl_reg;
+ bt848_reg_t bt848;
+ volatile u_long *dma_prog;
int b;
bt848 = bktr->base;
/* color format : yuvpack */
- bt848[BKTR_COLOR_FMT] = 0x44;
+ bt848->color_fmt = 0x44;
- bt848[BKTR_E_SCLOOP] |= 0x40; /* enable chroma comb */
- bt848[BKTR_O_SCLOOP] |= 0x40;
+ bt848->e_scloop |= 0x40; /* enable chroma comb */
+ bt848->o_scloop |= 0x40;
- bt848[BKTR_COLOR_CTL] = 0x30;
- bt848[BKTR_ADC] = 0x81;
+ bt848->color_ctl = 0x30;
+ bt848->adc = SYNC_LEVEL;
bktr->capcontrol = 1 << 6 | 1 << 4 | 1 << 2 | 3;
bktr->capcontrol = 1 << 5 | 1 << 4 | 1 << 2 | 3;
@@ -1900,9 +2036,8 @@ yuv422_prog( bktr_reg_t * bktr, char i_flag,
volatile unsigned int instskip, instskip2, instskip3;
volatile unsigned int inst3;
volatile u_long target_buffer, t1, buffer;
- volatile u_char *bt848, *bt_reg;
- volatile u_short *bts_reg;
- volatile u_long *dma_prog, *btl_reg;
+ bt848_reg_t bt848;
+ volatile u_long *dma_prog;
int b, b1;
bt848 = bktr->base;
@@ -1910,21 +2045,21 @@ yuv422_prog( bktr_reg_t * bktr, char i_flag,
bktr->capcontrol = 1 << 6 | 1 << 4 | 3;
- bt848[BKTR_ADC] = 0x81 ;
- bt848[BKTR_OFORM] = 0x00;
+ bt848->adc = SYNC_LEVEL;
+ bt848->oform = 0x00;
- bt848[BKTR_E_CONTROL] |= 0x20; /* disable luma decimation */
- bt848[BKTR_O_CONTROL] |= 0x20;
+ bt848->e_control |= 0x20; /* disable luma decimation */
+ bt848->o_control |= 0x20;
- bt848[BKTR_E_SCLOOP] |= 0x40; /* chroma agc enable */
- bt848[BKTR_O_SCLOOP] |= 0x40;
+ bt848->e_scloop |= 0x40; /* chroma agc enable */
+ bt848->o_scloop |= 0x40;
- bt848[BKTR_E_VSCALE_HI] |= 0xc0; /* luma comb and comb enable */
- bt848[BKTR_O_VSCALE_HI] |= 0xc0;
+ bt848->e_vscale_hi |= 0xc0; /* luma comb and comb enable */
+ bt848->o_vscale_hi |= 0xc0;
- bt848[BKTR_COLOR_FMT] = 0x88;
+ bt848->color_fmt = 0x88;
- bt848[BKTR_COLOR_CTL] = 0x10; /* disable gamma correction */
+ bt848->color_ctl = 0x10; /* disable gamma correction */
bt_enable_cnt = 0;
@@ -2019,45 +2154,40 @@ build_dma_prog( bktr_reg_t * bktr, char i_flag )
volatile unsigned int inst2;
volatile unsigned int inst3;
volatile u_long target_buffer;
- volatile u_char *bt848, *bt_reg;
- volatile u_short *bts_reg;
- volatile u_long *dma_prog, *btl_reg;
+ bt848_reg_t bt848;
+ volatile u_long *dma_prog;
int b;
bt848 = bktr->base;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK] ;
- *btl_reg = 0;
-
- bts_reg = (u_short * ) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg &= ~3;
+ bt848->int_mask = 0;
+ bt848->gpio_dma_ctl &= ~3;
/* capture control */
switch (i_flag) {
case 1:
bktr->bktr_cap_ctl = 0x11;
- bt848[BKTR_CAP_CTL] = 0x11;
- bt848[BKTR_E_VSCALE_HI] &= ~0x20;
- bt848[BKTR_O_VSCALE_HI] &= ~0x20;
+ bt848->cap_ctl = 0x11;
+ bt848->e_vscale_hi &= ~0x20;
+ bt848->o_vscale_hi &= ~0x20;
interlace = 1;
break;
case 2:
bktr->bktr_cap_ctl = 0x12;
- bt848[BKTR_CAP_CTL] = 0x12;
- bt848[BKTR_E_VSCALE_HI] &= ~0x20;
- bt848[BKTR_O_VSCALE_HI] &= ~0x20;
+ bt848->cap_ctl = 0x12;
+ bt848->e_vscale_hi &= ~0x20;
+ bt848->o_vscale_hi &= ~0x20;
interlace = 1;
break;
default:
bktr->bktr_cap_ctl = 0x13;
- bt848[BKTR_CAP_CTL] = 0x13;
- bt848[BKTR_E_VSCALE_HI] |= 0x20;
- bt848[BKTR_O_VSCALE_HI] |= 0x20;
+ bt848->cap_ctl = 0x13;
+ bt848->e_vscale_hi |= 0x20;
+ bt848->o_vscale_hi |= 0x20;
interlace = 2;
break;
}
- btl_reg = (u_long *) &bt848[BKTR_RISC_STRT_ADD] ;
- *btl_reg = vtophys(bktr->dma_prog);
+ bt848->risc_strt_add = vtophys(bktr->dma_prog);
pixel_width = bktr->depth;
rows = bktr->rows;
@@ -2094,15 +2224,13 @@ build_dma_prog( bktr_reg_t * bktr, char i_flag )
static void
start_capture( bktr_reg_t *bktr, unsigned type )
{
- volatile u_char *bt848, *bt_reg, i_flag;
- volatile u_short *bts_reg;
- volatile u_long *btl_reg;
+ bt848_reg_t bt848;
+ u_char i_flag;
- bt848 = (u_char *) bktr->base;
+ bt848 = bktr->base;
- *bt848 = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = *btl_reg;
+ bt848->dstatus = 0;
+ bt848->int_stat = bt848->int_stat;
bktr->flags |= type;
switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
@@ -2128,16 +2256,14 @@ start_capture( bktr_reg_t *bktr, unsigned type )
/*XXX
switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
default:
- *bts_reg |= 0xb;
+ *bts_reg |= 0xb; bts_reg never been initialized!
}
*/
- btl_reg = (u_long *) &bt848[BKTR_RISC_STRT_ADD];
- *btl_reg = vtophys(bktr->dma_prog);
+ bt848->risc_strt_add = vtophys(bktr->dma_prog);
/*XXX
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0x3;
+ bt848->gpio_dma_ctl = 0x3;
*/
}
@@ -2148,39 +2274,31 @@ start_capture( bktr_reg_t *bktr, unsigned type )
static void
set_fps( bktr_reg_t *bktr, u_short fps )
{
- volatile u_char *bt848, *bt_reg;
- volatile u_long *btl_reg;
- volatile u_short *bts_reg;
+ bt848_reg_t bt848;
- bt848 = (u_char *) bktr->base;
+ bt848 = bktr->base;
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = 0xffffffff;
+ bt848->gpio_dma_ctl = 0;
+ bt848->int_stat = 0xffffffff;
bktr->fps = fps;
if ( fps == 30 ) {
- bt848[BKTR_TDEC] = 0;
+ bt848->tdec = 0;
return;
} else {
- bt848[BKTR_TDEC] = (int) (((float) fps / 30.0) * 60.0) & 0x3f;
- bt848[BKTR_TDEC] |= 0x80;
+ bt848->tdec = (int) (((float) fps / 30.0) * 60.0) & 0x3f;
+ bt848->tdec |= 0x80;
}
if ( bktr->flags & METEOR_CAP_MASK ) {
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = 0xffffffff;
- btl_reg = (u_long *) &bt848[BKTR_RISC_STRT_ADD];
- *btl_reg = vtophys(bktr->dma_prog);
+ bt848->int_stat = 0xffffffff;
+ bt848->risc_strt_add = vtophys(bktr->dma_prog);
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 1;
- *bts_reg = bktr->capcontrol;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 1 << 11 | 2 | 1;
+ bt848->gpio_dma_ctl = 1;
+ bt848->gpio_dma_ctl = bktr->capcontrol;
+ bt848->int_mask = 1 << 11 | 2 | 1;
}
return;
@@ -2221,198 +2339,192 @@ get_bktr_mem( int unit, unsigned size )
* i2c primitives:
*/
-/* delays for the I2C bus transactions */
-#define NDELAY 0
-#if defined ( ORIGINAL_DELAYS )
-#define SDELAY 2
-#define LDELAY 20
-#else
-#define SDELAY 10
-#define LDELAY 40
-#endif /* ORIGINAL_DELAYS */
-/* macros to show the details more clearly */
typedef volatile u_long* i2c_regptr_t;
+#define I2C_REGADDR() ((i2c_regptr_t)&bktr->base->i2c_data_ctl)
+
+#define RACK (1 << 25)
+#define I2CDONE (1 << 8)
+#define I2CDIV (0x0f << 4)
+#define I2CBITTIME (0x05 << 4)
+#define I2CSYNC (0x01 << 3)
+#define I2CW3B (0x01 << 2)
+#define I2CSCL (0x01 << 1)
+#define I2CSDA (0x01 << 0)
+#define I2C_READ 0x01
+#define I2C_COMMAND (I2CBITTIME | I2CSCL | I2CSDA)
/*
- * primitives for the I2C clock phases
+ *
*/
-static inline void
-DataLo_ClockLo( i2c_regptr_t bti2c, int delay )
-{
- *bti2c = 0;
- if ( delay )
- DELAY( delay );
-}
-static inline void
-DataHi_ClockLo( i2c_regptr_t bti2c, int delay )
+static int
+i2cWrite( bktr_reg_t *bktr, int addr, int byte1, int byte2 )
{
- *bti2c = 1;
- if ( delay )
- DELAY( delay );
-}
+ u_long x;
+ u_long data;
+ i2c_regptr_t bti2c;
-static inline void
-DataLo_ClockHi( i2c_regptr_t bti2c, int delay )
-{
- *bti2c = 2;
- if ( delay )
- DELAY( delay );
-}
+ /* setup register addresses */
+ bti2c = I2C_REGADDR();
-static inline void
-DataHi_ClockHi( i2c_regptr_t bti2c, int delay )
-{
- *bti2c = 3;
- if ( delay )
- DELAY( delay );
-}
+ /* clear status bits */
+ bktr->base->int_stat = (RACK | I2CDONE);
-static inline int
-DataRead( i2c_regptr_t bti2c )
-{
- return ( *bti2c & 1 );
-}
+ /* build the command datum */
+ data = ((addr & 0xff) << 24) | ((byte1 & 0xff) << 16) | I2C_COMMAND;
+ if ( byte2 != -1 ) {
+ data |= ((byte2 & 0xff) << 8);
+ data |= I2CW3B;
+ }
+
+ /* write the address and data */
+ *bti2c = data;
+
+ /* wait for completion */
+ for ( x = 0xffffffff; x; --x ) { /* safety valve */
+ if ( bktr->base->int_stat & I2CDONE )
+ break;
+ }
+
+ /* check for ACK */
+ if ( !x || !(bktr->base->int_stat & RACK) )
+ return -1;
+ /* return OK */
+ return 0;
+}
-/* forward reference */
-static int i2cWrite( i2c_regptr_t, u_char );
/*
- * start an I2C bus transaction
+ *
*/
static int
-i2cStart( i2c_regptr_t bti2c, int address )
+i2cRead( bktr_reg_t *bktr, int addr )
{
-#if defined( EXTRA_START )
- /* ensure the proper starting state */
- DataHi_ClockLo( bti2c, LDELAY ); /* release data */
- DataHi_ClockHi( bti2c, LDELAY ); /* release clock */
-#endif /* EXTRA_START */
+ u_long x;
+ i2c_regptr_t bti2c;
- DataLo_ClockHi( bti2c, LDELAY ); /* lower data */
- DataLo_ClockLo( bti2c, LDELAY ); /* lower clock */
+ /* setup register addresses */
+ bti2c = I2C_REGADDR();
- /* send the address of the device */
- return i2cWrite( bti2c, address );
-}
+ /* clear status bits */
+ bktr->base->int_stat = (RACK | I2CDONE);
-/*
- * stop an I2C bus transaction
- */
-static void
-i2cStop( i2c_regptr_t bti2c )
-{
- DELAY( LDELAY );
- DataLo_ClockLo( bti2c, LDELAY ); /* lower clock & data */
- DataLo_ClockHi( bti2c, LDELAY ); /* release clock */
- DataHi_ClockHi( bti2c, LDELAY ); /* release data */
-}
+ /* write the READ address */
+ *bti2c = ((addr & 0xff) << 24) | I2C_COMMAND;
-/*
- * place a '1' bit on the I2C bus
- */
-static void
-i2cHi( i2c_regptr_t bti2c )
-{
- DataHi_ClockLo( bti2c, LDELAY ); /* assert HI data */
- DataHi_ClockHi( bti2c, LDELAY ); /* strobe clock */
- DataHi_ClockLo( bti2c, LDELAY ); /* release clock */
-}
+ /* wait for completion */
+ for ( x = 0xffffffff; x; --x ) { /* safety valve */
+ if ( bktr->base->int_stat & I2CDONE )
+ break;
+ }
-/*
- * place a '0' bit on the I2C bus
- */
-static void
-i2cLo( i2c_regptr_t bti2c )
-{
- DataLo_ClockLo( bti2c, LDELAY ); /* assert LO data */
- DataLo_ClockHi( bti2c, LDELAY ); /* strobe clock */
- DataLo_ClockLo( bti2c, LDELAY ); /* release clock */
+ /* check for ACK */
+ if ( !(bktr->base->int_stat & RACK) )
+ return -1;
+
+ /* it was a read */
+ return (*bti2c >> 8) & 0xff;
}
+
+#if defined( I2C_SOFTWARE_PROBE )
+
/*
- * give an 'ACK' to the slave
+ * we are keeping this around for any parts that we need to probe
+ * but that CANNOT be probed via an i2c read.
+ * this is necessary because the hardware i2c mechanism
+ * cannot be programmed for 1 byte writes.
+ * currently there are no known i2c parts that we need to probe
+ * and that cannot be safely read.
*/
-static void
-i2cGrantAck( i2c_regptr_t bti2c )
-{
- DataLo_ClockLo( bti2c, LDELAY ); /* assert LO data */
- DataLo_ClockHi( bti2c, LDELAY ); /* strobe clock */
- DataLo_ClockLo( bti2c, LDELAY ); /* remove clock */
- DataHi_ClockLo( bti2c, NDELAY ); /* float data */
-}
+static int i2cProbe( i2c_regptr_t bti2c, int addr );
+#define BITDELAY 40
+#define EXTRA_START
/*
- * get an 'ACK' from the slave
+ * probe for an I2C device at addr.
*/
static int
-i2cAck( i2c_regptr_t bti2c )
+i2cProbe( i2c_regptr_t bti2c, int addr )
{
- int acknowledge;
+ int x, status;
- DataHi_ClockLo( bti2c, LDELAY ); /* float data */
- DataHi_ClockHi( bti2c, LDELAY ); /* strobe clock */
+ /* the START */
+#if defined( EXTRA_START )
+ *bti2c = 1; DELAY( BITDELAY ); /* release data */
+ *bti2c = 3; DELAY( BITDELAY ); /* release clock */
+#endif /* EXTRA_START */
+ *bti2c = 2; DELAY( BITDELAY ); /* lower data */
+ *bti2c = 0; DELAY( BITDELAY ); /* lower clock */
+
+ /* write addr */
+ for ( x = 7; x >= 0; --x ) {
+ if ( addr & (1<<x) ) {
+ *bti2c = 1; DELAY( BITDELAY ); /* assert HI data */
+ *bti2c = 3; DELAY( BITDELAY ); /* strobe clock */
+ *bti2c = 1; DELAY( BITDELAY ); /* release clock */
+ }
+ else {
+ *bti2c = 0; DELAY( BITDELAY ); /* assert LO data */
+ *bti2c = 2; DELAY( BITDELAY ); /* strobe clock */
+ *bti2c = 0; DELAY( BITDELAY ); /* release clock */
+ }
+ }
- acknowledge = DataRead( bti2c ); /* read ACK bit */
+ /* look for an ACK */
+ *bti2c = 1; DELAY( BITDELAY ); /* float data */
+ *bti2c = 3; DELAY( BITDELAY ); /* strobe clock */
+ status = *bti2c & 1; /* read the ACK bit */
+ *bti2c = 1; DELAY( BITDELAY ); /* release clock */
- DataHi_ClockLo( bti2c, LDELAY ); /* release clock */
+ /* the STOP */
+ *bti2c = 0; DELAY( BITDELAY ); /* lower clock & data */
+ *bti2c = 2; DELAY( BITDELAY ); /* release clock */
+ *bti2c = 3; DELAY( BITDELAY ); /* release data */
- return acknowledge;
+ return status;
}
+#undef EXTRA_START
+#undef BITDELAY
-/*
- * read a byte from the I2C bus
- */
-static int
-i2cRead( i2c_regptr_t bti2c, int ack )
-{
- int x;
- int byte;
-
- DataHi_ClockLo( bti2c, SDELAY ); /* float data */
-
- for ( byte = 0, x = 7; x >= 0; --x ) {
- DataHi_ClockHi( bti2c, SDELAY ); /* strobe clock */
-
- if ( DataRead( bti2c ) ) /* read data */
- byte |= (1<<x); /* bit was Hi */
+#endif /* I2C_SOFTWARE_PROBE */
- DataHi_ClockLo( bti2c, SDELAY ); /* release clock */
- }
-#if defined( FUNNY_HI )
- i2cHi( bti2c );
-#endif /* FUNNY_HI */
-#if defined( REALLY_ACK )
- if ( ack )
- i2cGrantAck( bti2c ); /* Grant ACK */
-#endif /* REALLY_ACK */
- return byte;
-}
+#if defined( EEPROM_SUPPORT )
-/*
- * write a byte to the I2C bus
- */
static int
-i2cWrite( i2c_regptr_t bti2c, u_char byte )
+readEEProm( bktr_reg_t* bktr, int offset, int count, u_char *data )
{
- int x;
+ int x;
+ int addr;
+ int max;
+ int byte;
- DataLo_ClockLo( bti2c, LDELAY ); /* lower data & clock */
+ /* get the address of the EEProm */
+ addr = (int)(bktr->card->eepromAddr & 0xff);
+ if ( addr == 0 )
+ return -1;
- for ( x = 7; x >= 0; --x )
- (byte & (1<<x)) ? i2cHi( bti2c ) : i2cLo( bti2c );
+ max = (int)(bktr->card->eepromSize * EEPROMBLOCKSIZE);
+ if ( (offset + count) > max )
+ return -1;
- return i2cAck( bti2c );
-}
+ /* set the start address */
+ if ( i2cWrite( bktr, addr, offset, -1 ) == -1 )
+ return -1;
-#undef NDELAY
-#undef SDELAY
-#undef LDELAY
+ /* the read cycle */
+ for ( x = 0; x < count; ++x ) {
+ if ( (byte = i2cRead( bktr, (addr | 1) )) == -1 )
+ return -1;
+ data[ x ] = byte;
+ }
+ return 0;
+}
-#define I2C_REGADDR() (i2c_regptr_t)&bktr->base[ BKTR_I2C_CONTROL ]
+#endif /* EEPROM_SUPPORT */
/******************************************************************************
@@ -2420,26 +2532,9 @@ i2cWrite( i2c_regptr_t bti2c, u_char byte )
*/
-/* guaranteed address for any TSA5522 (PLL on all(?) tuners) */
-#define TSA5522_WADDR 0xc2
-#define TSA5522_RADDR 0xc3
-
-/* address of BTSC/SAP decoder chip */
-#define TDA9850_WADDR 0xb6
-#define TDA9850_RADDR 0xb7
-
-/* EEProm (128 * 8) on an STB card */
-#define X24C01_WADDR 0xae
-#define X24C01_RADDR 0xaf
-
-/* EEProm (256 * 8) on a Hauppauge card */
-#define PFC8582_WADDR 0xa0
-#define PFC8582_RADDR 0xa1
-
/*
* the data for each type of card
*/
-
#define NO_TUNER 0
#define TEMIC_TUNER 1
#define PHILIPS_TUNER 2
@@ -2455,33 +2550,44 @@ struct CARDTYPE card_types[] = {
{ "Unknown",
NO_TUNER,
0,
+ 0,
+ 0,
{ 0, 0, 0, 0 } },
/* CARD_MIRO */
{ "Miro TV",
NO_TUNER, /** TEMIC_TUNER ??? */
0,
+ 0,
+ 0,
{ 0x02, 0x01, 0x00, 0x00 } }, /* XXX ??? */
/* CARD_HAUPPAUGE */
{ "Hauppauge WinCast/TV",
PHILIPS_TUNER,
0,
+ PFC8582_WADDR,
+ (u_char)(256 / EEPROMBLOCKSIZE), /* 256 bytes */
{ 0x00, 0x02, 0x01, 0x01 } },
/* CARD_STB */
{ "STB TV/PCI",
TEMIC_TUNER,
0,
+ X24C01_WADDR,
+ (u_char)(128 / EEPROMBLOCKSIZE), /* 128 bytes */
{ 0x00, 0x01, 0x02, 0x02 } },
/* CARD_INTEL */
{ "Intel Smart Video III",
NO_TUNER,
0,
+ 0,
+ 0,
{ 0, 0, 0, 0 } }
};
+
/*
* If probe_card() fails to detect the proper card on boot you can
* override it by setting the following define to the card you are using:
@@ -2490,95 +2596,76 @@ struct CARDTYPE card_types[] = {
*
* where <card type> is one of the card defines in the above array.
*/
-#define PRESENT 0
-#define ABSENT 1
+#define ABSENT (-1)
static int
probe_card( bktr_reg_t *bktr, int verbose )
{
- i2c_regptr_t bti2c;
- int status;
+ int status;
#if defined( OVERRIDE_CARD )
bktr->card_type = OVERRIDE_CARD;
+ bktr->card = &(card_types[ bktr->card_type ]);
goto end;
#endif
- /* get the i2c register address */
- bti2c = I2C_REGADDR();
/* look for a tuner */
- status = i2cStart( bti2c, TSA5522_WADDR );
- i2cStop( bti2c );
- if ( status == ABSENT ) {
+ if ( i2cRead( bktr, TSA5522_RADDR ) == ABSENT ) {
bktr->card_type = CARD_INTEL;
+ bktr->card = &(card_types[ bktr->card_type ]);
goto checkDBX;
}
/* look for a hauppauge card */
- status = i2cStart( bti2c, PFC8582_WADDR );
- i2cStop( bti2c );
- if ( status == PRESENT ) {
+ if ( (status = i2cRead( bktr, PFC8582_RADDR )) != ABSENT ) {
bktr->card_type = CARD_HAUPPAUGE;
+ bktr->card = &(card_types[ bktr->card_type ]);
goto checkTuner;
}
/* look for an STB card */
- status = i2cStart( bti2c, X24C01_WADDR );
- i2cStop( bti2c );
- if ( status == PRESENT ) {
+ if ( (status = i2cRead( bktr, X24C01_RADDR )) != ABSENT ) {
bktr->card_type = CARD_STB;
+ bktr->card = &(card_types[ bktr->card_type ]);
goto checkTuner;
}
/* XXX FIXME: (how do I) look for a Miro card */
bktr->card_type = CARD_MIRO;
+ bktr->card = &(card_types[ bktr->card_type ]);
checkTuner:
- /**
- * XXX FIXME: how can we differentiate TEMIC vs. PHILIPS tuners ???
- */
- status = i2cStart( bti2c, 0xc0 );
- i2cStop( bti2c );
- if ( status == PRESENT ) {
- card_types[ bktr->card_type ].tuner = TEMIC_TUNER;
+ /* differentiate TEMIC vs. PHILIPS tuners */
+ if ( i2cRead( bktr, TEMIC_TSA5522_RADDR ) != ABSENT ) {
+ bktr->card->tuner = TEMIC_TUNER;
goto checkDBX;
}
- status = i2cStart( bti2c, 0xc6 );
- i2cStop( bti2c );
- if ( status == PRESENT ) {
- card_types[ bktr->card_type ].tuner = PHILIPS_TUNER;
+ if ( i2cRead( bktr, PHILIPS_TSA5523_RADDR ) != ABSENT ) {
+ bktr->card->tuner = PHILIPS_TUNER;
goto checkDBX;
}
- card_types[ bktr->card_type ].tuner = NO_TUNER;
+ /* no tuner found */
+ bktr->card->tuner = NO_TUNER;
checkDBX:
- /*
- * probe for BTSC (dbx) chips.
- */
- status = i2cStart( bti2c, TDA9850_WADDR );
- i2cStop( bti2c );
- if ( status == PRESENT )
- card_types[ bktr->card_type ].dbx = 1;
+ /* probe for BTSC (dbx) chips */
+ if ( i2cRead( bktr, TDA9850_RADDR ) != ABSENT )
+ bktr->card->dbx = 1;
end:
if ( verbose ) {
- printf( "%s", card_types[ bktr->card_type ].name );
-
- if ( card_types[ bktr->card_type ].tuner )
- printf( ", %s tuner",
- card_types[ bktr->card_type ].tuner
- == TEMIC_TUNER ? "Temic" : "Philips" );
-
- if ( card_types[ bktr->card_type ].dbx )
+ printf( "%s", bktr->card->name );
+ if ( bktr->card->tuner )
+ printf( ", %s tuner", bktr->card->tuner ==
+ TEMIC_TUNER ? "Temic" : "Philips" );
+ if ( bktr->card->dbx )
printf( ", dbx stereo" );
-
printf( "\n" );
}
return bktr->card_type;
}
#undef ABSENT
-#undef PRESENT
#define TSA5522_BANDA band_addrs[card_types[bktr->card_type].tuner-1][0]
@@ -2773,28 +2860,16 @@ tv_freq( bktr_reg_t* bktr, int frequency )
*/
N = frequency + TBL_IF;
- /* get the i2c register address */
- bti2c = I2C_REGADDR();
-
- /* send the data to the TSA5522 */
- i2cStart( bti2c, TSA5522_WADDR );
-
- /* the data sheet wants the order set according to direction */
if ( frequency > bktr->tuner.frequency ) {
- i2cWrite( bti2c, (N >> 8) & 0x7f ); /* divisor MSB */
- i2cWrite( bti2c, N & 0xff ); /* divisor LSB */
- i2cWrite( bti2c, TSA5522_CONTROL ); /* control bits */
- i2cWrite( bti2c, band ); /* band select */
+ i2cWrite( bktr, TSA5522_WADDR, (N>>8) & 0x7f, N & 0xff );
+ i2cWrite( bktr, TSA5522_WADDR, TSA5522_CONTROL, band );
}
else {
- i2cWrite( bti2c, TSA5522_CONTROL ); /* control bits */
- i2cWrite( bti2c, band ); /* band select */
- i2cWrite( bti2c, (N >> 8) & 0x7f ); /* divisor MSB */
- i2cWrite( bti2c, N & 0xff ); /* divisor LSB */
+ i2cWrite( bktr, TSA5522_WADDR, TSA5522_CONTROL, band );
+ i2cWrite( bktr, TSA5522_WADDR, (N>>8) & 0x7f, N & 0xff );
}
- i2cStop( bti2c );
-
+ /* update frequency */
bktr->tuner.frequency = frequency;
return 0;
@@ -2825,30 +2900,6 @@ tv_channel( bktr_reg_t* bktr, int channel )
}
-/*
- * get the status of the tuner
- */
-static int
-tuner_status( bktr_reg_t* bktr )
-{
- i2c_regptr_t bti2c;
- int status;
-
- /* get the i2c register address */
- bti2c = I2C_REGADDR();
-
- /* send the request to the TSA5522 */
- i2cStart( bti2c, TSA5522_RADDR );
-
- status = i2cRead( bti2c, 0 ); /* no ACK */
-
- i2cStop( bti2c );
-
- return status;
-}
-
-
-#if defined( AUDIO_SUPPORT )
/******************************************************************************
* audio specific routines:
*/
@@ -2861,8 +2912,8 @@ tuner_status( bktr_reg_t* bktr )
static int
set_audio( bktr_reg_t *bktr, int cmd )
{
- volatile u_char *bt848;
- volatile u_char temp;
+ bt848_reg_t bt848;
+ u_long temp;
volatile u_char idx;
#if defined( AUDIOMUX_DISCOVER )
@@ -2899,28 +2950,25 @@ set_audio( bktr_reg_t *bktr, int cmd )
* something like the dbx or teletext chips. This doesn't guarantee
* success, but follows the rule of least astonishment.
*/
- bt848[BKTR_GPIO_OUT_EN] = 0x07; /* drive low 3 bits */
- bt848[BKTR_GPIO_REG_INP] = 0xf8; /* read state of others */
-#if defined( AUDIOMUX_DISCOVER )
- printf("cmd: %d\n", cmd );
-
- temp = bt848[BKTR_GPIO_DATA] & ~7;
- bt848[BKTR_GPIO_DATA] = temp | (cmd & 0xff);
-
- return 0;
-#endif /* AUDIOMUX_DISCOVER */
+ /* this was an 8 bit reference before ?? */
+ bt848->gpio_reg_inp = (~GPIO_AUDIOMUX_BITS & 0xff);
if ( bktr->audio_mute_state == TRUE )
idx = 3;
else
idx = bktr->audio_mux_select;
- temp = bt848[BKTR_GPIO_DATA] & ~7; /* mask off lower three bits */
- bt848[BKTR_GPIO_DATA] =
- temp | card_types[bktr->card_type].audiomuxs[idx];
+ temp = bt848->gpio_data & ~GPIO_AUDIOMUX_BITS;
+ bt848->gpio_data =
+#if defined( AUDIOMUX_DISCOVER )
+ bt848->gpio_data = temp | (cmd & 0xff);
+ printf("cmd: %d\n", cmd );
+#else
+ temp | bktr->card->audiomuxs[ idx ];
+#endif /* AUDIOMUX_DISCOVER */
- return 0;
+ return( 0 );
}
@@ -2935,29 +2983,8 @@ set_audio( bktr_reg_t *bktr, int cmd )
static int
set_BTSC( bktr_reg_t *bktr, int control )
{
- i2c_regptr_t bti2c;
-
- /* get the i2c register address */
- bti2c = I2C_REGADDR();
-
- /* send the data to the TDA9850 BTSC */
- if ( i2cStart( bti2c, TDA9850_WADDR ) )
- goto fubar;
-
- if ( i2cWrite( bti2c, CON3ADDR ) )
- goto fubar;
-
- if ( i2cWrite( bti2c, control ) )
- goto fubar;
-
- i2cStop( bti2c );
- return 0;
-
- fubar:
- i2cStop( bti2c );
- return -1;
+ return i2cWrite( bktr, TDA9850_WADDR, CON3ADDR, control );
}
-#endif /* AUDIO_SUPPORT */
/******************************************************************************
@@ -2982,3 +3009,14 @@ bktr_drvinit( void *unused )
SYSINIT(bktrdev,SI_SUB_DRIVERS,SI_ORDER_MIDDLE+CDEV_MAJOR,bktr_drvinit,NULL)
#endif /* NBKTR > 0 */
+
+/* Local Variables: */
+/* mode: C */
+/* c-indent-level: 8 */
+/* c-brace-offset: -8 */
+/* c-argdecl-indent: 8 */
+/* c-label-offset: -8 */
+/* c-continued-statement-offset: 8 */
+/* c-tab-always-indent: nil */
+/* End: */
+
diff --git a/sys/dev/bktr/bktr_reg.h b/sys/dev/bktr/bktr_reg.h
index 85c6016..cd1240a 100644
--- a/sys/dev/bktr/bktr_reg.h
+++ b/sys/dev/bktr/bktr_reg.h
@@ -37,17 +37,119 @@
*/
#define BROOKTREE_848_ID 0x0350109E
-typedef volatile u_int breg_t;
+typedef volatile u_int bregister_t;
+/*
+ * if other persuasion endian, then compiler will probably require that
+ * these next
+ * macros be reversed
+ */
+#define BTBYTE(what) bregister_t what:8; int :24
+#define BTWORD(what) bregister_t what:16; int: 16
+#define BTLONG(what) bregister_t what:32
+
+struct bt848_registers {
+ BTBYTE (dstatus); /* 0, 1,2,3 */
+#define BT848_DSTATUS_PRES (1<<7)
+#define BT848_DSTATUS_HLOC (1<<6)
+#define BT848_DSTATUS_FIELD (1<<5)
+#define BT848_DSTATUS_NUML (1<<4)
+#define BT848_DSTATUS_CSEL (1<<3)
+#define BT848_DSTATUS_LOF (1<<1)
+#define BT848_DSTATUS_COF (1<<0)
+ BTBYTE (iform); /* 4, 5,6,7 */
+ BTBYTE (tdec); /* 8, 9,a,b */
+ BTBYTE (e_crop); /* c, d,e,f */
+ BTBYTE (e_vdelay_lo); /* 10, 11,12,13 */
+ BTBYTE (e_vactive_lo); /* 14, 15,16,17 */
+ BTBYTE (e_delay_lo); /* 18, 19,1a,1b */
+ BTBYTE (e_hactive_lo); /* 1c, 1d,1e,1f */
+ BTBYTE (e_hscale_hi); /* 20, 21,22,23 */
+ BTBYTE (e_hscale_lo); /* 24, 25,26,27 */
+ BTBYTE (bright); /* 28, 29,2a,2b */
+ BTBYTE (e_control); /* 2c, 2d,2e,2f */
+ BTBYTE (contrast_lo); /* 30, 31,32,33 */
+ BTBYTE (sat_u_lo); /* 34, 35,36,37 */
+ BTBYTE (sat_v_lo); /* 38, 39,3a,3b */
+ BTBYTE (hue); /* 3c, 3d,3e,3f */
+ BTBYTE (e_scloop); /* 40, 41,42,43 */
+ int :32; /* 44, 45,46,47 */
+ BTBYTE (oform); /* 48, 49,4a,4b */
+ BTBYTE (e_vscale_hi); /* 4c, 4d,4e,4f */
+ BTBYTE (e_vscale_lo); /* 50, 51,52,53 */
+ BTBYTE (test); /* 54, 55,56,57 */
+ int :32; /* 58, 59,5a,5b */
+ int :32; /* 5c, 5d,5e,5f */
+ BTLONG (adelay); /* 60, 61,62,63 */
+ BTBYTE (bdelay); /* 64, 65,66,67 */
+ BTBYTE (adc); /* 68, 69,6a,6b */
+ BTBYTE (e_vtc); /* 6c, 6d,6e,6f */
+ int :32; /* 70, 71,72,73 */
+ int :32; /* 74, 75,76,77 */
+ int :32; /* 78, 79,7a,7b */
+ BTLONG (sreset); /* 7c, 7d,7e,7f */
+ u_char filler[0x8c-0x80];
+ BTBYTE (o_crop); /* 8c, 8d,8e,8f */
+ BTBYTE (o_vdelay_lo); /* 90, 91,92,93 */
+ BTBYTE (o_vactive_lo); /* 94, 95,96,97 */
+ BTBYTE (o_delay_lo); /* 98, 99,9a,9b */
+ BTBYTE (o_hactive_lo); /* 9c, 9d,9e,9f */
+ BTBYTE (o_hscale_hi); /* a0, a1,a2,a3 */
+ BTBYTE (o_hscale_lo); /* a4, a5,a6,a7 */
+ int :32; /* a8, a9,aa,ab */
+ BTBYTE (o_control); /* ac, ad,ae,af */
+ u_char fillter1[16];
+ BTBYTE (o_scloop); /* c0, c1,c2,c3 */
+ int :32; /* c4, c5,c6,c7 */
+ int :32; /* c8, c9,ca,cb */
+ BTBYTE (o_vscale_hi); /* cc, cd,ce,cf */
+ BTBYTE (o_vscale_lo); /* d0, d1,d2,d3 */
+ BTBYTE (color_fmt); /* d4, d5,d6,d7 */
+ BTBYTE (color_ctl); /* d8, d9,da,db */
+ BTBYTE (cap_ctl); /* dc, dd,de,df */
+ BTBYTE (vbi_pack_size); /* e0, e1,e2,e3 */
+ BTBYTE (vbi_pack_del); /* e4, e5,e6,e7 */
+ int :32; /* e8, e9,ea,eb */
+ BTBYTE (o_vtc); /* ec, ed,ee,ef */
+ u_char filler2[0x100-0xf0];
+ BTLONG (int_stat); /* 100, 101,102,103 */
+ BTLONG (int_mask); /* 104, 105,106,107 */
+#define BT848_INT_RISCS (0xf<<28)
+#define BT848_INT_RISC_EN (1<<27)
+#define BT848_INT_RACK (1<<25)
+#define BT848_INT_FIELD (1<<24)
+#define BT848_INT_SCERR (1<<19)
+#define BT848_INT_OCERR (1<<18)
+#define BT848_INT_PABORT (1<<17)
+#define BT848_INT_RIPERR (1<<16)
+#define BT848_INT_PPERR (1<<15)
+#define BT848_INT_FDSR (1<<14)
+#define BT848_INT_FTRGT (1<<13)
+#define BT848_INT_FBUS (1<<12)
+#define BT848_INT_RISCI (1<<11)
+#define BT848_INT_GPINT (1<<9)
+#define BT848_INT_I2CDONE (1<<8)
+#define BT848_INT_VPRES (1<<5)
+#define BT848_INT_HLOCK (1<<4)
+#define BT848_INT_OFLOW (1<<3)
+#define BT848_INT_HSYNC (1<<2)
+#define BT848_INT_VSYNC (1<<1)
+#define BT848_INT_FMTCHG (1<<0)
+ int :32; /* 108, 109,10a,10b */
+ BTWORD (gpio_dma_ctl); /* 10c, 10d,10e,10f */
+ BTLONG (i2c_data_ctl); /* 110, 111,112,113 */
+ BTLONG (risc_strt_add); /* 114, 115,116,117 */
+ BTLONG (gpio_out_en); /* 118, 119,11a,11b */ /* really 24 bits */
+ BTLONG (gpio_reg_inp); /* 11c, 11d,11e,11f */ /* really 24 bits */
+ BTLONG (risc_count); /* 120, 121,122,123 */
+ u_char filler3[0x200-0x124];
+ BTLONG (gpio_data); /* 200, 201,202,203 */ /* really 24 bits */
+};
+
+typedef volatile struct bt848_registers *bt848_reg_t;
+typedef volatile struct bt848_registers *bt848_regptr_t;
#define BKTR_DSTATUS 0x000
-# define BT848_DSTATUS_PRES (1<<7)
-# define BT848_DSTATUS_HLOC (1<<6)
-# define BT848_DSTATUS_FIELD (1<<5)
-# define BT848_DSTATUS_NUML (1<<4)
-# define BT848_DSTATUS_CSEL (1<<3)
-# define BT848_DSTATUS_LOF (1<<1)
-# define BT848_DSTATUS_COF (1<<0)
#define BKTR_IFORM 0x004
#define BKTR_TDEC 0x008
#define BKTR_EVEN_CROP 0x00C
@@ -92,27 +194,6 @@ typedef volatile u_int breg_t;
#define BKTR_VBI_PACK_DEL 0x0E4
#define BKTR_INT_STAT 0x100
#define BKTR_INT_MASK 0x104
-# define BT848_INT_RISCS (0xf<<28)
-# define BT848_INT_RISC_EN (1<<27)
-# define BT848_INT_RACK (1<<25)
-# define BT848_INT_FIELD (1<<24)
-# define BT848_INT_SCERR (1<<19)
-# define BT848_INT_OCERR (1<<18)
-# define BT848_INT_PABORT (1<<17)
-# define BT848_INT_RIPERR (1<<16)
-# define BT848_INT_PPERR (1<<15)
-# define BT848_INT_FDSR (1<<14)
-# define BT848_INT_FTRGT (1<<13)
-# define BT848_INT_FBUS (1<<12)
-# define BT848_INT_RISCI (1<<11)
-# define BT848_INT_GPINT (1<<9)
-# define BT848_INT_I2CDONE (1<<8)
-# define BT848_INT_VPRES (1<<5)
-# define BT848_INT_HLOCK (1<<4)
-# define BT848_INT_OFLOW (1<<3)
-# define BT848_INT_HSYNC (1<<2)
-# define BT848_INT_VSYNC (1<<1)
-# define BT848_INT_FMTCHG (1<<0)
#define BKTR_RISC_COUNT 0x120
#define BKTR_RISC_STRT_ADD 0x114
#define BKTR_GPIO_DMA_CTL 0x10C
@@ -125,20 +206,29 @@ typedef volatile u_int breg_t;
/*
* device support for onboard tv tuners
*/
-struct tvtuner {
+struct TVTUNER {
int frequency;
u_char chnlset;
u_char channel;
u_char band;
};
+#define EEPROMBLOCKSIZE 32
+struct CARDTYPE {
+ char* name;
+ u_char tuner;
+ u_char dbx;
+ u_char eepromAddr;
+ u_char eepromSize; /* bytes / EEPROMBLOCKSIZE */
+ u_char audiomuxs[4]; /* tuner, external, internal/unused, mute */
+};
/*
* BrookTree 848 info structure, one per bt848 card installed.
*/
typedef struct bktr_softc {
- char * base; /* saa7116 register physical address */
- vm_offset_t phys_base; /* saa7116 register physical address */
+ bt848_reg_t base; /* Bt848 register physical address */
+ vm_offset_t phys_base; /* Bt848 register physical address */
pcici_t tag; /* PCI tag, for doing PCI commands */
vm_offset_t bigbuf; /* buffer that holds the captured image */
int alloc_pages; /* number of pages in bigbuf */
@@ -209,10 +299,12 @@ typedef struct bktr_softc {
void *devfs_token;
#endif
struct meteor_video video;
- struct tvtuner tuner;
+ struct TVTUNER tuner;
+ struct CARDTYPE* card;
u_char card_type; /* brand of card */
u_char audio_mux_select; /* current mode of the audio */
u_char audio_mute_state; /* mute state of the audio */
} bktr_reg_t;
+
diff --git a/sys/pci/README.bt848 b/sys/pci/README.bt848
index aa816d7..dce036d 100644
--- a/sys/pci/README.bt848
+++ b/sys/pci/README.bt848
@@ -1,4 +1,24 @@
-------------------------------------------------------------------------------
+This model now separates the "tuner control" items into a minor device:
+
+Create a video device:
+mknod bktr0 c 79 0
+
+Create a tuner device:
+mknod tuner0 c 79 16
+
+minor device layout: xxxxxxxx xxxT UUUU
+
+ UUUU: the card (ie UNIT) identifier, 0 thru 15
+ T == 0: video device
+ T == 1: tuner device
+
+Access your tuner ioctl thru your tuner device handle and anything
+which controls the video capture process thru the video device handle.
+
+Certain ioctl()s such as video source are available thru both devices.
+
+-------------------------------------------------------------------------------
There are 3 files necessary for the bt848 driver:
src/sys/i386/include/ioctl_bt848.h
diff --git a/sys/pci/brktree_reg.h b/sys/pci/brktree_reg.h
index 85c6016..cd1240a 100644
--- a/sys/pci/brktree_reg.h
+++ b/sys/pci/brktree_reg.h
@@ -37,17 +37,119 @@
*/
#define BROOKTREE_848_ID 0x0350109E
-typedef volatile u_int breg_t;
+typedef volatile u_int bregister_t;
+/*
+ * if other persuasion endian, then compiler will probably require that
+ * these next
+ * macros be reversed
+ */
+#define BTBYTE(what) bregister_t what:8; int :24
+#define BTWORD(what) bregister_t what:16; int: 16
+#define BTLONG(what) bregister_t what:32
+
+struct bt848_registers {
+ BTBYTE (dstatus); /* 0, 1,2,3 */
+#define BT848_DSTATUS_PRES (1<<7)
+#define BT848_DSTATUS_HLOC (1<<6)
+#define BT848_DSTATUS_FIELD (1<<5)
+#define BT848_DSTATUS_NUML (1<<4)
+#define BT848_DSTATUS_CSEL (1<<3)
+#define BT848_DSTATUS_LOF (1<<1)
+#define BT848_DSTATUS_COF (1<<0)
+ BTBYTE (iform); /* 4, 5,6,7 */
+ BTBYTE (tdec); /* 8, 9,a,b */
+ BTBYTE (e_crop); /* c, d,e,f */
+ BTBYTE (e_vdelay_lo); /* 10, 11,12,13 */
+ BTBYTE (e_vactive_lo); /* 14, 15,16,17 */
+ BTBYTE (e_delay_lo); /* 18, 19,1a,1b */
+ BTBYTE (e_hactive_lo); /* 1c, 1d,1e,1f */
+ BTBYTE (e_hscale_hi); /* 20, 21,22,23 */
+ BTBYTE (e_hscale_lo); /* 24, 25,26,27 */
+ BTBYTE (bright); /* 28, 29,2a,2b */
+ BTBYTE (e_control); /* 2c, 2d,2e,2f */
+ BTBYTE (contrast_lo); /* 30, 31,32,33 */
+ BTBYTE (sat_u_lo); /* 34, 35,36,37 */
+ BTBYTE (sat_v_lo); /* 38, 39,3a,3b */
+ BTBYTE (hue); /* 3c, 3d,3e,3f */
+ BTBYTE (e_scloop); /* 40, 41,42,43 */
+ int :32; /* 44, 45,46,47 */
+ BTBYTE (oform); /* 48, 49,4a,4b */
+ BTBYTE (e_vscale_hi); /* 4c, 4d,4e,4f */
+ BTBYTE (e_vscale_lo); /* 50, 51,52,53 */
+ BTBYTE (test); /* 54, 55,56,57 */
+ int :32; /* 58, 59,5a,5b */
+ int :32; /* 5c, 5d,5e,5f */
+ BTLONG (adelay); /* 60, 61,62,63 */
+ BTBYTE (bdelay); /* 64, 65,66,67 */
+ BTBYTE (adc); /* 68, 69,6a,6b */
+ BTBYTE (e_vtc); /* 6c, 6d,6e,6f */
+ int :32; /* 70, 71,72,73 */
+ int :32; /* 74, 75,76,77 */
+ int :32; /* 78, 79,7a,7b */
+ BTLONG (sreset); /* 7c, 7d,7e,7f */
+ u_char filler[0x8c-0x80];
+ BTBYTE (o_crop); /* 8c, 8d,8e,8f */
+ BTBYTE (o_vdelay_lo); /* 90, 91,92,93 */
+ BTBYTE (o_vactive_lo); /* 94, 95,96,97 */
+ BTBYTE (o_delay_lo); /* 98, 99,9a,9b */
+ BTBYTE (o_hactive_lo); /* 9c, 9d,9e,9f */
+ BTBYTE (o_hscale_hi); /* a0, a1,a2,a3 */
+ BTBYTE (o_hscale_lo); /* a4, a5,a6,a7 */
+ int :32; /* a8, a9,aa,ab */
+ BTBYTE (o_control); /* ac, ad,ae,af */
+ u_char fillter1[16];
+ BTBYTE (o_scloop); /* c0, c1,c2,c3 */
+ int :32; /* c4, c5,c6,c7 */
+ int :32; /* c8, c9,ca,cb */
+ BTBYTE (o_vscale_hi); /* cc, cd,ce,cf */
+ BTBYTE (o_vscale_lo); /* d0, d1,d2,d3 */
+ BTBYTE (color_fmt); /* d4, d5,d6,d7 */
+ BTBYTE (color_ctl); /* d8, d9,da,db */
+ BTBYTE (cap_ctl); /* dc, dd,de,df */
+ BTBYTE (vbi_pack_size); /* e0, e1,e2,e3 */
+ BTBYTE (vbi_pack_del); /* e4, e5,e6,e7 */
+ int :32; /* e8, e9,ea,eb */
+ BTBYTE (o_vtc); /* ec, ed,ee,ef */
+ u_char filler2[0x100-0xf0];
+ BTLONG (int_stat); /* 100, 101,102,103 */
+ BTLONG (int_mask); /* 104, 105,106,107 */
+#define BT848_INT_RISCS (0xf<<28)
+#define BT848_INT_RISC_EN (1<<27)
+#define BT848_INT_RACK (1<<25)
+#define BT848_INT_FIELD (1<<24)
+#define BT848_INT_SCERR (1<<19)
+#define BT848_INT_OCERR (1<<18)
+#define BT848_INT_PABORT (1<<17)
+#define BT848_INT_RIPERR (1<<16)
+#define BT848_INT_PPERR (1<<15)
+#define BT848_INT_FDSR (1<<14)
+#define BT848_INT_FTRGT (1<<13)
+#define BT848_INT_FBUS (1<<12)
+#define BT848_INT_RISCI (1<<11)
+#define BT848_INT_GPINT (1<<9)
+#define BT848_INT_I2CDONE (1<<8)
+#define BT848_INT_VPRES (1<<5)
+#define BT848_INT_HLOCK (1<<4)
+#define BT848_INT_OFLOW (1<<3)
+#define BT848_INT_HSYNC (1<<2)
+#define BT848_INT_VSYNC (1<<1)
+#define BT848_INT_FMTCHG (1<<0)
+ int :32; /* 108, 109,10a,10b */
+ BTWORD (gpio_dma_ctl); /* 10c, 10d,10e,10f */
+ BTLONG (i2c_data_ctl); /* 110, 111,112,113 */
+ BTLONG (risc_strt_add); /* 114, 115,116,117 */
+ BTLONG (gpio_out_en); /* 118, 119,11a,11b */ /* really 24 bits */
+ BTLONG (gpio_reg_inp); /* 11c, 11d,11e,11f */ /* really 24 bits */
+ BTLONG (risc_count); /* 120, 121,122,123 */
+ u_char filler3[0x200-0x124];
+ BTLONG (gpio_data); /* 200, 201,202,203 */ /* really 24 bits */
+};
+
+typedef volatile struct bt848_registers *bt848_reg_t;
+typedef volatile struct bt848_registers *bt848_regptr_t;
#define BKTR_DSTATUS 0x000
-# define BT848_DSTATUS_PRES (1<<7)
-# define BT848_DSTATUS_HLOC (1<<6)
-# define BT848_DSTATUS_FIELD (1<<5)
-# define BT848_DSTATUS_NUML (1<<4)
-# define BT848_DSTATUS_CSEL (1<<3)
-# define BT848_DSTATUS_LOF (1<<1)
-# define BT848_DSTATUS_COF (1<<0)
#define BKTR_IFORM 0x004
#define BKTR_TDEC 0x008
#define BKTR_EVEN_CROP 0x00C
@@ -92,27 +194,6 @@ typedef volatile u_int breg_t;
#define BKTR_VBI_PACK_DEL 0x0E4
#define BKTR_INT_STAT 0x100
#define BKTR_INT_MASK 0x104
-# define BT848_INT_RISCS (0xf<<28)
-# define BT848_INT_RISC_EN (1<<27)
-# define BT848_INT_RACK (1<<25)
-# define BT848_INT_FIELD (1<<24)
-# define BT848_INT_SCERR (1<<19)
-# define BT848_INT_OCERR (1<<18)
-# define BT848_INT_PABORT (1<<17)
-# define BT848_INT_RIPERR (1<<16)
-# define BT848_INT_PPERR (1<<15)
-# define BT848_INT_FDSR (1<<14)
-# define BT848_INT_FTRGT (1<<13)
-# define BT848_INT_FBUS (1<<12)
-# define BT848_INT_RISCI (1<<11)
-# define BT848_INT_GPINT (1<<9)
-# define BT848_INT_I2CDONE (1<<8)
-# define BT848_INT_VPRES (1<<5)
-# define BT848_INT_HLOCK (1<<4)
-# define BT848_INT_OFLOW (1<<3)
-# define BT848_INT_HSYNC (1<<2)
-# define BT848_INT_VSYNC (1<<1)
-# define BT848_INT_FMTCHG (1<<0)
#define BKTR_RISC_COUNT 0x120
#define BKTR_RISC_STRT_ADD 0x114
#define BKTR_GPIO_DMA_CTL 0x10C
@@ -125,20 +206,29 @@ typedef volatile u_int breg_t;
/*
* device support for onboard tv tuners
*/
-struct tvtuner {
+struct TVTUNER {
int frequency;
u_char chnlset;
u_char channel;
u_char band;
};
+#define EEPROMBLOCKSIZE 32
+struct CARDTYPE {
+ char* name;
+ u_char tuner;
+ u_char dbx;
+ u_char eepromAddr;
+ u_char eepromSize; /* bytes / EEPROMBLOCKSIZE */
+ u_char audiomuxs[4]; /* tuner, external, internal/unused, mute */
+};
/*
* BrookTree 848 info structure, one per bt848 card installed.
*/
typedef struct bktr_softc {
- char * base; /* saa7116 register physical address */
- vm_offset_t phys_base; /* saa7116 register physical address */
+ bt848_reg_t base; /* Bt848 register physical address */
+ vm_offset_t phys_base; /* Bt848 register physical address */
pcici_t tag; /* PCI tag, for doing PCI commands */
vm_offset_t bigbuf; /* buffer that holds the captured image */
int alloc_pages; /* number of pages in bigbuf */
@@ -209,10 +299,12 @@ typedef struct bktr_softc {
void *devfs_token;
#endif
struct meteor_video video;
- struct tvtuner tuner;
+ struct TVTUNER tuner;
+ struct CARDTYPE* card;
u_char card_type; /* brand of card */
u_char audio_mux_select; /* current mode of the audio */
u_char audio_mute_state; /* mute state of the audio */
} bktr_reg_t;
+
diff --git a/sys/pci/brooktree848.c b/sys/pci/brooktree848.c
index 1b10e50..444014f 100644
--- a/sys/pci/brooktree848.c
+++ b/sys/pci/brooktree848.c
@@ -122,10 +122,24 @@
1.7 3/19/97 fsmp@freefall.org
added audio support submitted by:
Michael Petry <petry@netwolf.NetMasters.com>
+
1.8 3/20/97 fsmp@freefall.org
extended audio support.
card auto-detection.
major cleanup, order of routines, declarations, etc.
+
+1.9 3/22/97 fsmp@freefall.org
+ merged in Amancio's minor unit for tuner control
+ mods.
+ misc. cleanup, especially in the _intr routine.
+ made AUDIO_SUPPORT mainline code.
+
+1.10 3/23/97 fsmp@freefall.org
+ added polled hardware i2c routines,
+ removed all existing software i2c routines.
+ created software i2cProbe() routine.
+ Randall Hopper's fixes of BT848_GHUE & BT848_GBRIG.
+ eeprom support.
*/
#include "bktr.h"
@@ -156,58 +170,6 @@
#include <vm/pmap.h>
#include <vm/vm_extern.h>
-
-/*
- * This is for start-up convenience only, NOT mandatory.
- * XXX: we need to support additional sets of frequencies.
- *
- * this selects the set of frequencies used by the tuner.
- * in your kernel config file set one of:
-options DEFAULT_CHNLSET=1 # CHNLSET_NABCST
-options DEFAULT_CHNLSET=2 # CHNLSET_CABLEIRC
- *
- * alternately, in this file, you can select one of:
- *
-#define DEFAULT_CHNLSET CHNLSET_NABCST
-#define DEFAULT_CHNLSET CHNLSET_CABLEIRC
- */
-#if !defined( DEFAULT_CHNLSET )
-#define DEFAULT_CHNLSET CHNLSET_NABCST
-#endif
-
-/*
- * the recognized cards.
- * used as indexes of several tables.
- */
-#define CARD_UNKNOWN 0
-#define CARD_MIRO 1
-#define CARD_HAUPPAUGE 2
-#define CARD_STB 3
-#define CARD_INTEL 4
-
-
-/*
- * XXX: hack to allow multiple programs to open the device,
- * ie., a tv client and a remote control
- * we need to make this a MINOR UNIT type thing someday...
- */
-#define MULTIPLE_OPENS
-
-/* XXX Fixme: remove me??? */
-#define ORIGINAL_DELAYS_NOT
-
-/* XXX Fixme: anomolies still exist in the i2c code */
-#define EXTRA_START
-#define FUNNY_HI
-#define REALLY_ACK
-
-/* XXX attempt to hold sync on marginal signals, experimental */
-#define LOW_SYNC_NOT
-
-/* srart of audio support */
-#define AUDIO_SUPPORT
-
-
#include "pci.h"
#if NPCI > 0
@@ -275,23 +237,72 @@ static struct cdevsw bktr_cdevsw =
/*
+ * This is for start-up convenience only, NOT mandatory.
+ */
+#if !defined( DEFAULT_CHNLSET )
+#define DEFAULT_CHNLSET CHNLSET_NABCST
+#endif
+
+/*
+ * the recognized cards.
+ * used as indexes of several tables.
+ */
+#define CARD_UNKNOWN 0
+#define CARD_MIRO 1
+#define CARD_HAUPPAUGE 2
+#define CARD_STB 3
+#define CARD_INTEL 4
+
+/*
+ * i2c things:
+ */
+
+/* XXX FIXME: experimental code, use with caution! */
+#define EEPROM_SUPPORT
+
+/* guaranteed address for any TSA5522/3 (PLL on all(?) tuners) */
+#define TSA5522_WADDR 0xc2
+#define TSA5522_RADDR 0xc3
+
+#define TEMIC_TSA5522_RADDR 0xc1
+#define PHILIPS_TSA5523_RADDR 0xc7
+
+/* address of BTSC/SAP decoder chip */
+#define TDA9850_WADDR 0xb6
+#define TDA9850_RADDR 0xb7
+
+/* EEProm (128 * 8) on an STB card */
+#define X24C01_WADDR 0xae
+#define X24C01_RADDR 0xaf
+
+/* EEProm (256 * 8) on a Hauppauge card */
+#define PFC8582_WADDR 0xa0
+#define PFC8582_RADDR 0xa1
+
+/* debug utility for holding previous INT_STAT contents */
+#define STATUS
+static u_long status_sum = 0;
+
+/* FIXME: magic#s sync detect threashold */
+#if 1
+#define SYNC_LEVEL 0x81 /* threashold ~125 mV */
+#else
+#define SYNC_LEVEL 0xa1 /* threashold ~75 mV */
+#endif
+
+
+/*
* misc. support routines.
*/
-struct CARDTYPE {
- char* name;
- u_char tuner;
- u_char dbx;
- u_char audiomuxs[4]; /* tuner, external, internal/unused, mute */
-};
-static struct CARDTYPE card_types[];
-static int probe_card( bktr_reg_t *bktr, int verbose );
-static vm_offset_t get_bktr_mem( int unit, unsigned size );
+static struct CARDTYPE card_types[];
+static int probe_card( bktr_reg_t *bktr, int verbose );
+static vm_offset_t get_bktr_mem( int unit, unsigned size );
/*
* bt848 RISC programming routines.
*/
-static int dump_bt848( volatile u_char *bt848 );
+static int dump_bt848( bt848_reg_t bt848 );
static void yuvpack_prog( bktr_reg_t * bktr, char i_flag, int cols,
int rows, int interlace) ;
@@ -306,6 +317,11 @@ static void build_dma_prog( bktr_reg_t * bktr, char i_flag);
/*
* video & video capture specific routines.
*/
+static int video_open( bktr_reg_t *bktr );
+static int video_close( bktr_reg_t *bktr );
+static int video_ioctl( bktr_reg_t* bktr, int unit,
+ int cmd, caddr_t arg, struct proc* pr );
+
static void start_capture( bktr_reg_t *bktr, unsigned type );
static void set_fps( bktr_reg_t *bktr, u_short fps );
@@ -313,18 +329,38 @@ static void set_fps( bktr_reg_t *bktr, u_short fps );
/*
* tuner specific functions.
*/
+static int tuner_open( bktr_reg_t* bktr );
+static int tuner_close( bktr_reg_t* bktr );
+static int tuner_ioctl( bktr_reg_t* bktr, int unit,
+ int cmd, caddr_t arg, struct proc* pr );
+
static int tv_channel( bktr_reg_t* bktr, int channel );
static int tv_freq( bktr_reg_t* bktr, int frequency );
-static int tuner_status( bktr_reg_t* bktr );
-#if defined( AUDIO_SUPPORT )
/*
* audio specific functions.
*/
static int set_audio( bktr_reg_t * bktr, int mode );
static int set_BTSC( bktr_reg_t * bktr, int control );
-#endif /* AUDIO_SUPPORT */
+
+
+/*
+ *
+ */
+static int common_ioctl( bktr_reg_t* bktr, bt848_reg_t bt848,
+ int cmd, caddr_t arg );
+
+
+/*
+ * i2c primitives
+ */
+static int i2cWrite( bktr_reg_t *bktr, int addr, int byte1, int byte2 );
+static int i2cRead( bktr_reg_t *bktr, int addr );
+#if defined( EEPROM_SUPPORT )
+static int readEEProm( bktr_reg_t* bktr, int offset, int count,
+ u_char* data );
+#endif /* EEPROM_SUPPORT */
/*
@@ -343,160 +379,6 @@ bktr_probe( pcici_t tag, pcidi_t type )
/*
- * interrupt handling routine complete bktr_read() if using interrupts.
- */
-static void
-bktr_intr( void *arg )
-{
- bktr_reg_t *bktr = (bktr_reg_t *) arg;
- volatile u_long *btl_reg, t_pc;
- volatile u_char *bt848, *bt_reg, s_status;
- volatile u_short *bts_reg;
- u_long bktr_status, *bktr_pc;
-
-#if 0
-/* XXX: what is this for??? */
- u_long next_base = (u_long)(vtophys(bktr->bigbuf)), stat;
-#endif
-
- bt848 = bktr->base;
- bt_reg = (u_char *) &bt848;
- s_status = *bt_reg;
- *bt_reg = 0;
-
- if (!(bktr->flags & METEOR_OPEN)) {
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
- }
-
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- bktr_status = *btl_reg ;
- *btl_reg = *btl_reg;
- *btl_reg = 0;
- if (*btl_reg & (1 << 25))
- *btl_reg |= 1 << 8;
- bktr_pc = (u_long *) &bt848[BKTR_RISC_COUNT];
- t_pc = *bktr_pc;
-
- /* printf(" STATUS %x %x %x \n", s_status, bktr_status, t_pc); */
-
- if (!((bktr_status & 0x800) || (bktr_status & 1 << 19 ))) {
- btl_status_prev = bktr_status;
- /* return; */
- }
-
- /* if risc was disabled re-start process again */
- if (!(bktr_status & (1 << 27)) || ((bktr_status & 0xff000) != 0) ) {
-
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = *btl_reg;
-
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
-
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
-
- btl_reg = (u_long *) &bt848[BKTR_RISC_STRT_ADD] ;
- *btl_reg = vtophys(bktr->dma_prog);
-
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 1;
- *bts_reg = bktr->capcontrol;
-
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 1 << 23 | 1 << 11 | 2 | 1;
- bt848[BKTR_CAP_CTL] = bktr->bktr_cap_ctl;
-
- return;
- }
-
- btl_reg = (u_long *) &bt848[BKTR_CAP_CTL];
- if (!(bktr_status & (1 << 11))) return;
-
- bktr_pc = (u_long *) &bt848[BKTR_RISC_COUNT];
-
- /*printf("intr status %x %x %x\n", bktr_status, s_status, *bktr_pc);*/
-
- /*
- * Disable future interrupts if a capture mode is not selected.
- * This can happen when we are in the process of closing or
- * changing capture modes, otherwise it shouldn't happen.
- */
- if (!(bktr->flags & METEOR_CAP_MASK))
- *btl_reg = 0;
-
- /*
- * If we have a complete frame.
- */
- if (!(bktr->flags & METEOR_WANT_MASK)) {
- bktr->frames_captured++;
- /*
- * post the completion time.
- */
- if (bktr->flags & METEOR_WANT_TS) {
- struct timeval *ts;
-
- if ((u_int) bktr->alloc_pages * PAGE_SIZE
- <= (bktr->frame_size + sizeof(struct timeval))) {
- ts =(struct timeval *)bktr->bigbuf +
- bktr->frame_size;
- /* doesn't work in synch mode except
- * for first frame */
- /* XXX */
- microtime(ts);
- }
- }
-
- /*
- * Wake up the user in single capture mode.
- */
- if (bktr->flags & METEOR_SINGLE) {
-
- if (!(bktr_status & (1 << 24)))
- return;
-
- /* stop dma */
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 1; /* disable risc and fifo */
- wakeup((caddr_t)bktr);
- }
-
- /*
- * If the user requested to be notified via signal,
- * let them know the frame is complete.
- */
- if (bktr->proc && !(bktr->signal & METEOR_SIG_MODE_MASK))
- psignal(bktr->proc, bktr->signal&(~METEOR_SIG_MODE_MASK));
-
- /*
- * Reset the want flags if in continuous or
- * synchronous capture mode.
- */
- if (bktr->flags & (METEOR_CONTIN|METEOR_SYNCAP)) {
- switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
- case METEOR_ONLY_ODD_FIELDS:
- bktr->flags |= METEOR_WANT_ODD;
- break;
- case METEOR_ONLY_EVEN_FIELDS:
- bktr->flags |= METEOR_WANT_EVEN;
- break;
- default:
- bktr->flags |= METEOR_WANT_MASK;
- break;
- }
- }
- }
-
- return;
-}
-
-
-/*
* what should we do here?
*/
static void
@@ -513,8 +395,7 @@ static void
bktr_attach( pcici_t tag, int unit )
{
bktr_reg_t *bktr;
- volatile u_char *bt848;
- volatile u_long *btl_reg;
+ bt848_reg_t bt848;
#ifdef BROOKTREE_IRQ
u_long old_irq, new_irq;
#endif
@@ -615,9 +496,8 @@ end of setup up dma risc program
bktr->depth = 2; /* two bytes per pixel */
bktr->frames = 1; /* one frame */
bt848 = bktr->base;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
- bt848[BKTR_GPIO_DMA_CTL] = 0;
+ bt848->int_mask = 0;
+ bt848->gpio_dma_ctl = 0;
}
/* defaults for the tuner section of the card */
@@ -633,7 +513,167 @@ end of setup up dma risc program
#endif /* DEVFS */
}
-#define UNIT(x) ((x) & 0x07)
+
+/*
+ * interrupt handling routine complete bktr_read() if using interrupts.
+ */
+static void
+bktr_intr( void *arg )
+{
+
+ bktr_reg_t *bktr = (bktr_reg_t *) arg;
+ volatile u_long *bktr_pc;
+ bt848_reg_t bt848;
+ u_long bktr_status;
+ u_char dstatus;
+
+ bt848 = bktr->base;
+
+ /*
+ * check to see if any interrupts are unmasked on this device. If
+ * none are, then we likely got here by way of being on a PCI shared
+ * interrupt dispatch list.
+ */
+ if ( bt848->int_mask == 0 )
+ return; /* bail out now, before we do something we
+ shouldn't */
+
+ if (!(bktr->flags & METEOR_OPEN)) {
+ bt848->gpio_dma_ctl = 0;
+ bt848->int_mask = 0;
+ /* return; ?? */
+ }
+
+ /* record and clear the INTerrupt status bits */
+ bktr_status = bt848->int_stat;
+ bt848->int_stat = bt848->int_stat;
+
+ /* record and clear the device status register */
+ dstatus = bt848->dstatus;
+ bt848->dstatus = 0;
+
+#if defined( STATUS )
+ /* add any new device status or INTerrupt status bits */
+ status_sum |= (bktr_status & ~0xc0); /* clear 2 resv bits */
+ status_sum |= ((dstatus & 0x03) << 6); /* device LOF/COF */
+#endif /* STATUS */
+
+#if 0
+ /* check i2c status */
+ if (bt848->int_stat & (1 << 25)) /* XXX bug, already cleared above */
+ bt848->int_stat |= 1 << 8;
+#endif
+
+#if 0
+ bktr_pc = bt848->risc_count;
+ printf( " STATUS %x %x %x \n", dstatus, bktr_status, *bktr_pc );
+#endif
+
+ if (!((bktr_status & 0x800) || (bktr_status & 1 << 19 ))) {
+ btl_status_prev = bktr_status;
+ /* return; */
+ }
+
+ /* if risc was disabled re-start process again */
+ if (!(bktr_status & (1 << 27)) || ((bktr_status & 0xff000) != 0) ) {
+
+/* XXX isn't this redundant ??? */
+ bt848->int_stat = bt848->int_stat;
+
+ bt848->gpio_dma_ctl = 0;
+
+ bt848->int_mask = 0;
+
+ bt848->risc_strt_add = vtophys(bktr->dma_prog);
+
+ bt848->gpio_dma_ctl = 1;
+ bt848->gpio_dma_ctl = bktr->capcontrol;
+
+ bt848->int_mask = 1 << 23 | 1 << 11 | 2 | 1;
+ bt848->cap_ctl = bktr->bktr_cap_ctl;
+
+ return;
+ }
+
+ if (!(bktr_status & (1 << 11)))
+ return;
+#if 0
+ printf( "intr status %x %x %x\n", bktr_status, dstatus,
+ bt848->risc_count);
+#endif
+
+ /*
+ * Disable future interrupts if a capture mode is not selected.
+ * This can happen when we are in the process of closing or
+ * changing capture modes, otherwise it shouldn't happen.
+ */
+ if (!(bktr->flags & METEOR_CAP_MASK))
+ bt848->cap_ctl = 0;
+
+ /*
+ * If we have a complete frame.
+ */
+ if (!(bktr->flags & METEOR_WANT_MASK)) {
+ bktr->frames_captured++;
+ /*
+ * post the completion time.
+ */
+ if (bktr->flags & METEOR_WANT_TS) {
+ struct timeval *ts;
+
+ if ((u_int) bktr->alloc_pages * PAGE_SIZE
+ <= (bktr->frame_size + sizeof(struct timeval))) {
+ ts =(struct timeval *)bktr->bigbuf +
+ bktr->frame_size;
+ /* doesn't work in synch mode except
+ * for first frame */
+ /* XXX */
+ microtime(ts);
+ }
+ }
+
+ /*
+ * Wake up the user in single capture mode.
+ */
+ if (bktr->flags & METEOR_SINGLE) {
+
+ if (!(bktr_status & (1 << 24)))
+ return;
+
+ /* stop dma */
+ bt848->int_mask = 0;
+ bt848->gpio_dma_ctl = 1; /* disable risc and fifo */
+ wakeup((caddr_t)bktr);
+ }
+
+ /*
+ * If the user requested to be notified via signal,
+ * let them know the frame is complete.
+ */
+ if (bktr->proc && !(bktr->signal & METEOR_SIG_MODE_MASK))
+ psignal(bktr->proc, bktr->signal&(~METEOR_SIG_MODE_MASK));
+
+ /*
+ * Reset the want flags if in continuous or
+ * synchronous capture mode.
+ */
+ if (bktr->flags & (METEOR_CONTIN|METEOR_SYNCAP)) {
+ switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
+ case METEOR_ONLY_ODD_FIELDS:
+ bktr->flags |= METEOR_WANT_ODD;
+ break;
+ case METEOR_ONLY_EVEN_FIELDS:
+ bktr->flags |= METEOR_WANT_EVEN;
+ break;
+ default:
+ bktr->flags |= METEOR_WANT_MASK;
+ break;
+ }
+ }
+ }
+
+ return;
+}
/*---------------------------------------------------------
@@ -644,6 +684,9 @@ end of setup up dma risc program
*/
+#define UNIT(x) ((x) & 0x0f)
+#define MINOR(x) ((x) & 0xf0)
+
/*
*
*/
@@ -651,11 +694,9 @@ int
bktr_open( dev_t dev, int flags, int fmt, struct proc *p )
{
bktr_reg_t *bktr;
- int unit;
+ int unit, minor;
int i;
- volatile u_char *bt848;
- volatile u_char *bt_reg;
- volatile u_long *btl_reg;
+ bt848_reg_t bt848;
unit = UNIT(minor(dev));
if (unit >= NBKTR) /* unit out of range */
@@ -666,46 +707,51 @@ bktr_open( dev_t dev, int flags, int fmt, struct proc *p )
if (!(bktr->flags & METEOR_INITALIZED)) /* device not found */
return(ENXIO);
-#if defined( MULTIPLE_OPENS )
- if (bktr->flags & METEOR_OPEN) /* device already open */
- return 0;
-#else
+ if ( minor(dev) & 0x0010 )
+ return tuner_open( bktr );
+ else
+ return video_open( bktr );
+}
+
+
+/*
+ *
+ */
+static int
+video_open( bktr_reg_t *bktr )
+{
+ bt848_reg_t bt848;
+
if (bktr->flags & METEOR_OPEN) /* device is busy */
return(EBUSY);
-#endif /* MULTIPLE_OPENS */
bktr->flags |= METEOR_OPEN;
-
+
bt848 = bktr->base;
#if 0
dump_bt848( bt848 );
#endif /* 0 */
- *bt848 = 0x3; /* bt848[ 0 ] */
- *bt848 = 0xc0;
+ bt848->dstatus = 0x00; /* bt848[ DSTATUS ] */
-#if defined( LOW_SYNC )
- bt848[BKTR_ADC] = 0xa1;
-#else
- bt848[BKTR_ADC] = 0x81;
-#endif /* LOW_SYNC */
+ bt848->adc = SYNC_LEVEL;
- bt848[BKTR_IFORM] = 0x69;
+ bt848->iform = 0x69;
bktr->flags = (bktr->flags & ~METEOR_DEV_MASK) | METEOR_DEV0;
- bt848[BKTR_COLOR_CTL] = 0x20;
+ bt848->color_ctl = 0x20;
- bt848[BKTR_E_HSCALE_LO] = 0xaa;
- bt848[BKTR_O_HSCALE_LO] = 0xaa;
+ bt848->e_hscale_lo = 0xaa;
+ bt848->o_hscale_lo = 0xaa;
- bt848[BKTR_E_DELAY_LO] = 0x72;
- bt848[BKTR_O_DELAY_LO] = 0x72;
- bt848[BKTR_E_SCLOOP] = 0;
- bt848[BKTR_O_SCLOOP] = 0;
+ bt848->e_delay_lo = 0x72;
+ bt848->o_delay_lo = 0x72;
+ bt848->e_scloop = 0;
+ bt848->o_scloop = 0;
- bt848[BKTR_VBI_PACK_SIZE] = 0;
- bt848[BKTR_VBI_PACK_DEL] = 0;
+ bt848->vbi_pack_size = 0;
+ bt848->vbi_pack_del = 0;
bzero((u_char *) bktr->bigbuf, 640*480*4);
bktr->fifo_errors = 0;
@@ -720,16 +766,28 @@ bktr_open( dev_t dev, int flags, int fmt, struct proc *p )
bktr->video.banksize = 0;
bktr->video.ramsize = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 1 << 23;
+ bt848->int_mask = 1 << 23; /* ? */
+
+ return( 0 );
+}
+
+
+/*
+ *
+ */
+static int
+tuner_open( bktr_reg_t *bktr )
+{
+ bt848_reg_t bt848 = bktr->base;
+
+#define GPIO_AUDIOMUX_BITS 0x07
+ bt848->gpio_out_en = GPIO_AUDIOMUX_BITS; /* drive low 3 bits */
-#if defined( AUDIO_SUPPORT )
set_audio( bktr, AUDIO_UNMUTE );
- if ( card_types[ bktr->card_type ].dbx )
- set_BTSC( bktr, 0 ); /* enable the stereo chip */
-#endif /* AUDIO_SUPPORT */
+ if ( bktr->card->dbx )
+ set_BTSC( bktr, 0 ); /* enable stereo */
- return(0);
+ return( 0 );
}
@@ -741,9 +799,8 @@ bktr_close( dev_t dev, int flags, int fmt, struct proc *p )
{
bktr_reg_t *bktr;
int unit;
- volatile u_char *bt848;
- volatile u_long *btl_reg;
- u_short *bts_reg;
+ bt848_reg_t bt848;
+
#ifdef METEOR_DEALLOC_ABOVE
int temp;
#endif
@@ -754,29 +811,55 @@ bktr_close( dev_t dev, int flags, int fmt, struct proc *p )
bktr = &(brooktree[unit]);
+ if ( minor(dev) & 0x0010 )
+ return tuner_close( bktr );
+ else
+ return video_close( bktr );
+}
+
+
+/*
+ *
+ */
+static int
+video_close( bktr_reg_t *bktr )
+{
+ bt848_reg_t bt848;
+
bktr->flags &= ~METEOR_OPEN;
bktr->flags &= ~(METEOR_SINGLE | METEOR_WANT_MASK);
bktr->flags &= ~(METEOR_CAP_MASK|METEOR_WANT_MASK);
+
bt848 = bktr->base;
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
- bt848[BKTR_CAP_CTL] = 0;
+ bt848->gpio_dma_ctl = 0;
+ bt848->cap_ctl = 0;
bktr->dma_prog_loaded = 0;
- bt848[BKTR_TDEC] = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
+ bt848->tdec = 0;
+ bt848->int_mask = 0;
- bt848[BKTR_SRESET] = 0xf;
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT] ;
- *btl_reg = 0xffffffff;
+ bt848->sreset = 0xf;
+ bt848->int_stat = 0xffffffff;
+
+ return( 0 );
+}
+
+
+/*
+ * tuner close handle,
+ * place holder for tuner specific operations on a close.
+ */
+static int
+tuner_close( bktr_reg_t *bktr )
+{
+ bt848_reg_t bt848 = bktr->base;
-#if defined( AUDIO_SUPPORT )
/* mute the audio by switching the mux */
set_audio( bktr, AUDIO_MUTE );
-#endif /* AUDIO_SUPPORT */
- return(0);
+ bt848->gpio_out_en = 0; /* float low 3 bits */
+
+ return( 0 );
}
@@ -790,9 +873,9 @@ bktr_read( dev_t dev, struct uio *uio, int ioflag )
int unit;
int status;
int count;
- volatile u_char *bt848;
- u_short *bts_reg;
-
+ bt848_reg_t bt848;
+
+ if (minor(dev) > 0 ) return(ENXIO);
unit = UNIT(minor(dev));
if (unit >= NBKTR) /* unit out of range */
return(ENXIO);
@@ -804,7 +887,7 @@ bktr_read( dev_t dev, struct uio *uio, int ioflag )
if (bktr->flags & METEOR_CAP_MASK)
return(EIO); /* already capturing */
- bt848 = (u_char *) bktr->base;
+ bt848 = bktr->base;
count = bktr->rows * bktr->cols * bktr->depth;
@@ -813,9 +896,8 @@ bktr_read( dev_t dev, struct uio *uio, int ioflag )
bktr->flags &= ~(METEOR_CAP_MASK|METEOR_WANT_MASK);
/* Start capture */
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0x1;
- *bts_reg = 0x3;
+ bt848->gpio_dma_ctl = 0x1;
+ bt848->gpio_dma_ctl = 0x3;
status=tsleep((caddr_t)bktr, METPRI, "capturing", 0);
if (!status) /* successful capture */
@@ -835,7 +917,7 @@ bktr_read( dev_t dev, struct uio *uio, int ioflag )
int
bktr_write( dev_t dev, struct uio *uio, int ioflag )
{
- return(0);
+ return( 0 );
}
@@ -843,166 +925,73 @@ bktr_write( dev_t dev, struct uio *uio, int ioflag )
*
*/
int
-bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
+bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc* pr )
{
- bktr_reg_t *bktr;
- int unit;
- int status;
- int count;
- int tmp_int;
- volatile u_char *bt848, c_temp;
- volatile u_short *bts_reg, s_temp;
- volatile u_long *btl_reg;
- unsigned int temp, temp1;
- unsigned int error;
- struct meteor_geomet *geo;
- struct meteor_counts *cnt;
- struct meteor_video *video;
- vm_offset_t buf;
+ bktr_reg_t* bktr;
+ int unit;
unit = UNIT(minor(dev));
if (unit >= NBKTR) /* unit out of range */
- return(ENXIO);
+ return( ENXIO );
+ bktr = &(brooktree[ unit ]);
- bktr = &(brooktree[unit]);
if (bktr->bigbuf == 0) /* no frame buffer allocated (ioctl failed) */
- return(ENOMEM);
-
- bt848 = bktr->base;
- switch (cmd) {
-
- case TVTUNER_SETCHNL:
-#if defined( AUDIO_SUPPORT )
- set_audio( bktr, AUDIO_MUTE );
-#endif /* AUDIO_SUPPORT */
- temp = tv_channel( bktr, (int)*(unsigned long *)arg );
-#if defined( AUDIO_SUPPORT )
- set_audio( bktr, AUDIO_UNMUTE );
-#endif /* AUDIO_SUPPORT */
- if ( temp < 0 )
- return EINVAL;
- *(unsigned long *)arg = temp;
- break;
-
- case TVTUNER_GETCHNL:
- *(unsigned long *)arg = bktr->tuner.channel;
- break;
+ return( ENOMEM );
- case TVTUNER_SETTYPE:
- temp = *(unsigned long *)arg;
- if ( (temp < CHNLSET_MIN) || (temp > CHNLSET_MAX) )
- return EINVAL;
- bktr->tuner.chnlset = temp;
- break;
+ if ( minor(dev) & 0x0010 )
+ return tuner_ioctl( bktr, unit, cmd, arg, pr );
+ else
+ return video_ioctl( bktr, unit, cmd, arg, pr );
+}
- case TVTUNER_GETTYPE:
- *(unsigned long *)arg = bktr->tuner.chnlset;
- break;
- case TVTUNER_GETSTATUS:
- temp = tuner_status( bktr );
- *(unsigned long *)arg = temp & 0xff;
- break;
+/*
+ * video ioctls
+ */
+static int
+video_ioctl( bktr_reg_t* bktr, int unit,
+ int cmd, caddr_t arg, struct proc* pr )
+{
+ int status;
+ int count;
+ int tmp_int;
+ bt848_reg_t bt848;
+ volatile u_char c_temp;
+ volatile u_short s_temp;
+ unsigned int temp, temp1;
+ unsigned int error;
+ struct meteor_geomet *geo;
+ struct meteor_counts *cnt;
+ struct meteor_video *video;
+ vm_offset_t buf;
- case TVTUNER_SETFREQ:
-#if defined( AUDIO_SUPPORT_XXX )
- set_audio( bktr, AUDIO_MUTE );
-#endif /* AUDIO_SUPPORT */
- temp = tv_freq( bktr, (int)*(unsigned long *)arg );
-#if defined( AUDIO_SUPPORT_XXX )
- set_audio( bktr, AUDIO_UNMUTE );
-#endif /* AUDIO_SUPPORT */
- if ( temp < 0 )
- return EINVAL;
- *(unsigned long *)arg = temp;
- break;
+ bt848 = bktr->base;
- case TVTUNER_GETFREQ:
- *(unsigned long *)arg = bktr->tuner.frequency;
- break;
+ switch ( cmd ) {
- case METEORSTATUS: /* get 7196 status */
- c_temp = bt848[0];
+ case METEORSTATUS: /* get Bt848 status */
+ c_temp = bt848->dstatus;
temp = 0;
if (!(c_temp & 0x40)) temp |= METEOR_STATUS_HCLK;
if (!(c_temp & 0x10)) temp |= METEOR_STATUS_FIDT;
*(u_short *)arg = temp;
break;
- case METEORSINPUT: /* set input device */
- switch(*(unsigned long *)arg & METEOR_DEV_MASK) {
-
- /* this is the RCA video input */
- case 0: /* default */
- case METEOR_INPUT_DEV0:
- bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
- | METEOR_DEV0;
- bt848[BKTR_IFORM] &= ~0x60;
- bt848[BKTR_IFORM] |= 0x60;
- bt848[BKTR_E_CONTROL] &= ~0x40;
- bt848[BKTR_O_CONTROL] &= ~0x40;
-#if defined( AUDIO_SUPPORT )
- set_audio( bktr, AUDIO_MUTE );
- set_audio( bktr, AUDIO_EXTERN );
- set_audio( bktr, AUDIO_UNMUTE );
-#endif /* AUDIO_SUPPORT */
- break;
-
- /* this is the tuner input */
- case METEOR_INPUT_DEV1:
- bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
- | METEOR_DEV1;
- bt848[BKTR_IFORM] &= ~0x60;
- bt848[BKTR_IFORM] |= 0x40;
- bt848[BKTR_E_CONTROL] &= ~0x40;
- bt848[BKTR_O_CONTROL] &= ~0x40;
-#if defined( AUDIO_SUPPORT )
- set_audio( bktr, AUDIO_MUTE );
- set_audio( bktr, AUDIO_TUNER );
- set_audio( bktr, AUDIO_UNMUTE );
-#endif /* AUDIO_SUPPORT */
- break;
-
- /* this is the S-VHS input */
- case METEOR_INPUT_DEV2:
- case METEOR_INPUT_DEV_SVIDEO:
- bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
- | METEOR_DEV2;
- bt848[BKTR_IFORM] &= ~0x60;
- bt848[BKTR_IFORM] |= 0x20;
- bt848[BKTR_E_CONTROL] |= 0x40;
- bt848[BKTR_O_CONTROL] |= 0x40;
-#if defined( AUDIO_SUPPORT )
- set_audio( bktr, AUDIO_MUTE );
- set_audio( bktr, AUDIO_EXTERN );
- set_audio( bktr, AUDIO_UNMUTE );
-#endif /* AUDIO_SUPPORT */
- break;
-
- default:
- return EINVAL;
- }
- break;
-
- case METEORGINPUT: /* get input device */
- *(u_long *)arg = bktr->flags & METEOR_DEV_MASK;
- break;
-
case METEORSFMT: /* set input format */
switch(*(unsigned long *)arg & METEOR_FORM_MASK ) {
case 0: /* default */
case METEOR_FMT_NTSC:
bktr->flags = (bktr->flags & ~METEOR_FORM_MASK) |
METEOR_NTSC;
- bt848[BKTR_IFORM] &= ~0x3;
- bt848[BKTR_IFORM] |= 1;
+ bt848->iform &= ~0x3;
+ bt848->iform |= 1;
break;
case METEOR_FMT_AUTOMODE:
bktr->flags = (bktr->flags & ~METEOR_FORM_MASK) |
METEOR_AUTOMODE;
- bt848[BKTR_IFORM] &= ~0x3;
+ bt848->iform &= ~0x3;
break;
default:
@@ -1057,39 +1046,39 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
break;
case METEORSHUE: /* set hue */
- bt848[BKTR_HUE] = (*(u_char *) arg) & 0xff;
+ bt848->hue = (*(u_char *) arg) & 0xff;
break;
case METEORGHUE: /* get hue */
- *(u_char *)arg = bt848[BKTR_HUE];
+ *(u_char *)arg = bt848->hue;
break;
case METEORSBRIG: /* set brightness */
- bt848[BKTR_BRIGHT] = *(u_char *)arg & 0xff;
+ bt848->bright = *(u_char *)arg & 0xff;
break;
case METEORGBRIG: /* get brightness */
- *(u_char *)arg = bt848[BKTR_BRIGHT];
+ *(u_char *)arg = bt848->bright;
break;
case METEORSCSAT: /* set chroma saturation */
temp = (int)*(u_char *)arg;
- bt848[BKTR_SAT_U_LO] = bt848[BKTR_SAT_V_LO] =
+ bt848->sat_u_lo = bt848->sat_v_lo =
(temp << 1) & 0xff;
- bt848[BKTR_E_CONTROL] &= ~0x3; /* clear U/V MSBs */
- bt848[BKTR_O_CONTROL] &= ~0x3; /* clear U/V MSBs */
+ bt848->e_control &= ~0x3; /* clear U/V MSBs */
+ bt848->o_control &= ~0x3; /* clear U/V MSBs */
if ( temp & 0x80 ) {
- bt848[BKTR_E_CONTROL] |= 0x3;
- bt848[BKTR_O_CONTROL] |= 0x3;
+ bt848->e_control |= 0x3;
+ bt848->o_control |= 0x3;
}
break;
case METEORGCSAT: /* get chroma saturation */
- temp = (bt848[BKTR_SAT_V_LO] >> 1) & 0xff;
- if ( bt848[BKTR_E_CONTROL] & 0x01 )
+ temp = (bt848->sat_v_lo >> 1) & 0xff;
+ if ( bt848->e_control & 0x01 )
temp |= 0x80;
*(u_char *)arg = (u_char)temp;
break;
@@ -1097,157 +1086,19 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
case METEORSCONT: /* set contrast */
temp = (int)*(u_char *)arg & 0xff;
temp <<= 1;
- bt848[BKTR_CONTRAST_LO] = temp & 0xff;
- bt848[BKTR_E_CONTROL] &= ~0x4;
- bt848[BKTR_O_CONTROL] &= ~0x4;
- bt848[BKTR_E_CONTROL] |= ((temp & 0x100) >> 6 ) & 0x4 ;
- bt848[BKTR_O_CONTROL] |= ((temp & 0x100) >> 6 ) & 0x4 ;
+ bt848->contrast_lo = temp & 0xff;
+ bt848->e_control &= ~0x4;
+ bt848->o_control &= ~0x4;
+ bt848->e_control |= ((temp & 0x100) >> 6 ) & 0x4 ;
+ bt848->o_control |= ((temp & 0x100) >> 6 ) & 0x4 ;
break;
case METEORGCONT: /* get contrast */
- temp = (int)bt848[BKTR_CONTRAST_LO] & 0xff;
- temp |= ((int)bt848[BKTR_O_CONTROL] & 0x04) << 6;
+ temp = (int)bt848->contrast_lo & 0xff;
+ temp |= ((int)bt848->o_control & 0x04) << 6;
*(u_char *)arg = (u_char)((temp >> 1) & 0xff);
break;
- /* hue is a 2's compliment number, -90' to +89.3' in 0.7' steps */
- case BT848_SHUE: /* set hue */
- bt848[BKTR_HUE] = (u_char)(*(int*)arg & 0xff);
- break;
-
- case BT848_GHUE: /* get hue */
- *(int*)arg = bt848[BKTR_HUE] & 0xff;
- break;
-
- /* brightness is a 2's compliment #, -50 to +%49.6% in 0.39% steps */
- case BT848_SBRIG: /* set brightness */
- bt848[BKTR_BRIGHT] = (u_char)(*(int *)arg & 0xff);
- break;
-
- case BT848_GBRIG: /* get brightness */
- *(int *)arg = bt848[BKTR_BRIGHT] & 0xff;
- break;
-
- /* */
- case BT848_SCSAT: /* set chroma saturation */
- tmp_int = *(int*)arg;
-
- temp = bt848[BKTR_E_CONTROL] & 0xfc;
- temp1 = bt848[BKTR_O_CONTROL] & 0xfc;
- if ( tmp_int & 0x100 ) {
- temp |= 0x03;
- temp1 |= 0x03;
- }
-
- bt848[BKTR_SAT_U_LO] = (u_char)(tmp_int & 0xff);
- bt848[BKTR_SAT_V_LO] = (u_char)(tmp_int & 0xff);
- bt848[BKTR_E_CONTROL] = temp;
- bt848[BKTR_O_CONTROL] = temp1;
- break;
-
- case BT848_GCSAT: /* get chroma saturation */
- tmp_int = (int)bt848[BKTR_SAT_V_LO] & 0xff;
- if ( bt848[BKTR_E_CONTROL] & 0x01 )
- tmp_int |= 0x0100;
- *(int*)arg = tmp_int;
- break;
-
- /* */
- case BT848_SVSAT: /* set chroma V saturation */
- tmp_int = *(int*)arg;
-
- temp = bt848[BKTR_E_CONTROL] & 0xfe;
- temp1 = bt848[BKTR_O_CONTROL] & 0xfe;
- if ( tmp_int & 0x100 ) {
- temp |= 0x01;
- temp1 |= 0x01;
- }
-
- bt848[BKTR_SAT_V_LO] = (u_char)(tmp_int & 0xff);
- bt848[BKTR_E_CONTROL] = temp;
- bt848[BKTR_O_CONTROL] = temp1;
- break;
-
- case BT848_GVSAT: /* get chroma V saturation */
- tmp_int = (int)bt848[BKTR_SAT_V_LO] & 0xff;
- if ( bt848[BKTR_E_CONTROL] & 0x01 )
- tmp_int |= 0x0100;
- *(int*)arg = tmp_int;
- break;
-
- /* */
- case BT848_SUSAT: /* set chroma U saturation */
- tmp_int = *(int*)arg;
-
- temp = bt848[BKTR_E_CONTROL] & 0xfd;
- temp1 = bt848[BKTR_O_CONTROL] & 0xfd;
- if ( tmp_int & 0x100 ) {
- temp |= 0x02;
- temp1 |= 0x02;
- }
-
- bt848[BKTR_SAT_U_LO] = (u_char)(tmp_int & 0xff);
- bt848[BKTR_E_CONTROL] = temp;
- bt848[BKTR_O_CONTROL] = temp1;
- break;
-
- case BT848_GUSAT: /* get chroma U saturation */
- tmp_int = (int)bt848[BKTR_SAT_U_LO] & 0xff;
- if ( bt848[BKTR_E_CONTROL] & 0x02 )
- tmp_int |= 0x0100;
- *(int*)arg = tmp_int;
- break;
-
- /* */
- case BT848_SCONT: /* set contrast */
- tmp_int = *(int*)arg;
-
- temp = bt848[BKTR_E_CONTROL] & 0xfb;
- temp1 = bt848[BKTR_O_CONTROL] & 0xfb;
- if ( tmp_int & 0x100 ) {
- temp |= 0x04;
- temp1 |= 0x04;
- }
-
- bt848[BKTR_CONTRAST_LO] = (u_char)(tmp_int & 0xff);
- bt848[BKTR_E_CONTROL] = temp;
- bt848[BKTR_O_CONTROL] = temp1;
- break;
-
- case BT848_GCONT: /* get contrast */
- tmp_int = (int)bt848[BKTR_CONTRAST_LO] & 0xff;
- if ( bt848[BKTR_E_CONTROL] & 0x04 )
- tmp_int |= 0x0100;
- *(int*)arg = tmp_int;
- break;
-
- case BT848_SCBARS: /* set colorbar output */
- bt848[BKTR_COLOR_CTL] |= 0x40;
- break;
-
- case BT848_CCBARS: /* clear colorbar output */
- bt848[BKTR_COLOR_CTL] &= ~0x40;
- break;
-
-#if defined( AUDIO_SUPPORT )
- case BT848_SAUDIO: /* set audio channel */
- if ( set_audio( bktr, *(int*)arg ) < 0 )
- return EIO;
- break;
-
- case BT848_GAUDIO: /* get audio channel */
- temp = bktr->audio_mux_select;
- if ( bktr->audio_mute_state == TRUE )
- temp |= AUDIO_MUTE;
- *(int*)arg = temp;
- break;
-
- case BT848_SBTSC: /* set audio channel */
- if ( set_BTSC( bktr, *(int*)arg ) < 0 )
- return EIO;
- break;
-#endif /* AUDIO_SUPPORT */
-
case METEORSSIGNAL:
bktr->signal = *(int *) arg;
bktr->proc = pr;
@@ -1273,29 +1124,25 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
bktr->flags &= ~METEOR_WANT_MASK;
/* wait for capture to complete */
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = 0xffffffff;
-
- btl_reg = (u_long *) &bt848[BKTR_GPIO_OUT_EN];
- *btl_reg = 1;
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0x1;
- *bts_reg = bktr->capcontrol;
+ bt848->int_stat = 0xffffffff;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
+#if 0
+XXX why was this done???
+ bt848->gpio_out_en = 1;
+#endif
+ bt848->gpio_dma_ctl = 0x1;
+ bt848->gpio_dma_ctl = bktr->capcontrol;
- *btl_reg = 1 << 23 | 1 << 11 | 2 | 1;
+ bt848->int_mask = 1 << 23 | 1 << 11 | 2 | 1;
error=tsleep((caddr_t)bktr, METPRI, "capturing", hz);
if (error) {
- btl_reg = (u_long *) &bt848[BKTR_RISC_COUNT];
-
printf("bktr%d: ioctl: tsleep error %d %x\n",
- unit, error, *btl_reg);
+ unit, error, bt848->risc_count);
}
bktr->flags &= ~(METEOR_SINGLE|METEOR_WANT_MASK);
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
+ /* bt848->int_stat; ?? */
break;
case METEOR_CAP_CONTINOUS:
@@ -1306,16 +1153,12 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
return(EIO); /* already capturing */
start_capture(bktr, METEOR_CONTIN);
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = *btl_reg;
-
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
+ bt848->int_stat = bt848->int_stat;
- *bts_reg = 1;
- *bts_reg = bktr->capcontrol;
+ bt848->gpio_dma_ctl = 1;
+ bt848->gpio_dma_ctl = bktr->capcontrol;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 1 << 23 | 1 << 11 | 2 | 1;
+ bt848->int_mask = 1 << 23 | 1 << 11 | 2 | 1;
#if 0
dump_bt848( bt848 );
@@ -1326,12 +1169,10 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
case METEOR_CAP_STOP_CONT:
if (bktr->flags & METEOR_CONTIN) {
/* turn off capture */
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
- bts_reg = (u_short *)&bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
-
- bktr->flags &= ~(METEOR_CONTIN|METEOR_WANT_MASK);
+ bt848->int_mask = 0;
+ bt848->gpio_dma_ctl = 0;
+ bktr->flags &=
+ ~(METEOR_CONTIN|METEOR_WANT_MASK);
}
}
break;
@@ -1385,13 +1226,12 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
error = EINVAL;
}
- if (error) return error;
+ if (error)
+ return error;
bktr->dma_prog_loaded = 0;
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
+ bt848->gpio_dma_ctl = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 0;
+ bt848->int_mask = 0;
if (temp=geo->rows * geo->columns * geo->frames * 2) {
if (geo->oformat & METEOR_GEO_RGB24) temp = temp * 2;
@@ -1431,30 +1271,30 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
temp = ((910.0/( (float) bktr->cols *1.21875)) - 1.0) * 4096.0;
/* temp = ((754.0/(float) bktr->cols) - 1 ) * 4096.0;*/
- bt848[BKTR_E_HSCALE_LO] = temp & 0xff;
- bt848[BKTR_O_HSCALE_LO] = temp & 0xff;
- bt848[BKTR_E_HSCALE_HI] = ( temp >> 8 ) & 0xff;
- bt848[BKTR_O_HSCALE_HI] = ( temp >> 8 ) & 0xff;
+ bt848->e_hscale_lo = temp & 0xff;
+ bt848->o_hscale_lo = temp & 0xff;
+ bt848->e_hscale_hi = ( temp >> 8 ) & 0xff;
+ bt848->o_hscale_hi = ( temp >> 8 ) & 0xff;
/* horizontal active */
temp = bktr->cols;
- bt848[BKTR_E_HACTIVE_LO] = temp & 0xff;
- bt848[BKTR_O_HACTIVE_LO] = temp & 0xff;
- bt848[BKTR_EVEN_CROP] &= ~0x3;
- bt848[BKTR_ODD_CROP] &= ~0x3;
- bt848[BKTR_EVEN_CROP] |= (temp >> 8 ) & 0x3;
- bt848[BKTR_ODD_CROP] |= (temp >> 8 ) & 0x3;
+ bt848->e_hactive_lo = temp & 0xff;
+ bt848->o_hactive_lo = temp & 0xff;
+ bt848->e_crop &= ~0x3;
+ bt848->o_crop &= ~0x3;
+ bt848->e_crop |= (temp >> 8 ) & 0x3;
+ bt848->o_crop |= (temp >> 8 ) & 0x3;
/* horizontal delay */
temp = ((135.0/754.0) * (float) bktr->cols) ;
temp = temp + 2;
temp = temp & 0x3fe;
- bt848[BKTR_E_DELAY_LO] = temp & 0xff;
- bt848[BKTR_O_DELAY_LO] = temp & 0xff;
- bt848[BKTR_EVEN_CROP] &= ~0xc;
- bt848[BKTR_ODD_CROP] &= ~0xc;
- bt848[BKTR_EVEN_CROP] |= (temp >> 6) & 0xc;
- bt848[BKTR_ODD_CROP] |= (temp >> 6) & 0xc;
+ bt848->e_delay_lo = temp & 0xff;
+ bt848->o_delay_lo = temp & 0xff;
+ bt848->e_crop &= ~0xc;
+ bt848->o_crop &= ~0xc;
+ bt848->e_crop |= (temp >> 6) & 0xc;
+ bt848->o_crop |= (temp >> 6) & 0xc;
/* vscale */
if (geo->oformat & METEOR_GEO_ODD_ONLY ||
@@ -1466,12 +1306,12 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
tmp_int &= 0x1fff;
/* Vertical scaling */
- bt848[BKTR_E_VSCALE_LO] = tmp_int & 0xff;
- bt848[BKTR_O_VSCALE_LO] = tmp_int & 0xff;
- bt848[BKTR_E_VSCALE_HI] &= ~0x1f;
- bt848[BKTR_O_VSCALE_HI] &= ~0x1f;
- bt848[BKTR_E_VSCALE_HI] |= (tmp_int >> 8) & 0x1f;
- bt848[BKTR_O_VSCALE_HI] |= (tmp_int >> 8) & 0x1f;
+ bt848->e_vscale_lo = tmp_int & 0xff;
+ bt848->o_vscale_lo = tmp_int & 0xff;
+ bt848->e_vscale_hi &= ~0x1f;
+ bt848->o_vscale_hi &= ~0x1f;
+ bt848->e_vscale_hi |= (tmp_int >> 8) & 0x1f;
+ bt848->o_vscale_hi |= (tmp_int >> 8) & 0x1f;
bktr->format = METEOR_GEO_YUV_422;
switch (geo->oformat & METEOR_GEO_OUTPUT_MASK) {
@@ -1515,20 +1355,17 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
}
start_capture(bktr, METEOR_CONTIN);
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = *btl_reg;
- bts_reg = (u_short *)&bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0x1;
- *bts_reg = bktr->capcontrol;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 1 << 23 | 2 | 1;
+ bt848->int_stat = bt848->int_stat;
+ bt848->gpio_dma_ctl = 0x1;
+ bt848->gpio_dma_ctl = bktr->capcontrol;
+ bt848->int_mask = 1 << 23 | 2 | 1;
}
}
break;
/* end of METEORSETGEO */
default:
- return ENODEV;
+ return common_ioctl( bktr, bt848, cmd, arg );
}
return 0;
@@ -1536,6 +1373,312 @@ bktr_ioctl( dev_t dev, int cmd, caddr_t arg, int flag, struct proc *pr )
/*
+ * tuner ioctls
+ */
+static int
+tuner_ioctl( bktr_reg_t* bktr, int unit,
+ int cmd, caddr_t arg, struct proc* pr )
+{
+ bt848_reg_t bt848;
+ int status;
+ int tmp_int;
+ unsigned int temp, temp1;
+#if defined( EEPROM_SUPPORT )
+ int offset;
+ int count;
+ u_char *buf;
+#endif /* EEPROM_SUPPORT */
+
+ bt848 = bktr->base;
+
+ switch ( cmd ) {
+
+ case TVTUNER_SETCHNL:
+ tmp_int = bktr->audio_mute_state;
+ set_audio( bktr, AUDIO_MUTE ); /* prevent 'click' */
+ temp = tv_channel( bktr, (int)*(unsigned long *)arg );
+ tsleep((caddr_t)bktr, PZERO, "tuning", hz/8 );
+ if ( tmp_int == FALSE )
+ set_audio( bktr, AUDIO_UNMUTE );
+ if ( temp < 0 )
+ return EINVAL;
+ *(unsigned long *)arg = temp;
+ break;
+
+ case TVTUNER_GETCHNL:
+ *(unsigned long *)arg = bktr->tuner.channel;
+ break;
+
+ case TVTUNER_SETTYPE:
+ temp = *(unsigned long *)arg;
+ if ( (temp < CHNLSET_MIN) || (temp > CHNLSET_MAX) )
+ return EINVAL;
+ bktr->tuner.chnlset = temp;
+ break;
+
+ case TVTUNER_GETTYPE:
+ *(unsigned long *)arg = bktr->tuner.chnlset;
+ break;
+
+ case TVTUNER_GETSTATUS:
+ temp = i2cRead( bktr, TSA5522_RADDR );
+ *(unsigned long *)arg = temp & 0xff;
+ break;
+
+ case TVTUNER_SETFREQ:
+#if defined( AUDIO_SUPPORT_XXX )
+ tmp_int = bktr->audio_mute_state;
+ set_audio( bktr, AUDIO_MUTE ); /* prevent 'click' */
+#endif /* AUDIO_SUPPORT */
+ temp = tv_freq( bktr, (int)*(unsigned long *)arg );
+#if defined( AUDIO_SUPPORT_XXX )
+ tsleep((caddr_t)bktr, PZERO, "tuning", hz/8 );
+ if ( tmp_int == FALSE )
+ set_audio( bktr, AUDIO_UNMUTE );
+#endif /* AUDIO_SUPPORT */
+ if ( temp < 0 )
+ return EINVAL;
+ *(unsigned long *)arg = temp;
+ break;
+
+ case TVTUNER_GETFREQ:
+ *(unsigned long *)arg = bktr->tuner.frequency;
+ break;
+
+ case BT848_SAUDIO: /* set audio channel */
+ if ( set_audio( bktr, *(int*)arg ) < 0 )
+ return EIO;
+ break;
+
+ /* hue is a 2's compliment number, -90' to +89.3' in 0.7' steps */
+ case BT848_SHUE: /* set hue */
+ bt848->hue = (u_char)(*(int*)arg & 0xff);
+ break;
+
+ case BT848_GHUE: /* get hue */
+ *(int*)arg = (signed char)(bt848->hue & 0xff);
+ break;
+
+ /* brightness is a 2's compliment #, -50 to +%49.6% in 0.39% steps */
+ case BT848_SBRIG: /* set brightness */
+ bt848->bright = (u_char)(*(int *)arg & 0xff);
+ break;
+
+ case BT848_GBRIG: /* get brightness */
+ *(int *)arg = (signed char)(bt848->bright & 0xff);
+ break;
+
+ /* */
+ case BT848_SCSAT: /* set chroma saturation */
+ tmp_int = *(int*)arg;
+
+ temp = bt848->e_control & 0xfc;
+ temp1 = bt848->o_control & 0xfc;
+ if ( tmp_int & 0x100 ) {
+ temp |= 0x03;
+ temp1 |= 0x03;
+ }
+
+ bt848->sat_u_lo = (u_char)(tmp_int & 0xff);
+ bt848->sat_v_lo = (u_char)(tmp_int & 0xff);
+ bt848->e_control = temp;
+ bt848->o_control = temp1;
+ break;
+
+ case BT848_GCSAT: /* get chroma saturation */
+ tmp_int = (int)(bt848->sat_v_lo & 0xff);
+ if ( bt848->e_control & 0x01 )
+ tmp_int |= 0x0100;
+ *(int*)arg = tmp_int;
+ break;
+
+ /* */
+ case BT848_SVSAT: /* set chroma V saturation */
+ tmp_int = *(int*)arg;
+
+ temp = bt848->e_control & 0xfe;
+ temp1 = bt848->o_control & 0xfe;
+ if ( tmp_int & 0x100 ) {
+ temp |= 0x01;
+ temp1 |= 0x01;
+ }
+
+ bt848->sat_v_lo = (u_char)(tmp_int & 0xff);
+ bt848->e_control = temp;
+ bt848->o_control = temp1;
+ break;
+
+ case BT848_GVSAT: /* get chroma V saturation */
+ tmp_int = (int)bt848->sat_v_lo & 0xff;
+ if ( bt848->e_control & 0x01 )
+ tmp_int |= 0x0100;
+ *(int*)arg = tmp_int;
+ break;
+
+ /* */
+ case BT848_SUSAT: /* set chroma U saturation */
+ tmp_int = *(int*)arg;
+
+ temp = bt848->e_control & 0xfd;
+ temp1 = bt848->o_control & 0xfd;
+ if ( tmp_int & 0x100 ) {
+ temp |= 0x02;
+ temp1 |= 0x02;
+ }
+
+ bt848->sat_u_lo = (u_char)(tmp_int & 0xff);
+ bt848->e_control = temp;
+ bt848->o_control = temp1;
+ break;
+
+ case BT848_GUSAT: /* get chroma U saturation */
+ tmp_int = (int)bt848->sat_u_lo & 0xff;
+ if ( bt848->e_control & 0x02 )
+ tmp_int |= 0x0100;
+ *(int*)arg = tmp_int;
+ break;
+
+ /* */
+ case BT848_SCONT: /* set contrast */
+ tmp_int = *(int*)arg;
+
+ temp = bt848->e_control & 0xfb;
+ temp1 = bt848->o_control & 0xfb;
+ if ( tmp_int & 0x100 ) {
+ temp |= 0x04;
+ temp1 |= 0x04;
+ }
+
+ bt848->contrast_lo = (u_char)(tmp_int & 0xff);
+ bt848->e_control = temp;
+ bt848->o_control = temp1;
+ break;
+
+ case BT848_GCONT: /* get contrast */
+ tmp_int = (int)bt848->contrast_lo & 0xff;
+ if ( bt848->e_control & 0x04 )
+ tmp_int |= 0x0100;
+ *(int*)arg = tmp_int;
+ break;
+
+ case BT848_SCBARS: /* set colorbar output */
+ bt848->color_ctl |= 0x40;
+ break;
+
+ case BT848_CCBARS: /* clear colorbar output */
+ bt848->color_ctl &= ~0x40;
+ break;
+
+ case BT848_GAUDIO: /* get audio channel */
+ temp = bktr->audio_mux_select;
+ if ( bktr->audio_mute_state == TRUE )
+ temp |= AUDIO_MUTE;
+ *(int*)arg = temp;
+ break;
+
+ case BT848_SBTSC: /* set audio channel */
+ if ( set_BTSC( bktr, *(int*)arg ) < 0 )
+ return EIO;
+ break;
+
+#if defined( EEPROM_SUPPORT )
+ case BT848_WEEPROM: /* write eeprom */
+ return EINVAL;
+
+ case BT848_REEPROM: /* read eeprom */
+ offset = (((struct eeProm *)arg)->offset);
+ count = (((struct eeProm *)arg)->count);
+ buf = &(((struct eeProm *)arg)->bytes[ 0 ]);
+ if ( readEEProm( bktr, offset, count, buf ) < 0 )
+ return EIO;
+ break;
+#endif /* EEPROM_SUPPORT */
+
+ default:
+ return common_ioctl( bktr, bt848, cmd, arg );
+ }
+
+ return( 0 );
+}
+
+
+/*
+ * common ioctls
+ */
+int
+common_ioctl( bktr_reg_t* bktr, bt848_reg_t bt848, int cmd, caddr_t arg )
+{
+ int status;
+ unsigned int temp;
+
+ switch (cmd) {
+
+ case METEORSINPUT: /* set input device */
+ switch(*(unsigned long *)arg & METEOR_DEV_MASK) {
+
+ /* this is the RCA video input */
+ case 0: /* default */
+ case METEOR_INPUT_DEV0:
+ bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
+ | METEOR_DEV0;
+ bt848->iform &= ~0x60;
+ bt848->iform |= 0x60;
+ bt848->e_control &= ~0x40;
+ bt848->o_control &= ~0x40;
+ set_audio( bktr, AUDIO_EXTERN );
+ break;
+
+ /* this is the tuner input */
+ case METEOR_INPUT_DEV1:
+ bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
+ | METEOR_DEV1;
+ bt848->iform &= ~0x60;
+ bt848->iform |= 0x40;
+ bt848->e_control &= ~0x40;
+ bt848->o_control &= ~0x40;
+ set_audio( bktr, AUDIO_TUNER );
+ break;
+
+ /* this is the S-VHS input */
+ case METEOR_INPUT_DEV2:
+ case METEOR_INPUT_DEV_SVIDEO:
+ bktr->flags = (bktr->flags & ~METEOR_DEV_MASK)
+ | METEOR_DEV2;
+ bt848->iform &= ~0x60;
+ bt848->iform |= 0x20;
+ bt848->e_control |= 0x40;
+ bt848->o_control |= 0x40;
+ set_audio( bktr, AUDIO_EXTERN );
+ break;
+
+ default:
+ return EINVAL;
+ }
+ break;
+
+ case METEORGINPUT: /* get input device */
+ *(u_long *)arg = bktr->flags & METEOR_DEV_MASK;
+ break;
+
+#if defined( STATUS )
+ case BT848_GSTATUS: /* reap status */
+ disable_intr();
+ temp = status_sum;
+ status_sum = 0;
+ enable_intr();
+ *(u_int*)arg = temp;
+ break;
+#endif /* STATUS */
+
+ default:
+ return ENODEV;
+ }
+
+ return( 0 );
+}
+
+
+/*
*
*/
int
@@ -1546,9 +1689,10 @@ bktr_mmap( dev_t dev, int offset, int nprot )
unit = UNIT(minor(dev));
- if (unit >= NBKTR) /* at this point could this happen? */
+ if (unit >= NBKTR || minor(dev) > 0 ) /* at this point could this happen? */
return(-1);
+
bktr = &(brooktree[unit]);
if (nprot & PROT_EXEC)
@@ -1570,10 +1714,9 @@ bktr_mmap( dev_t dev, int offset, int nprot )
*
*/
static int
-dump_bt848( volatile u_char *bt848 )
+dump_bt848( bt848_reg_t bt848 )
{
- u_long *bt_long;
- u_short *bt_short;
+ volatile u_char *bt848r = (u_char *)bt848;
int r[60]={
4, 8, 0xc, 0x8c, 0x10, 0x90, 0x14, 0x94,
0x18, 0x98, 0x1c, 0x9c, 0x20, 0xa0, 0x24, 0xa4,
@@ -1586,20 +1729,15 @@ dump_bt848( volatile u_char *bt848 )
for (i = 0; i < 40; i+=4) {
printf(" Reg:value : \t%x:%x \t%x:%x \t %x:%x \t %x:%x\n",
- r[i], bt848[r[i]],
- r[i+1], bt848[r[i+1]],
- r[i+2], bt848[r[i+2]],
- r[i+3], bt848[r[i+3]]);
+ r[i], bt848r[r[i]],
+ r[i+1], bt848r[r[i+1]],
+ r[i+2], bt848r[r[i+2]],
+ r[i+3], bt848r[r[i+3]]);
}
- bt_long = (u_long *) &bt848[BKTR_INT_STAT];
- printf(" Reg 100 %x \n", *bt_long);
-
- bt_long = (u_long *) &bt848[BKTR_INT_MASK];
- printf(" Reg 104 %x \n", *bt_long);
-
- bt_long = (u_long *) &bt848[BKTR_GPIO_DMA_CTL];
- printf(" Reg 10C %x \n", *bt_long);
+ printf(" INT STAT %x \n", bt848->int_stat);
+ printf(" Reg INT_MASK %x \n", bt848->int_mask);
+ printf(" Reg GPIO_DMA_CTL %x \n", bt848->gpio_dma_ctl);
return 0;
}
@@ -1616,14 +1754,14 @@ dump_bt848( volatile u_char *bt848 )
#define BKTR_EOL 0x1
#define BKTR_SOL 0x2
-#define OP_WRITE 0x1 << 28
-#define OP_WRITEC 0x5 << 28
-#define OP_JUMP 0x7 << 28
-#define OP_SYNC 0x8 << 28
-#define OP_WRITE123 0x9 << 28
-#define OP_WRITES123 0xb << 28
-#define OP_SOL 1 << 27
-#define OP_EOL 1 << 26
+#define OP_WRITE (0x1 << 28)
+#define OP_WRITEC (0x5 << 28)
+#define OP_JUMP (0x7 << 28)
+#define OP_SYNC (0x8 << 28)
+#define OP_WRITE123 (0x9 << 28)
+#define OP_WRITES123 (0xb << 28)
+#define OP_SOL (1 << 27)
+#define OP_EOL (1 << 26)
static void
rgb_prog( bktr_reg_t * bktr, char i_flag, int cols,
@@ -1631,40 +1769,39 @@ rgb_prog( bktr_reg_t * bktr, char i_flag, int cols,
{
int i;
int byte_count;
+ bt848_reg_t bt848;
volatile unsigned int inst;
volatile unsigned int inst2;
volatile unsigned int inst3;
volatile u_long target_buffer, buffer;
- volatile u_char *bt848, *bt_reg;
- volatile u_short *bts_reg;
volatile u_long pitch;
- volatile u_long *dma_prog, *btl_reg, *t_test;
+ volatile u_long *dma_prog, *t_test;
int b, c;
bt848 = bktr->base;
/* color format : rgb32 */
if (bktr->depth == 4)
- bt848[BKTR_COLOR_FMT] = 0;
+ bt848->color_fmt = 0;
else
- bt848[BKTR_COLOR_FMT] = 0x33;
+ bt848->color_fmt = 0x33;
- bt848[BKTR_COLOR_CTL] = 0x40;
- bt848[BKTR_COLOR_CTL] = 0x10;
+ bt848->color_ctl = 0x40;
+ bt848->color_ctl = 0x10;
#if 0
- bt848[0x10] = 0x1C;
- bt848[0x90] = 0x1C;
+ bt848->e_vdelay_low = 0x1C;
+ bt848->o_vdelay_low = 0x1C;
#endif
- bt848[BKTR_VBI_PACK_SIZE] = 0;
- bt848[BKTR_VBI_PACK_DEL] = 0;
+ bt848->vbi_pack_size = 0;
+ bt848->vbi_pack_del = 0;
- bt848[BKTR_ADC] = 0x81;
- bt848[BKTR_COLOR_CTL] = 0x20;
+ bt848->adc = SYNC_LEVEL;
+ bt848->color_ctl = 0x20;
- bt848[BKTR_E_VSCALE_HI] |= 0xc0;
- bt848[BKTR_O_VSCALE_HI] |= 0xc0;
+ bt848->e_vscale_hi |= 0xc0;
+ bt848->o_vscale_hi |= 0xc0;
bktr->capcontrol = 3 << 2 | 3;
@@ -1775,21 +1912,20 @@ yuvpack_prog( bktr_reg_t *bktr, char i_flag,
volatile unsigned int inst2;
volatile unsigned int inst3;
volatile u_long target_buffer, buffer;
- volatile u_char *bt848, *bt_reg;
- volatile u_short *bts_reg;
- volatile u_long *dma_prog, *btl_reg;
+ bt848_reg_t bt848;
+ volatile u_long *dma_prog;
int b;
bt848 = bktr->base;
/* color format : yuvpack */
- bt848[BKTR_COLOR_FMT] = 0x44;
+ bt848->color_fmt = 0x44;
- bt848[BKTR_E_SCLOOP] |= 0x40; /* enable chroma comb */
- bt848[BKTR_O_SCLOOP] |= 0x40;
+ bt848->e_scloop |= 0x40; /* enable chroma comb */
+ bt848->o_scloop |= 0x40;
- bt848[BKTR_COLOR_CTL] = 0x30;
- bt848[BKTR_ADC] = 0x81;
+ bt848->color_ctl = 0x30;
+ bt848->adc = SYNC_LEVEL;
bktr->capcontrol = 1 << 6 | 1 << 4 | 1 << 2 | 3;
bktr->capcontrol = 1 << 5 | 1 << 4 | 1 << 2 | 3;
@@ -1900,9 +2036,8 @@ yuv422_prog( bktr_reg_t * bktr, char i_flag,
volatile unsigned int instskip, instskip2, instskip3;
volatile unsigned int inst3;
volatile u_long target_buffer, t1, buffer;
- volatile u_char *bt848, *bt_reg;
- volatile u_short *bts_reg;
- volatile u_long *dma_prog, *btl_reg;
+ bt848_reg_t bt848;
+ volatile u_long *dma_prog;
int b, b1;
bt848 = bktr->base;
@@ -1910,21 +2045,21 @@ yuv422_prog( bktr_reg_t * bktr, char i_flag,
bktr->capcontrol = 1 << 6 | 1 << 4 | 3;
- bt848[BKTR_ADC] = 0x81 ;
- bt848[BKTR_OFORM] = 0x00;
+ bt848->adc = SYNC_LEVEL;
+ bt848->oform = 0x00;
- bt848[BKTR_E_CONTROL] |= 0x20; /* disable luma decimation */
- bt848[BKTR_O_CONTROL] |= 0x20;
+ bt848->e_control |= 0x20; /* disable luma decimation */
+ bt848->o_control |= 0x20;
- bt848[BKTR_E_SCLOOP] |= 0x40; /* chroma agc enable */
- bt848[BKTR_O_SCLOOP] |= 0x40;
+ bt848->e_scloop |= 0x40; /* chroma agc enable */
+ bt848->o_scloop |= 0x40;
- bt848[BKTR_E_VSCALE_HI] |= 0xc0; /* luma comb and comb enable */
- bt848[BKTR_O_VSCALE_HI] |= 0xc0;
+ bt848->e_vscale_hi |= 0xc0; /* luma comb and comb enable */
+ bt848->o_vscale_hi |= 0xc0;
- bt848[BKTR_COLOR_FMT] = 0x88;
+ bt848->color_fmt = 0x88;
- bt848[BKTR_COLOR_CTL] = 0x10; /* disable gamma correction */
+ bt848->color_ctl = 0x10; /* disable gamma correction */
bt_enable_cnt = 0;
@@ -2019,45 +2154,40 @@ build_dma_prog( bktr_reg_t * bktr, char i_flag )
volatile unsigned int inst2;
volatile unsigned int inst3;
volatile u_long target_buffer;
- volatile u_char *bt848, *bt_reg;
- volatile u_short *bts_reg;
- volatile u_long *dma_prog, *btl_reg;
+ bt848_reg_t bt848;
+ volatile u_long *dma_prog;
int b;
bt848 = bktr->base;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK] ;
- *btl_reg = 0;
-
- bts_reg = (u_short * ) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg &= ~3;
+ bt848->int_mask = 0;
+ bt848->gpio_dma_ctl &= ~3;
/* capture control */
switch (i_flag) {
case 1:
bktr->bktr_cap_ctl = 0x11;
- bt848[BKTR_CAP_CTL] = 0x11;
- bt848[BKTR_E_VSCALE_HI] &= ~0x20;
- bt848[BKTR_O_VSCALE_HI] &= ~0x20;
+ bt848->cap_ctl = 0x11;
+ bt848->e_vscale_hi &= ~0x20;
+ bt848->o_vscale_hi &= ~0x20;
interlace = 1;
break;
case 2:
bktr->bktr_cap_ctl = 0x12;
- bt848[BKTR_CAP_CTL] = 0x12;
- bt848[BKTR_E_VSCALE_HI] &= ~0x20;
- bt848[BKTR_O_VSCALE_HI] &= ~0x20;
+ bt848->cap_ctl = 0x12;
+ bt848->e_vscale_hi &= ~0x20;
+ bt848->o_vscale_hi &= ~0x20;
interlace = 1;
break;
default:
bktr->bktr_cap_ctl = 0x13;
- bt848[BKTR_CAP_CTL] = 0x13;
- bt848[BKTR_E_VSCALE_HI] |= 0x20;
- bt848[BKTR_O_VSCALE_HI] |= 0x20;
+ bt848->cap_ctl = 0x13;
+ bt848->e_vscale_hi |= 0x20;
+ bt848->o_vscale_hi |= 0x20;
interlace = 2;
break;
}
- btl_reg = (u_long *) &bt848[BKTR_RISC_STRT_ADD] ;
- *btl_reg = vtophys(bktr->dma_prog);
+ bt848->risc_strt_add = vtophys(bktr->dma_prog);
pixel_width = bktr->depth;
rows = bktr->rows;
@@ -2094,15 +2224,13 @@ build_dma_prog( bktr_reg_t * bktr, char i_flag )
static void
start_capture( bktr_reg_t *bktr, unsigned type )
{
- volatile u_char *bt848, *bt_reg, i_flag;
- volatile u_short *bts_reg;
- volatile u_long *btl_reg;
+ bt848_reg_t bt848;
+ u_char i_flag;
- bt848 = (u_char *) bktr->base;
+ bt848 = bktr->base;
- *bt848 = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = *btl_reg;
+ bt848->dstatus = 0;
+ bt848->int_stat = bt848->int_stat;
bktr->flags |= type;
switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
@@ -2128,16 +2256,14 @@ start_capture( bktr_reg_t *bktr, unsigned type )
/*XXX
switch(bktr->flags & METEOR_ONLY_FIELDS_MASK) {
default:
- *bts_reg |= 0xb;
+ *bts_reg |= 0xb; bts_reg never been initialized!
}
*/
- btl_reg = (u_long *) &bt848[BKTR_RISC_STRT_ADD];
- *btl_reg = vtophys(bktr->dma_prog);
+ bt848->risc_strt_add = vtophys(bktr->dma_prog);
/*XXX
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0x3;
+ bt848->gpio_dma_ctl = 0x3;
*/
}
@@ -2148,39 +2274,31 @@ start_capture( bktr_reg_t *bktr, unsigned type )
static void
set_fps( bktr_reg_t *bktr, u_short fps )
{
- volatile u_char *bt848, *bt_reg;
- volatile u_long *btl_reg;
- volatile u_short *bts_reg;
+ bt848_reg_t bt848;
- bt848 = (u_char *) bktr->base;
+ bt848 = bktr->base;
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 0;
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = 0xffffffff;
+ bt848->gpio_dma_ctl = 0;
+ bt848->int_stat = 0xffffffff;
bktr->fps = fps;
if ( fps == 30 ) {
- bt848[BKTR_TDEC] = 0;
+ bt848->tdec = 0;
return;
} else {
- bt848[BKTR_TDEC] = (int) (((float) fps / 30.0) * 60.0) & 0x3f;
- bt848[BKTR_TDEC] |= 0x80;
+ bt848->tdec = (int) (((float) fps / 30.0) * 60.0) & 0x3f;
+ bt848->tdec |= 0x80;
}
if ( bktr->flags & METEOR_CAP_MASK ) {
- btl_reg = (u_long *) &bt848[BKTR_INT_STAT];
- *btl_reg = 0xffffffff;
- btl_reg = (u_long *) &bt848[BKTR_RISC_STRT_ADD];
- *btl_reg = vtophys(bktr->dma_prog);
+ bt848->int_stat = 0xffffffff;
+ bt848->risc_strt_add = vtophys(bktr->dma_prog);
- bts_reg = (u_short *) &bt848[BKTR_GPIO_DMA_CTL];
- *bts_reg = 1;
- *bts_reg = bktr->capcontrol;
- btl_reg = (u_long *) &bt848[BKTR_INT_MASK];
- *btl_reg = 1 << 11 | 2 | 1;
+ bt848->gpio_dma_ctl = 1;
+ bt848->gpio_dma_ctl = bktr->capcontrol;
+ bt848->int_mask = 1 << 11 | 2 | 1;
}
return;
@@ -2221,198 +2339,192 @@ get_bktr_mem( int unit, unsigned size )
* i2c primitives:
*/
-/* delays for the I2C bus transactions */
-#define NDELAY 0
-#if defined ( ORIGINAL_DELAYS )
-#define SDELAY 2
-#define LDELAY 20
-#else
-#define SDELAY 10
-#define LDELAY 40
-#endif /* ORIGINAL_DELAYS */
-/* macros to show the details more clearly */
typedef volatile u_long* i2c_regptr_t;
+#define I2C_REGADDR() ((i2c_regptr_t)&bktr->base->i2c_data_ctl)
+
+#define RACK (1 << 25)
+#define I2CDONE (1 << 8)
+#define I2CDIV (0x0f << 4)
+#define I2CBITTIME (0x05 << 4)
+#define I2CSYNC (0x01 << 3)
+#define I2CW3B (0x01 << 2)
+#define I2CSCL (0x01 << 1)
+#define I2CSDA (0x01 << 0)
+#define I2C_READ 0x01
+#define I2C_COMMAND (I2CBITTIME | I2CSCL | I2CSDA)
/*
- * primitives for the I2C clock phases
+ *
*/
-static inline void
-DataLo_ClockLo( i2c_regptr_t bti2c, int delay )
-{
- *bti2c = 0;
- if ( delay )
- DELAY( delay );
-}
-static inline void
-DataHi_ClockLo( i2c_regptr_t bti2c, int delay )
+static int
+i2cWrite( bktr_reg_t *bktr, int addr, int byte1, int byte2 )
{
- *bti2c = 1;
- if ( delay )
- DELAY( delay );
-}
+ u_long x;
+ u_long data;
+ i2c_regptr_t bti2c;
-static inline void
-DataLo_ClockHi( i2c_regptr_t bti2c, int delay )
-{
- *bti2c = 2;
- if ( delay )
- DELAY( delay );
-}
+ /* setup register addresses */
+ bti2c = I2C_REGADDR();
-static inline void
-DataHi_ClockHi( i2c_regptr_t bti2c, int delay )
-{
- *bti2c = 3;
- if ( delay )
- DELAY( delay );
-}
+ /* clear status bits */
+ bktr->base->int_stat = (RACK | I2CDONE);
-static inline int
-DataRead( i2c_regptr_t bti2c )
-{
- return ( *bti2c & 1 );
-}
+ /* build the command datum */
+ data = ((addr & 0xff) << 24) | ((byte1 & 0xff) << 16) | I2C_COMMAND;
+ if ( byte2 != -1 ) {
+ data |= ((byte2 & 0xff) << 8);
+ data |= I2CW3B;
+ }
+
+ /* write the address and data */
+ *bti2c = data;
+
+ /* wait for completion */
+ for ( x = 0xffffffff; x; --x ) { /* safety valve */
+ if ( bktr->base->int_stat & I2CDONE )
+ break;
+ }
+
+ /* check for ACK */
+ if ( !x || !(bktr->base->int_stat & RACK) )
+ return -1;
+ /* return OK */
+ return 0;
+}
-/* forward reference */
-static int i2cWrite( i2c_regptr_t, u_char );
/*
- * start an I2C bus transaction
+ *
*/
static int
-i2cStart( i2c_regptr_t bti2c, int address )
+i2cRead( bktr_reg_t *bktr, int addr )
{
-#if defined( EXTRA_START )
- /* ensure the proper starting state */
- DataHi_ClockLo( bti2c, LDELAY ); /* release data */
- DataHi_ClockHi( bti2c, LDELAY ); /* release clock */
-#endif /* EXTRA_START */
+ u_long x;
+ i2c_regptr_t bti2c;
- DataLo_ClockHi( bti2c, LDELAY ); /* lower data */
- DataLo_ClockLo( bti2c, LDELAY ); /* lower clock */
+ /* setup register addresses */
+ bti2c = I2C_REGADDR();
- /* send the address of the device */
- return i2cWrite( bti2c, address );
-}
+ /* clear status bits */
+ bktr->base->int_stat = (RACK | I2CDONE);
-/*
- * stop an I2C bus transaction
- */
-static void
-i2cStop( i2c_regptr_t bti2c )
-{
- DELAY( LDELAY );
- DataLo_ClockLo( bti2c, LDELAY ); /* lower clock & data */
- DataLo_ClockHi( bti2c, LDELAY ); /* release clock */
- DataHi_ClockHi( bti2c, LDELAY ); /* release data */
-}
+ /* write the READ address */
+ *bti2c = ((addr & 0xff) << 24) | I2C_COMMAND;
-/*
- * place a '1' bit on the I2C bus
- */
-static void
-i2cHi( i2c_regptr_t bti2c )
-{
- DataHi_ClockLo( bti2c, LDELAY ); /* assert HI data */
- DataHi_ClockHi( bti2c, LDELAY ); /* strobe clock */
- DataHi_ClockLo( bti2c, LDELAY ); /* release clock */
-}
+ /* wait for completion */
+ for ( x = 0xffffffff; x; --x ) { /* safety valve */
+ if ( bktr->base->int_stat & I2CDONE )
+ break;
+ }
-/*
- * place a '0' bit on the I2C bus
- */
-static void
-i2cLo( i2c_regptr_t bti2c )
-{
- DataLo_ClockLo( bti2c, LDELAY ); /* assert LO data */
- DataLo_ClockHi( bti2c, LDELAY ); /* strobe clock */
- DataLo_ClockLo( bti2c, LDELAY ); /* release clock */
+ /* check for ACK */
+ if ( !(bktr->base->int_stat & RACK) )
+ return -1;
+
+ /* it was a read */
+ return (*bti2c >> 8) & 0xff;
}
+
+#if defined( I2C_SOFTWARE_PROBE )
+
/*
- * give an 'ACK' to the slave
+ * we are keeping this around for any parts that we need to probe
+ * but that CANNOT be probed via an i2c read.
+ * this is necessary because the hardware i2c mechanism
+ * cannot be programmed for 1 byte writes.
+ * currently there are no known i2c parts that we need to probe
+ * and that cannot be safely read.
*/
-static void
-i2cGrantAck( i2c_regptr_t bti2c )
-{
- DataLo_ClockLo( bti2c, LDELAY ); /* assert LO data */
- DataLo_ClockHi( bti2c, LDELAY ); /* strobe clock */
- DataLo_ClockLo( bti2c, LDELAY ); /* remove clock */
- DataHi_ClockLo( bti2c, NDELAY ); /* float data */
-}
+static int i2cProbe( i2c_regptr_t bti2c, int addr );
+#define BITDELAY 40
+#define EXTRA_START
/*
- * get an 'ACK' from the slave
+ * probe for an I2C device at addr.
*/
static int
-i2cAck( i2c_regptr_t bti2c )
+i2cProbe( i2c_regptr_t bti2c, int addr )
{
- int acknowledge;
+ int x, status;
- DataHi_ClockLo( bti2c, LDELAY ); /* float data */
- DataHi_ClockHi( bti2c, LDELAY ); /* strobe clock */
+ /* the START */
+#if defined( EXTRA_START )
+ *bti2c = 1; DELAY( BITDELAY ); /* release data */
+ *bti2c = 3; DELAY( BITDELAY ); /* release clock */
+#endif /* EXTRA_START */
+ *bti2c = 2; DELAY( BITDELAY ); /* lower data */
+ *bti2c = 0; DELAY( BITDELAY ); /* lower clock */
+
+ /* write addr */
+ for ( x = 7; x >= 0; --x ) {
+ if ( addr & (1<<x) ) {
+ *bti2c = 1; DELAY( BITDELAY ); /* assert HI data */
+ *bti2c = 3; DELAY( BITDELAY ); /* strobe clock */
+ *bti2c = 1; DELAY( BITDELAY ); /* release clock */
+ }
+ else {
+ *bti2c = 0; DELAY( BITDELAY ); /* assert LO data */
+ *bti2c = 2; DELAY( BITDELAY ); /* strobe clock */
+ *bti2c = 0; DELAY( BITDELAY ); /* release clock */
+ }
+ }
- acknowledge = DataRead( bti2c ); /* read ACK bit */
+ /* look for an ACK */
+ *bti2c = 1; DELAY( BITDELAY ); /* float data */
+ *bti2c = 3; DELAY( BITDELAY ); /* strobe clock */
+ status = *bti2c & 1; /* read the ACK bit */
+ *bti2c = 1; DELAY( BITDELAY ); /* release clock */
- DataHi_ClockLo( bti2c, LDELAY ); /* release clock */
+ /* the STOP */
+ *bti2c = 0; DELAY( BITDELAY ); /* lower clock & data */
+ *bti2c = 2; DELAY( BITDELAY ); /* release clock */
+ *bti2c = 3; DELAY( BITDELAY ); /* release data */
- return acknowledge;
+ return status;
}
+#undef EXTRA_START
+#undef BITDELAY
-/*
- * read a byte from the I2C bus
- */
-static int
-i2cRead( i2c_regptr_t bti2c, int ack )
-{
- int x;
- int byte;
-
- DataHi_ClockLo( bti2c, SDELAY ); /* float data */
-
- for ( byte = 0, x = 7; x >= 0; --x ) {
- DataHi_ClockHi( bti2c, SDELAY ); /* strobe clock */
-
- if ( DataRead( bti2c ) ) /* read data */
- byte |= (1<<x); /* bit was Hi */
+#endif /* I2C_SOFTWARE_PROBE */
- DataHi_ClockLo( bti2c, SDELAY ); /* release clock */
- }
-#if defined( FUNNY_HI )
- i2cHi( bti2c );
-#endif /* FUNNY_HI */
-#if defined( REALLY_ACK )
- if ( ack )
- i2cGrantAck( bti2c ); /* Grant ACK */
-#endif /* REALLY_ACK */
- return byte;
-}
+#if defined( EEPROM_SUPPORT )
-/*
- * write a byte to the I2C bus
- */
static int
-i2cWrite( i2c_regptr_t bti2c, u_char byte )
+readEEProm( bktr_reg_t* bktr, int offset, int count, u_char *data )
{
- int x;
+ int x;
+ int addr;
+ int max;
+ int byte;
- DataLo_ClockLo( bti2c, LDELAY ); /* lower data & clock */
+ /* get the address of the EEProm */
+ addr = (int)(bktr->card->eepromAddr & 0xff);
+ if ( addr == 0 )
+ return -1;
- for ( x = 7; x >= 0; --x )
- (byte & (1<<x)) ? i2cHi( bti2c ) : i2cLo( bti2c );
+ max = (int)(bktr->card->eepromSize * EEPROMBLOCKSIZE);
+ if ( (offset + count) > max )
+ return -1;
- return i2cAck( bti2c );
-}
+ /* set the start address */
+ if ( i2cWrite( bktr, addr, offset, -1 ) == -1 )
+ return -1;
-#undef NDELAY
-#undef SDELAY
-#undef LDELAY
+ /* the read cycle */
+ for ( x = 0; x < count; ++x ) {
+ if ( (byte = i2cRead( bktr, (addr | 1) )) == -1 )
+ return -1;
+ data[ x ] = byte;
+ }
+ return 0;
+}
-#define I2C_REGADDR() (i2c_regptr_t)&bktr->base[ BKTR_I2C_CONTROL ]
+#endif /* EEPROM_SUPPORT */
/******************************************************************************
@@ -2420,26 +2532,9 @@ i2cWrite( i2c_regptr_t bti2c, u_char byte )
*/
-/* guaranteed address for any TSA5522 (PLL on all(?) tuners) */
-#define TSA5522_WADDR 0xc2
-#define TSA5522_RADDR 0xc3
-
-/* address of BTSC/SAP decoder chip */
-#define TDA9850_WADDR 0xb6
-#define TDA9850_RADDR 0xb7
-
-/* EEProm (128 * 8) on an STB card */
-#define X24C01_WADDR 0xae
-#define X24C01_RADDR 0xaf
-
-/* EEProm (256 * 8) on a Hauppauge card */
-#define PFC8582_WADDR 0xa0
-#define PFC8582_RADDR 0xa1
-
/*
* the data for each type of card
*/
-
#define NO_TUNER 0
#define TEMIC_TUNER 1
#define PHILIPS_TUNER 2
@@ -2455,33 +2550,44 @@ struct CARDTYPE card_types[] = {
{ "Unknown",
NO_TUNER,
0,
+ 0,
+ 0,
{ 0, 0, 0, 0 } },
/* CARD_MIRO */
{ "Miro TV",
NO_TUNER, /** TEMIC_TUNER ??? */
0,
+ 0,
+ 0,
{ 0x02, 0x01, 0x00, 0x00 } }, /* XXX ??? */
/* CARD_HAUPPAUGE */
{ "Hauppauge WinCast/TV",
PHILIPS_TUNER,
0,
+ PFC8582_WADDR,
+ (u_char)(256 / EEPROMBLOCKSIZE), /* 256 bytes */
{ 0x00, 0x02, 0x01, 0x01 } },
/* CARD_STB */
{ "STB TV/PCI",
TEMIC_TUNER,
0,
+ X24C01_WADDR,
+ (u_char)(128 / EEPROMBLOCKSIZE), /* 128 bytes */
{ 0x00, 0x01, 0x02, 0x02 } },
/* CARD_INTEL */
{ "Intel Smart Video III",
NO_TUNER,
0,
+ 0,
+ 0,
{ 0, 0, 0, 0 } }
};
+
/*
* If probe_card() fails to detect the proper card on boot you can
* override it by setting the following define to the card you are using:
@@ -2490,95 +2596,76 @@ struct CARDTYPE card_types[] = {
*
* where <card type> is one of the card defines in the above array.
*/
-#define PRESENT 0
-#define ABSENT 1
+#define ABSENT (-1)
static int
probe_card( bktr_reg_t *bktr, int verbose )
{
- i2c_regptr_t bti2c;
- int status;
+ int status;
#if defined( OVERRIDE_CARD )
bktr->card_type = OVERRIDE_CARD;
+ bktr->card = &(card_types[ bktr->card_type ]);
goto end;
#endif
- /* get the i2c register address */
- bti2c = I2C_REGADDR();
/* look for a tuner */
- status = i2cStart( bti2c, TSA5522_WADDR );
- i2cStop( bti2c );
- if ( status == ABSENT ) {
+ if ( i2cRead( bktr, TSA5522_RADDR ) == ABSENT ) {
bktr->card_type = CARD_INTEL;
+ bktr->card = &(card_types[ bktr->card_type ]);
goto checkDBX;
}
/* look for a hauppauge card */
- status = i2cStart( bti2c, PFC8582_WADDR );
- i2cStop( bti2c );
- if ( status == PRESENT ) {
+ if ( (status = i2cRead( bktr, PFC8582_RADDR )) != ABSENT ) {
bktr->card_type = CARD_HAUPPAUGE;
+ bktr->card = &(card_types[ bktr->card_type ]);
goto checkTuner;
}
/* look for an STB card */
- status = i2cStart( bti2c, X24C01_WADDR );
- i2cStop( bti2c );
- if ( status == PRESENT ) {
+ if ( (status = i2cRead( bktr, X24C01_RADDR )) != ABSENT ) {
bktr->card_type = CARD_STB;
+ bktr->card = &(card_types[ bktr->card_type ]);
goto checkTuner;
}
/* XXX FIXME: (how do I) look for a Miro card */
bktr->card_type = CARD_MIRO;
+ bktr->card = &(card_types[ bktr->card_type ]);
checkTuner:
- /**
- * XXX FIXME: how can we differentiate TEMIC vs. PHILIPS tuners ???
- */
- status = i2cStart( bti2c, 0xc0 );
- i2cStop( bti2c );
- if ( status == PRESENT ) {
- card_types[ bktr->card_type ].tuner = TEMIC_TUNER;
+ /* differentiate TEMIC vs. PHILIPS tuners */
+ if ( i2cRead( bktr, TEMIC_TSA5522_RADDR ) != ABSENT ) {
+ bktr->card->tuner = TEMIC_TUNER;
goto checkDBX;
}
- status = i2cStart( bti2c, 0xc6 );
- i2cStop( bti2c );
- if ( status == PRESENT ) {
- card_types[ bktr->card_type ].tuner = PHILIPS_TUNER;
+ if ( i2cRead( bktr, PHILIPS_TSA5523_RADDR ) != ABSENT ) {
+ bktr->card->tuner = PHILIPS_TUNER;
goto checkDBX;
}
- card_types[ bktr->card_type ].tuner = NO_TUNER;
+ /* no tuner found */
+ bktr->card->tuner = NO_TUNER;
checkDBX:
- /*
- * probe for BTSC (dbx) chips.
- */
- status = i2cStart( bti2c, TDA9850_WADDR );
- i2cStop( bti2c );
- if ( status == PRESENT )
- card_types[ bktr->card_type ].dbx = 1;
+ /* probe for BTSC (dbx) chips */
+ if ( i2cRead( bktr, TDA9850_RADDR ) != ABSENT )
+ bktr->card->dbx = 1;
end:
if ( verbose ) {
- printf( "%s", card_types[ bktr->card_type ].name );
-
- if ( card_types[ bktr->card_type ].tuner )
- printf( ", %s tuner",
- card_types[ bktr->card_type ].tuner
- == TEMIC_TUNER ? "Temic" : "Philips" );
-
- if ( card_types[ bktr->card_type ].dbx )
+ printf( "%s", bktr->card->name );
+ if ( bktr->card->tuner )
+ printf( ", %s tuner", bktr->card->tuner ==
+ TEMIC_TUNER ? "Temic" : "Philips" );
+ if ( bktr->card->dbx )
printf( ", dbx stereo" );
-
printf( "\n" );
}
return bktr->card_type;
}
#undef ABSENT
-#undef PRESENT
#define TSA5522_BANDA band_addrs[card_types[bktr->card_type].tuner-1][0]
@@ -2773,28 +2860,16 @@ tv_freq( bktr_reg_t* bktr, int frequency )
*/
N = frequency + TBL_IF;
- /* get the i2c register address */
- bti2c = I2C_REGADDR();
-
- /* send the data to the TSA5522 */
- i2cStart( bti2c, TSA5522_WADDR );
-
- /* the data sheet wants the order set according to direction */
if ( frequency > bktr->tuner.frequency ) {
- i2cWrite( bti2c, (N >> 8) & 0x7f ); /* divisor MSB */
- i2cWrite( bti2c, N & 0xff ); /* divisor LSB */
- i2cWrite( bti2c, TSA5522_CONTROL ); /* control bits */
- i2cWrite( bti2c, band ); /* band select */
+ i2cWrite( bktr, TSA5522_WADDR, (N>>8) & 0x7f, N & 0xff );
+ i2cWrite( bktr, TSA5522_WADDR, TSA5522_CONTROL, band );
}
else {
- i2cWrite( bti2c, TSA5522_CONTROL ); /* control bits */
- i2cWrite( bti2c, band ); /* band select */
- i2cWrite( bti2c, (N >> 8) & 0x7f ); /* divisor MSB */
- i2cWrite( bti2c, N & 0xff ); /* divisor LSB */
+ i2cWrite( bktr, TSA5522_WADDR, TSA5522_CONTROL, band );
+ i2cWrite( bktr, TSA5522_WADDR, (N>>8) & 0x7f, N & 0xff );
}
- i2cStop( bti2c );
-
+ /* update frequency */
bktr->tuner.frequency = frequency;
return 0;
@@ -2825,30 +2900,6 @@ tv_channel( bktr_reg_t* bktr, int channel )
}
-/*
- * get the status of the tuner
- */
-static int
-tuner_status( bktr_reg_t* bktr )
-{
- i2c_regptr_t bti2c;
- int status;
-
- /* get the i2c register address */
- bti2c = I2C_REGADDR();
-
- /* send the request to the TSA5522 */
- i2cStart( bti2c, TSA5522_RADDR );
-
- status = i2cRead( bti2c, 0 ); /* no ACK */
-
- i2cStop( bti2c );
-
- return status;
-}
-
-
-#if defined( AUDIO_SUPPORT )
/******************************************************************************
* audio specific routines:
*/
@@ -2861,8 +2912,8 @@ tuner_status( bktr_reg_t* bktr )
static int
set_audio( bktr_reg_t *bktr, int cmd )
{
- volatile u_char *bt848;
- volatile u_char temp;
+ bt848_reg_t bt848;
+ u_long temp;
volatile u_char idx;
#if defined( AUDIOMUX_DISCOVER )
@@ -2899,28 +2950,25 @@ set_audio( bktr_reg_t *bktr, int cmd )
* something like the dbx or teletext chips. This doesn't guarantee
* success, but follows the rule of least astonishment.
*/
- bt848[BKTR_GPIO_OUT_EN] = 0x07; /* drive low 3 bits */
- bt848[BKTR_GPIO_REG_INP] = 0xf8; /* read state of others */
-#if defined( AUDIOMUX_DISCOVER )
- printf("cmd: %d\n", cmd );
-
- temp = bt848[BKTR_GPIO_DATA] & ~7;
- bt848[BKTR_GPIO_DATA] = temp | (cmd & 0xff);
-
- return 0;
-#endif /* AUDIOMUX_DISCOVER */
+ /* this was an 8 bit reference before ?? */
+ bt848->gpio_reg_inp = (~GPIO_AUDIOMUX_BITS & 0xff);
if ( bktr->audio_mute_state == TRUE )
idx = 3;
else
idx = bktr->audio_mux_select;
- temp = bt848[BKTR_GPIO_DATA] & ~7; /* mask off lower three bits */
- bt848[BKTR_GPIO_DATA] =
- temp | card_types[bktr->card_type].audiomuxs[idx];
+ temp = bt848->gpio_data & ~GPIO_AUDIOMUX_BITS;
+ bt848->gpio_data =
+#if defined( AUDIOMUX_DISCOVER )
+ bt848->gpio_data = temp | (cmd & 0xff);
+ printf("cmd: %d\n", cmd );
+#else
+ temp | bktr->card->audiomuxs[ idx ];
+#endif /* AUDIOMUX_DISCOVER */
- return 0;
+ return( 0 );
}
@@ -2935,29 +2983,8 @@ set_audio( bktr_reg_t *bktr, int cmd )
static int
set_BTSC( bktr_reg_t *bktr, int control )
{
- i2c_regptr_t bti2c;
-
- /* get the i2c register address */
- bti2c = I2C_REGADDR();
-
- /* send the data to the TDA9850 BTSC */
- if ( i2cStart( bti2c, TDA9850_WADDR ) )
- goto fubar;
-
- if ( i2cWrite( bti2c, CON3ADDR ) )
- goto fubar;
-
- if ( i2cWrite( bti2c, control ) )
- goto fubar;
-
- i2cStop( bti2c );
- return 0;
-
- fubar:
- i2cStop( bti2c );
- return -1;
+ return i2cWrite( bktr, TDA9850_WADDR, CON3ADDR, control );
}
-#endif /* AUDIO_SUPPORT */
/******************************************************************************
@@ -2982,3 +3009,14 @@ bktr_drvinit( void *unused )
SYSINIT(bktrdev,SI_SUB_DRIVERS,SI_ORDER_MIDDLE+CDEV_MAJOR,bktr_drvinit,NULL)
#endif /* NBKTR > 0 */
+
+/* Local Variables: */
+/* mode: C */
+/* c-indent-level: 8 */
+/* c-brace-offset: -8 */
+/* c-argdecl-indent: 8 */
+/* c-label-offset: -8 */
+/* c-continued-statement-offset: 8 */
+/* c-tab-always-indent: nil */
+/* End: */
+
OpenPOWER on IntegriCloud