Mailing List archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[linux-dvb] Re: cinergyT2: which kernel/usb module to use?



Klaus Schmidinger wrote:

Holger Waechtler wrote:

> ...

The entire idea of caching pasttime events in a ringbuffer was bogus, do you know any use for this? Your code contains a race condition that can show up at particular combinations of CPU speed and status update rates. Maybe only a theoretical one but in any case an example for bad programming.


The correct implementation is this:

while (!exit) {
select(fd, ...);
ioctl(fd, FE_READ_STATUS, &status);
/* process/display status */
};


Select what? If the driver sees an event so it can wake up poll(),
it surely can generate a frontend event, no?
Certainly it is valid to call FE_READ_STATUS instead of looking
at the event retrieved with FE_GET_EVENT, but the API guarantees
that FE_GET_EVENT will also give you the tuning status.

a pasttime event, yes. But who cares about the lockbit status some while ago?

Holger

Back when I did some experimenting in that area it looked as if
FE_READ_STATUS would return an FE_HAS_LOCK _immediately_ after tuning (presumably
the status bits were still at the value they had vefore tuning),

the concept is simple: FE_READ_STATUS always reflects the currect lock bits. Tuning is in any case asynchronous, you can loose lock at every time (especially for weak signals, mostly in DVB-T environments). Commercial STBs often have one or more LED-alike lock-indicators in their OSD, updated every few fractions of a second. The proposed implementation is trivial:

open(frontend_fd);
while (!exit) {
select(frontend_fd, timeout = e.g. 0.2sec);
/* now a status bits have changed or we are arrived at the end of the signal quality indicator interval */
/* let's read the current demod device status */
if (ioctl(frontend_fd, FE_READ_STATUS, &status) == 0) {
/* display lock bits somewhere in OSD */
}
if (ioctl(frontend_fd, FE_READ_UNC, &status) == 0) {
/* display BER somewhere in OSD if enabled */
}
if (ioctl(frontend_fd, FE_READ_BER, &status) == 0) {
/* display number of uncorrected blocks somewhere in OSD if enabled */
}
/**
* same for all other statistics, maybe it makes sense to merge the result
* of the ioctls in a single progress bar status, e.g.:
* UNC > 0: yellow/red small dot, the more UNC the more red
* UNC = 0: green bar, length inversely proportional to BER, zero BER means maximum length
* or anything similiar.
*/
/* redraw OSD */
};
close(frontend_fd);

well... this is one way to implement it -- there are many others. The above is in my opinion just the most simple and robust one.

although the lock clearly wasn't there yet. Also, checking with FE_READ_STATUS
periodically indicated that every now and then the lock was _lost_, although
the signal was displayed load and clear. The FE_GET_EVENT way appeared
to be much more stable and reliable.

For which demod? Since the FE_GET_EVENT implementation was based on FE_READ_STATUS this is unlikely and would indicate a bug in the dvb_frontend.c code...

Holger





Home | Main Index | Thread Index