/************************************************************************* * Copyright 2009/2010/2011 Ralph Spitzner (rasp@spitzner.org) * * This file is part of v2Yahdr. * * v2Yahdr 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 3 of the License, or * (at your option) any later version. * * Yahdr 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 v2Yahdr. If not, see . **************************************************************************/ #include "ydefs.h" #define RET_ERR() {sqlite3_finalize(stmt); return false; } static int demux_fd,video_fd,audio_fds[8]; static struct dvb_frontend_parameters fe_parm; static struct dmx_pes_filter_params pesfilter; //static struct dvb_frontend_info fe_info; static uint16_t vpid,apids[8]; static uint8_t adapter; static void close_fds() { int i; if(demux_fd > 0) demux_fd = close(demux_fd); if(video_fd > 0) video_fd = close(video_fd); for(i = 0; i != 8; i++) { if(audio_fds[i] > 0) audio_fds[i] = close(audio_fds[i]); } } static void telldvr(uint8_t anum) { int i; bzero(&pids,sizeof(pids)); /// pids are in dvr.c pids[0] = vpid; for(i = 0; i != 8; i++) pids[1+i] = apids[i]; printf("PIDS:"); for(i = 0; i != 10; i++) printf("%d ",pids[i]); printf("\n"); printf("cdvr %d anum %d\n",cdvr,anum); cdvr = anum; printf("cdvr %d anum %d\n",cdvr,anum); //pthread_kill(tspipepid,SIGPIPE); } /*** if req_adapter != 0, just tune specified adapter whether busy or not..... ***/ bool tuneto(char *name) { int i; char buffer[255]; ADAPTER *adp; SERVICE *esp; APID *apidp; PRG *prgp; TRANSPORT *tsp; SERVICE *p_service[8]; TRANSPORT *p_transport[8]; int maxl; bool found; bzero(apids,sizeof(apids)); INFO("tune to:>%s<\n",name); esp = services; adp = adapters; found = false; bzero(p_service,sizeof(p_service)); bzero(p_transport,sizeof(p_transport)); maxl = 0; tsp = NULL; while(esp) { if(!(strcmp(esp->name,name))) { tsp = transports; while(tsp) { if(tsp->tsid == esp->tsid) { adp = adapters; while(adp) { if((adp->number == tsp->adapter)) { /// check ca cap if(esp->ca == 1) { if(!(adp->pref & HAS_CA) || adp->busy) { adp = adp->next; continue; } found = true; break; } else if(adp->busy == false) { found = true; break; } } adp = adp->next; } } if(found == false) { tsp = tsp->next; } else { break; } } } if(found == false) { esp = esp->next; } else { break; } } if(esp == NULL) { return false; } prgp = programs; while(prgp) { if((prgp->s_id == esp->s_id) && (prgp->tsid == esp->tsid)) { break; } prgp = prgp->next; } if(prgp == NULL) { return false; } vpid = prgp->vpid; apidp = apid_l; i = 0; while(apidp) { if((apidp->tsid == prgp->tsid) && (apidp->ppid == prgp->ppid)) { apids[i] = apidp->pid; i++; if(i == 8) { break; } } apidp = apidp->next; } bzero(&fe_parm,sizeof(struct dvb_frontend_parameters)); bzero(&pesfilter,sizeof(struct dmx_pes_filter_params)); tuned_ts.adp = adp; tuned_ts.prgp = prgp; tuned_ts.tsp = tsp; tuned_ts.sp = esp; tuned_ts.apidp = apidp; telldvr(adp->number); sleep(1); close_fds(); switch(adp->type) { case TERR: fe_parm.inversion = INVERSION_AUTO; fe_parm.u.ofdm.code_rate_HP =FEC_3_4; fe_parm.u.ofdm.code_rate_LP = FEC_AUTO; fe_parm.u.ofdm.constellation = QAM_AUTO; //16; // ?? fe_parm.u.ofdm.transmission_mode = TRANSMISSION_MODE_AUTO;//8K; fe_parm.u.ofdm.guard_interval = GUARD_INTERVAL_AUTO;//1_8; fe_parm.u.ofdm.bandwidth = tsp->bw == 7 ? BANDWIDTH_7_MHZ : BANDWIDTH_8_MHZ ; break; case CABLE: fe_parm.inversion = INVERSION_AUTO; fe_parm.u.qam.fec_inner = FEC_AUTO; fe_parm.u.qam.symbol_rate = 6900000; fe_parm.u.qam.modulation = tsp->qam; break; default: printf("Unknown adapter type %d\n",adp->type); return false; } fe_parm.frequency = tsp->freq; sprintf(buffer,"/dev/dvb/adapter%d/frontend0",adp->number); printf("tuning %s\n",buffer); if(adp->fe_fd == 0) { adp->fe_fd = open(buffer,O_RDWR); if(adp->fe_fd <= 0) { printf("adapter frontend %d ",adapter); perror(buffer); return false; } } if (ioctl(adp->fe_fd, FE_SET_FRONTEND, &fe_parm) < 0) { printf("frontend adapter %d ",adapter); perror("ioctl FE_SET_FRONTEND failed"); return false; } if(check_frontend (adp->fe_fd,8) == false) { printf("check frontent failed\n"); return false; } /// tuned to frequncy, set filter PIDs //getchar(); sprintf(buffer,"/dev/dvb/adapter%d/demux0",adp->number); video_fd = open(buffer,O_RDWR); if(prgp->vpid != 0) { if(video_fd <= 0) { perror("set video fd"); return false; } pesfilter.pid = vpid; pesfilter.input = DMX_IN_FRONTEND; pesfilter.output = DMX_OUT_TS_TAP; pesfilter.pes_type = DMX_PES_VIDEO; pesfilter.flags = DMX_IMMEDIATE_START; if(ioctl(video_fd,DMX_SET_PES_FILTER,&pesfilter) < 0) { perror("video ioctl"); return false; } } ///open audio fds, set filter for(i=0; i != 8; i++) { if(apids[i] != 0) { audio_fds[i] = open(buffer,O_RDWR); if(audio_fds[i] <= 0) { perror("set audio fd(s)"); return false; } pesfilter.pid = apids[i]; pesfilter.input = DMX_IN_FRONTEND; pesfilter.output = DMX_OUT_TS_TAP; pesfilter.pes_type = i == 1 ? DMX_PES_AUDIO : DMX_PES_OTHER; pesfilter.flags = DMX_IMMEDIATE_START; if(ioctl(audio_fds[i],DMX_SET_PES_FILTER,&pesfilter) < 0) { perror("audio ioctl"); return false; } } else break; } return true; }