From: Felix Domke Date: Wed, 17 Aug 2005 02:16:32 +0000 (+0000) Subject: - add iSeekableService, implement it for serviceDvb X-Git-Tag: 2.6.0~5726 X-Git-Url: https://git.cweiske.de/enigma2.git/commitdiff_plain/0af11516cabc973907890f548925a66313c8d18c - add iSeekableService, implement it for serviceDvb --- diff --git a/lib/dvb/demux.cpp b/lib/dvb/demux.cpp index bdd8e67d..3e05065b 100644 --- a/lib/dvb/demux.cpp +++ b/lib/dvb/demux.cpp @@ -59,6 +59,38 @@ RESULT eDVBDemux::getMPEGDecoder(ePtr &decoder) return 0; } +RESULT eDVBDemux::getSTC(pts_t &pts) +{ + char filename[128]; +#if HAVE_DVB_API_VERSION < 3 + sprintf(filename, "/dev/dvb/card%d/demux%d", adapter, demux); +#else + sprintf(filename, "/dev/dvb/adapter%d/demux%d", adapter, demux); +#endif + int fd = ::open(filename, O_RDWR); + + if (fd < 0) + return -ENODEV; + + struct dmx_stc stc; + stc.num = 0; + stc.base = 1; + + if (ioctl(fd, DMX_GET_STC, &stc) < 0) + { + ::close(fd); + return -1; + } + + pts = stc.stc; + eDebug("got demux stc: %08llx", pts); + + ::close(fd); + + return 0; +} + + void eDVBSectionReader::data(int) { __u8 data[4096]; // max. section size diff --git a/lib/dvb/demux.h b/lib/dvb/demux.h index fdec4177..23aef0f3 100644 --- a/lib/dvb/demux.h +++ b/lib/dvb/demux.h @@ -21,6 +21,7 @@ public: RESULT createSectionReader(eMainloop *context, ePtr &reader); RESULT createTSRecorder(ePtr &recorder); RESULT getMPEGDecoder(ePtr &reader); + RESULT getSTC(pts_t &pts); }; class eDVBSectionReader: public iDVBSectionReader, public Object diff --git a/lib/dvb/dvb.cpp b/lib/dvb/dvb.cpp index cfb32d09..3e4c7bdc 100644 --- a/lib/dvb/dvb.cpp +++ b/lib/dvb/dvb.cpp @@ -552,14 +552,39 @@ RESULT eDVBChannel::getLength(pts_t &len) RESULT eDVBChannel::getCurrentPosition(pts_t &pos) { -#if 0 off_t begin = 0; /* getPTS for offset 0 is cached, so it doesn't harm. */ int r = m_tstools.getPTS(begin, pos); if (r) + { + eDebug("tstools getpts(0) failed!"); return r; + } + + pts_t now; + + r = m_demux->get().getSTC(now); + + if (r) + { + eDebug("demux getSTC failed"); + return -1; + } + + eDebug("STC: %08llx PTS: %08llx, diff %lld", now, pos, now - pos); + + /* when we are less than 10 seconds before the start, return 0. */ + /* (we're just waiting for the timespam to start) */ + if ((now < pos) && ((pos - now) < 90000 * 10)) + { + pos = 0; + return 0; + } + + if (now < pos) /* wrap around */ + pos = now + ((pts_t)1)<<33 - pos; + else + pos = now - pos; - // DMX_GET_STC -#endif return 0; } diff --git a/lib/dvb/idvb.h b/lib/dvb/idvb.h index 518525f9..683a7b71 100644 --- a/lib/dvb/idvb.h +++ b/lib/dvb/idvb.h @@ -459,7 +459,7 @@ public: /* so this is VERY UGLY. */ virtual RESULT playFile(const char *file) = 0; - virtual RESULT getLength(pts_t &len) = 0; + virtual RESULT getLength(pts_t &pts) = 0; virtual RESULT getCurrentPosition(pts_t &pos) = 0; // seekTo ... @@ -475,6 +475,7 @@ public: virtual RESULT createSectionReader(eMainloop *context, ePtr &reader)=0; virtual RESULT createTSRecorder(ePtr &recorder)=0; virtual RESULT getMPEGDecoder(ePtr &reader)=0; + virtual RESULT getSTC(pts_t &pts)=0; }; class iTSMPEGDecoder: public iObject diff --git a/lib/dvb/pmt.cpp b/lib/dvb/pmt.cpp index 541a248c..e62de9b8 100644 --- a/lib/dvb/pmt.cpp +++ b/lib/dvb/pmt.cpp @@ -168,6 +168,15 @@ int eDVBServicePMTHandler::getDemux(ePtr &demux) return -1; } +int eDVBServicePMTHandler::getPVRChannel(ePtr &pvr_channel) +{ + pvr_channel = m_pvr_channel; + if (pvr_channel) + return 0; + else + return -1; +} + int eDVBServicePMTHandler::tune(eServiceReferenceDVB &ref) { RESULT res; diff --git a/lib/dvb/pmt.h b/lib/dvb/pmt.h index 9d35aa4c..efe54ee7 100644 --- a/lib/dvb/pmt.h +++ b/lib/dvb/pmt.h @@ -66,6 +66,7 @@ public: int getProgramInfo(struct program &program); int getDemux(ePtr &demux); + int getPVRChannel(ePtr &pvr_channel); int tune(eServiceReferenceDVB &ref); }; diff --git a/lib/dvb/tstools.h b/lib/dvb/tstools.h index a50ab441..4ec4b66a 100644 --- a/lib/dvb/tstools.h +++ b/lib/dvb/tstools.h @@ -1,6 +1,7 @@ #ifndef __lib_dvb_tstools_h #define __lib_dvb_tstools_h +#include #include /* diff --git a/lib/service/iservice.h b/lib/service/iservice.h index 61695a91..4a19378c 100644 --- a/lib/service/iservice.h +++ b/lib/service/iservice.h @@ -1,6 +1,7 @@ #ifndef __lib_dvb_iservice_h #define __lib_dvb_iservice_h +#include #include #include #include @@ -177,6 +178,16 @@ public: TEMPLATE_TYPEDEF(ePtr, iPauseableServicePtr); +class iSeekableService: public iObject +{ +public: + virtual RESULT getLength(pts_t &SWIG_OUTPUT)=0; + virtual RESULT seekTo(pts_t to)=0; + virtual RESULT getPlayPosition(pts_t &SWIG_OUTPUT)=0; +}; + +TEMPLATE_TYPEDEF(ePtr, iSeekableServicePtr); + class iPlayableService: public iObject { friend class iServiceHandler; @@ -192,6 +203,7 @@ public: virtual RESULT connectEvent(const Slot2 &event, ePtr &connection)=0; virtual RESULT start()=0; virtual RESULT stop()=0; + virtual RESULT seek(ePtr &ptr)=0; virtual RESULT pause(ePtr &ptr)=0; virtual RESULT info(ePtr &ptr)=0; }; diff --git a/lib/service/servicedvb.cpp b/lib/service/servicedvb.cpp index 955ceb0a..ac224562 100644 --- a/lib/service/servicedvb.cpp +++ b/lib/service/servicedvb.cpp @@ -313,9 +313,14 @@ void eDVBServicePlay::serviceEvent(int event) // how we can do this better? // update cache pid when the user changed the audio track or video track // TODO handling of difference audio types.. default audio types.. - m_dvb_service->setCachePID(eDVBService::cVPID, vpid); - m_dvb_service->setCachePID(eDVBService::cAPID, apid); - m_dvb_service->setCachePID(eDVBService::cPCRPID, pcrpid); + + /* don't worry about non-existing services, nor pvr services */ + if (m_dvb_service && !m_is_pvr) + { + m_dvb_service->setCachePID(eDVBService::cVPID, vpid); + m_dvb_service->setCachePID(eDVBService::cAPID, apid); + m_dvb_service->setCachePID(eDVBService::cPCRPID, pcrpid); + } } break; @@ -325,9 +330,10 @@ void eDVBServicePlay::serviceEvent(int event) RESULT eDVBServicePlay::start() { + int r; eDebug("starting DVB service"); + r = m_service_handler.tune((eServiceReferenceDVB&)m_reference); m_event(this, evStart); - return m_service_handler.tune((eServiceReferenceDVB&)m_reference); } RESULT eDVBServicePlay::stop() @@ -349,6 +355,46 @@ RESULT eDVBServicePlay::pause(ePtr &ptr) return -1; } +RESULT eDVBServicePlay::seek(ePtr &ptr) +{ + if (m_is_pvr) + { + ptr = this; + return 0; + } + + ptr = 0; + return -1; +} + +RESULT eDVBServicePlay::getLength(pts_t &len) +{ + ePtr pvr_channel; + + if (m_service_handler.getPVRChannel(pvr_channel)) + { + eDebug("getPVRChannel failed!"); + return -1; + } + + return pvr_channel->getLength(len); +} + +RESULT eDVBServicePlay::seekTo(pts_t to) +{ + return -1; +} + +RESULT eDVBServicePlay::getPlayPosition(pts_t &pos) +{ + ePtr pvr_channel; + + if (m_service_handler.getPVRChannel(pvr_channel)) + return -1; + + return pvr_channel->getCurrentPosition(pos); +} + RESULT eDVBServicePlay::info(ePtr &ptr) { ptr = this; diff --git a/lib/service/servicedvb.h b/lib/service/servicedvb.h index 78444158..1dd66e40 100644 --- a/lib/service/servicedvb.h +++ b/lib/service/servicedvb.h @@ -37,7 +37,7 @@ public: RESULT getNext(eServiceReference &ptr); }; -class eDVBServicePlay: public iPlayableService, public Object, public iServiceInformation +class eDVBServicePlay: public iPlayableService, iSeekableService, public Object, public iServiceInformation { DECLARE_REF(eDVBServicePlay); private: @@ -66,9 +66,15 @@ public: RESULT connectEvent(const Slot2 &event, ePtr &connection); RESULT start(); RESULT stop(); + RESULT seek(ePtr &ptr); RESULT pause(ePtr &ptr); RESULT info(ePtr &ptr); + // iSeekableService + RESULT getLength(pts_t &len); + RESULT seekTo(pts_t to); + RESULT getPlayPosition(pts_t &pos); + // iServiceInformation RESULT getName(std::string &name); RESULT getEvent(ePtr &evt, int nownext); diff --git a/lib/service/servicemp3.cpp b/lib/service/servicemp3.cpp index f550afc0..549a288a 100644 --- a/lib/service/servicemp3.cpp +++ b/lib/service/servicemp3.cpp @@ -140,6 +140,7 @@ RESULT eServiceMP3::stop() } RESULT eServiceMP3::pause(ePtr &ptr) { ptr=this; return 0; } +RESULT eServiceMP3::seek(ePtr &ptr) { ptr = 0; return -1; } // iPausableService RESULT eServiceMP3::pause() { printf("mp3 pauses!\n"); return 0; } diff --git a/lib/service/servicemp3.h b/lib/service/servicemp3.h index d46f6bd7..92117857 100644 --- a/lib/service/servicemp3.h +++ b/lib/service/servicemp3.h @@ -55,6 +55,7 @@ public: RESULT start(); RESULT stop(); RESULT pause(ePtr &ptr); + RESULT seek(ePtr &ptr); // iPausableService RESULT pause();