From: Dave Schmitz <[EMAIL PROTECTED]>

> I was curious to know if anyone is using both video tuning and FM
> tuning in the same (bttv) app.

Does not work with e.g. one hauppauge card. It has only one tuner and
cant tune both, tv and fm.

> I was wondering what the best approach is to use both devices.
> Do I need to close the /dev/video0 and open /dev/radio0 and vice
> versa when switching between functionality?

> Is there a way to open both devices? 

Hm. Depends on the hardware. I've an extra radio card and both devices
dont know each other, of course. But with the same tuner on a grabber
card...  Maybe you could select some other (tunerless) input for video
and use the radio part of that card... Try or ask Gerd... (-:

> Also, I've noticed a ioctl called VIDIOCGUNIT which is suppose to
> "obtain related devices if a driver has multiple components". What
> is this information used for?  

Good question. I tried my litte C code (attached) on various /dev/xyz 
with bttv 0.7.x. Only /dev/video0 reported something - very usefull to
find relationships form /dev/radioX to user things...

I wanted to write some radio app that time...

Okay, run my piece of C. It's for v4l1. The output here for /dev/radio
shows the behavior of "my" miropcm20 driver....


Bye,
        Robert

bash-2.05$ ./v4l-test /dev/radio
Found Miro PCM20, which has 1 channel(s).
Unable to check for related units...      <---------
Sorry, this device is unable to answer on VIDIOGCHAN for channel 0...
Setting to channel 0.
VIDIOCSCHAN failed. (This is normal...)
Tuner0 (FM): low: 87.000, high: 108.000
 current frequency (97.150): stereo RDS (auto)
 signal:48059
Audio0 (Radio): mode: mono stereo 
 flags: unmuted balance:-32768 step:0


/*
 * Copyright (C) 2000  Robert Siemer <[EMAIL PROTECTED]>
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or (at
 * your option) any later version.
 *
 * This program is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
 * USA.
 */

#define _GNU_SOURCE

#include <stdio.h>
#include <fcntl.h>
#include <unistd.h>
#include <errno.h>
#include <sys/ioctl.h>
#include <linux/videodev.h>

typedef struct {
        unsigned int freq;
        unsigned int signal;
        unsigned int stereo :1;
        unsigned int rds    :1;
} station;


int main (int argc, char *argv[])
{
        int fd, i;
        struct video_capability vcap;
        struct video_unit       vu;
        struct video_channel    vchan;
        struct video_tuner      vt;
        unsigned long           freq;
        struct video_audio      va;

        if (argc==0)
                return 1;

        fd=open(argv[1], O_RDONLY);
        if (fd<0) {
                perror(program_invocation_short_name);
                return 1;
        }

        if (ioctl(fd, VIDIOCGCAP, &vcap)<0) {
                perror(program_invocation_short_name);
                return 1;
        }

        if (vcap.type&VID_TYPE_TUNER && !vcap.type&VID_TYPE_CAPTURE &&
            !vcap.type&VID_TYPE_OVERLAY)
                printf("Hmmm, does not look like a radio card - but I don't"
                       " care... [:\n");

        if (vcap.audios!=1)
                printf("Aehm, what does it mean: this device has %d"
                       " audio devices...\n", vcap.audios);

        printf("Found %s, which has %d channel(s).\n", vcap.name,
               vcap.channels);
        
        if (ioctl(fd, VIDIOCGUNIT, &vu)<0)
                printf("Unable to check for related units...\n");
        else
                printf("video:%d vbi:%d radio:%d audio:%d teletext:%d\n",
                       vu.video, vu.vbi, vu.radio, vu.audio, vu.teletext);

        for (vchan.channel=0; vchan.channel<vcap.channels; vchan.channel++) {
                if (ioctl(fd, VIDIOCGCHAN, &vchan)<0) {
                        printf("Sorry, this device is unable to answer on"
                               " VIDIOGCHAN for channel %d...\n",
                               vchan.channel);
                        continue;
                }
                printf("Channel%d (%s): ", vchan.channel, vchan.name);
                if (vchan.tuners<1 && !(vchan.flags&VIDEO_VC_TUNER)) {
                        printf("no tuner --> no radio\n");
                        continue;
                }
                if ((vchan.tuners<1 && vchan.flags&VIDEO_VC_TUNER) ||
                    (vchan.tuners>=1 && !(vchan.flags&VIDEO_VC_TUNER)))
                        printf("device is unsure about having some (%d)"
                               " tuners on this channel...\n", vchan.tuners);
                if (vchan.type&VIDEO_TYPE_TV || vchan.type&VIDEO_TYPE_CAMERA
                    || !(vchan.flags&VIDEO_VC_AUDIO)) {
                        printf("A radio has audio and no tv/camera input. "
                               "This is not true here...\n");
                        continue;
                }
                printf("\n");
                break;
        }

        if (vchan.channel==vcap.channels) vchan.channel=0, vchan.tuners=1;
        printf("Setting to channel %d.\n", vchan.channel);
        if (ioctl(fd, VIDIOCSCHAN, &vchan)<0) {
                printf("VIDIOCSCHAN failed. (This is normal...)\n");
                }

        for (vt.tuner=0; vt.tuner<vchan.tuners; vt.tuner++) {
                if (ioctl(fd, VIDIOCGTUNER, &vt)<0) {
                        printf("ioctl() problem with tuner %d.\n", vt.tuner);
                        continue;
                        }
                printf("Tuner%d (%s): ", vt.tuner, vt.name);
                i=(vt.flags&VIDEO_TUNER_LOW)? 16000 : 16;
                printf("low: %.3f, high: %.3f\n",
                       (double)vt.rangelow/i, (double)vt.rangehigh/i);
                if (ioctl(fd, VIDIOCSTUNER, &vt)<0 ||
                    ioctl(fd, VIDIOCGFREQ, &freq)<0) {
                        printf("Sorry, this tuner is just fucked up...\n");
                        continue;
                        }
                printf(" current frequency (%.3f): ", (double)freq/i);
                if (vt.flags&VIDEO_TUNER_STEREO_ON)
                        printf("stereo ");
                if (vt.flags&VIDEO_TUNER_RDS_ON)
                        printf("RDS ");
                if (vt.mode&VIDEO_MODE_AUTO)
                        printf("(auto)");
                printf("\n");
                printf(" signal:%d\n", vt.signal);
        }


        for (va.audio=0; va.audio<vcap.audios; va.audio++) {
                if (ioctl(fd, VIDIOCGAUDIO, &va)<0) {
                        printf("ioctl() problem with audio %d.\n", va.audio);
                        continue;
                }
                printf("Audio%d (%s): ", va.audio, va.name);
                printf("mode: ");
                if (va.mode&VIDEO_SOUND_MONO)
                        printf("mono ");
                if (va.mode&VIDEO_SOUND_STEREO)
                        printf("stereo ");
                if (va.mode&VIDEO_SOUND_LANG1)
                        printf("lang1 ");
                if (va.mode&VIDEO_SOUND_LANG2)
                        printf("lang2");
                printf("\n");
                printf(" flags: ");
                if (va.flags&VIDEO_AUDIO_MUTABLE) {
                        if (va.flags&VIDEO_AUDIO_MUTE)
                                printf("muted ");
                        else
                                printf("unmuted ");
                }
                if (va.flags&VIDEO_AUDIO_VOLUME)
                        printf("volume:%d ", va.volume);
                if (va.flags&VIDEO_AUDIO_BASS)
                        printf("bass:%d ", va.bass);
                if (va.flags&VIDEO_AUDIO_TREBLE)
                        printf("treble:%d ", va.treble);
                printf("balance:%d step:%d\n", va.balance-32768, va.step);
        }
        return 0;
}

Reply via email to