OSDN Git Service

add dist
[rec10/rec10-git.git] / dist / trunk / tstools / tunerec / tunerec.c
diff --git a/dist/trunk/tstools/tunerec/tunerec.c b/dist/trunk/tstools/tunerec/tunerec.c
new file mode 100755 (executable)
index 0000000..a42c146
--- /dev/null
@@ -0,0 +1,191 @@
+#include <linux/dvb/frontend.h>
+#include <linux/dvb/dmx.h>
+#include <linux/dvb/audio.h>
+#include <linux/dvb/version.h>
+#include <sys/ioctl.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <time.h>
+
+#define ARRAY_SIZE(arr) (sizeof(arr) / sizeof((arr)[0]))
+
+struct channel {
+       int id;
+       const char *name;
+       unsigned int frequency;
+       unsigned int ts_id;
+};
+static int search(int adapter_nr,struct channel *ch)
+{
+       char file[256];
+       int fd;
+       struct dvb_frontend_info info;
+       struct channel *channel;
+       struct dtv_property prop[3];
+       struct dtv_properties props;
+       int i;
+       fe_status_t status;
+
+       sprintf(file, "/dev/dvb/adapter%d/frontend0", adapter_nr);
+       if ((fd = open(file, (O_RDWR | O_CREAT | O_TRUNC), 0666)) < 0) {
+               perror("open");
+               return -1;
+       }
+
+       if (ioctl(fd, FE_GET_INFO, &info) < 0) {
+               perror("ioctl FE_GET_INFO");
+               goto out;
+       }
+
+       if (info.type == FE_QPSK) {
+               channel = ch;
+               //channel = lookup_channel(channel_id, isdbs_channels,
+               //                       ARRAY_SIZE(isdbs_channels));
+       } else if (info.type == FE_OFDM) {
+               channel = ch;
+               //channel = lookup_channel(channel_id, isdbt_channels,
+               //                       ARRAY_SIZE(isdbt_channels));
+       } else {
+               fprintf(stderr, "Unknown type of adapter\n");
+               goto out;
+       }
+       if (channel == NULL) {
+               fprintf(stderr, "Unknown id of channel\n");
+               goto out;
+       }
+
+       prop[0].cmd = DTV_FREQUENCY;
+       prop[0].u.data = channel->frequency;
+       prop[1].cmd = DTV_ISDBS_TS_ID;
+       prop[1].u.data = channel->ts_id;
+       prop[2].cmd = DTV_TUNE;
+
+       props.props = prop;
+       props.num = 3;
+
+       if ((ioctl(fd, FE_SET_PROPERTY, &props)) < 0) {
+               perror("ioctl FE_SET_PROPERTY");
+               goto out;
+       }
+
+       for (i = 0; i < 4; i++) {
+               if (ioctl(fd, FE_READ_STATUS, &status) < 0) {
+                       perror("ioctl FE_READ_STATUS");
+                       goto out;
+               }
+               if (status & FE_HAS_LOCK) {
+                       fprintf(stderr, "Successfully tuned to %d(%d) .\n",
+                               channel->frequency,channel->ts_id);
+                       return 0;
+               }
+               usleep(250 * 1000);
+       }
+
+       fprintf(stderr, "Failed to tune to %s (status %02x).\n",
+               channel->name, status);
+
+out:
+       close(fd);
+       return -1;
+}
+
+static int track(int adapter_nr)
+{
+       char file[256];
+       int fd;
+       struct dmx_pes_filter_params filter;
+
+       filter.pid = 0x2000;
+       filter.input = DMX_IN_FRONTEND;
+       filter.output = DMX_OUT_TS_TAP;
+       filter.pes_type =  DMX_PES_VIDEO;
+       filter.flags = DMX_IMMEDIATE_START;
+
+       sprintf(file, "/dev/dvb/adapter%d/demux0", adapter_nr);
+       if ((fd = open(file, O_RDWR)) < 0) {
+               perror("open");
+               return -1;
+       }
+
+
+       if (ioctl(fd, DMX_SET_PES_FILTER, &filter) < 0) {
+               perror("ioctl DMX_SET_PES_FILTER");
+               close(fd);
+               return -1;
+       }
+}
+
+void record(int adapter_nr, char* output, int rectime) {
+       int fin, fout;
+       char input[256];
+       time_t start_time, current_time;
+       char buf[1316];
+       ssize_t rt, wt;
+       int size_remain;
+
+       fout = open(output, (O_WRONLY | O_CREAT | O_TRUNC));
+       if ( fout < 0 ) {
+               printf("output file open failed\n");
+               return;
+       }
+       sprintf(input, "/dev/dvb/adapter%d/dvr0", adapter_nr);
+       start_time = time(NULL);
+       fin = open(input, (O_RDONLY));
+       while ( rt = read(fin, buf, 1316) ) {
+               while ( wt = write(fout, buf, rt) ) {
+                       rt -= wt;
+                       if ( rt == 0 ) break;
+                       if ( wt == 0 ) {
+                               printf("output file write failed\n");
+                               goto error;
+                       }
+               }
+               current_time = time(NULL);
+               if ( current_time - start_time > rectime ) {
+                       break;
+               }
+       }
+
+       error:
+       close(fin);
+       close(fout);
+}
+
+int main(int argc, char *argv[]) {
+       int adapter_nr;
+       int channel_id;
+       int channel_freq;
+       int fd;
+       int ret;
+       int rectime;
+
+       if (argc <= 2) {
+               fprintf(stderr, "Usage: %s adapter_nr freq [tsid]\n", argv[0]);
+               return 1;
+       }
+       struct channel *ch;
+       adapter_nr = strtol(argv[1], NULL, 0);
+       channel_freq = strtol(argv[2], NULL, 10);
+       channel_id=0;
+       if (argc >= 4){
+               channel_id = strtol(argv[3], NULL, 10);
+       }
+       if ( argc >= 5 ) {
+               rectime = atoi(argv[4]);
+       }
+       struct channel ch1 ={0,"",channel_freq,channel_id};
+       ch = &ch1;
+       //struct channel ch;//{   1, "NHK BS-1",          1318000, 0x40f1 }
+       //ch={0,"",argv}
+       fd = search(adapter_nr, ch);
+       if (fd < 0)
+               return 1;
+
+       ret = track(adapter_nr);
+       record(adapter_nr, argv[5], rectime);
+       close(fd);
+
+       return ret < 0;
+}