Andrew de Quincey wrote:
On Friday 10 Sep 2004 11:02, John Dalgliesh wrote:
On Fri, 10 Sep 2004, Andrew de Quincey wrote:
On Thursday 09 Sep 2004 23:41, Gerd Knorr wrote:
Just hope there isn't a card out there with both DVB AND analogue
tuners on it....
class isn't a value but a bitmask, so you can actually say the card
can do both analog and digital tv ...
Ah right cool. Eurgh, nasty problem waiting down the line when those
cards Holger mentioned appear.
I don't think I understand the condition you are worried about. Do you
mean that the card has to have two separate (i2c-addressable) tuners, one
for analogue and one for digital? Or would a card that has one tuner that
does both like <http://www.dvico.com/products_mul_hd3.html> be a worry?
Just wondering :)
If the card is marked as both analogue and digital, and happens to use
one of the i2c addresses which several devices use, you could end up with
the wrong i2c device associated with the wrong device - e.g. the tda9987
(analogue tuner) driver was being used incorrectly as the driver for the
cx22702 (digtial demodulator) because they both commonly reside at the
same i2c address. And theres no way to detect the tda9887 more
specifically.
Gah, if only Philips had mandated that all i2c devices must have a unique
32 bit identifier!
The i2c bus is well-designed for this particular purpose, it is the API
that does not matches the reality.
i2c devices are usually dumb tiny special chips that do a very special
job, which heavily depend on the hardware around them and how everything
is wired together. Not really the environment where autoprobing is a
good idea.
And there is no urge doing anything so complicated at all: all
infrastructure we need are two simple functions for every card's
i2c/SPI/8bit-parallel/whatever uC bus:
int card->uC_write(u8 addr, const u8 *buf, int len);
int card->uC_read(u8 addr, u8 *buf, int len);
This is enough to implement the access functions for a particular device:
#define DEVICE_ADDR XXX
static
int device_writereg (u8 reg, u8 val)
{
u8 buf [] = { reg, val };
return card->uC_write(DEVICE_ADDR, buf, sizeof(buf));
}
static
int device_readreg (u8 reg, u8 *val)
{
u8 buf [] = { reg };
int ret;
if ((ret = card->uC_write(DEVICE_ADDR, buf, sizeof(buf))))
return ret;
return card->uC_read(DEVICE_ADDR, val, 1);
}
These function pointers are passed to the frontend_spec struct (e.g.
mt312_cardspec) and from there together with the card-specific constants
and initialisation tables to the "frontend library" functions.