Пример #1
0
eDVBLocalTimeHandler::eDVBLocalTimeHandler()
	:m_use_dvb_time(true), m_updateNonTunedTimer(eTimer::create(eApp)), m_time_ready(false)
{
	if ( !instance )
		instance=this;
	ePtr<eDVBResourceManager> res_mgr;
	eDVBResourceManager::getInstance(res_mgr);
	if (!res_mgr)
		eDebug("[eDVBLocalTimerHandler] no resource manager !!!!!!!");
	else
	{
		res_mgr->connectChannelAdded(slot(*this,&eDVBLocalTimeHandler::DVBChannelAdded), m_chanAddedConn);
		time_t now = time(0);
		if ( now < 1072224000 ) // 01.01.2004
			eDebug("RTC not ready... wait for transponder time");
		else // inform all who's waiting for valid system time..
		{
			eDebug("Use valid Linux Time :) (RTC?)");
			noRTC();
			if (strncmp(mybox,"gb800solo", sizeof(mybox)) == 0 || strncmp(mybox,"gb800se", sizeof(mybox)) == 0 || strncmp(mybox,"gb800ue", sizeof(mybox)) == 0)
				m_time_ready = false; //sorry no RTC
			else
			    m_time_ready = true;
			/*emit*/ m_timeUpdated();
		}
	}
	CONNECT(m_updateNonTunedTimer->timeout, eDVBLocalTimeHandler::updateNonTuned);
}
Пример #2
0
void eDVBLocalTimeHandler::updateTime( time_t tp_time, eDVBChannel *chan, int update_count )
{
	int time_difference;
	bool restart_tdt = false;
	if (!tp_time)
		restart_tdt = true;
	else if (tp_time == -1)
	{
		restart_tdt = true;
		/*if ( eSystemInfo::getInstance()->getHwType() == eSystemInfo::DM7020 ||
		( eSystemInfo::getInstance()->getHwType() == eSystemInfo::DM7000
			&& eSystemInfo::getInstance()->hasStandbyWakeupTimer() ) )     TODO !!!!!!! */
		{
			eDebug("[eDVBLocalTimerHandler] no transponder tuned... or no TDT/TOT avail .. try to use RTC :)");
			time_t rtc_time = getRTC();
			if ( rtc_time ) // RTC Ready?
			{
				tm now;
				localtime_r(&rtc_time, &now);
				eDebug("[eDVBLocalTimerHandler] RTC time is %02d:%02d:%02d",
					now.tm_hour,
					now.tm_min,
					now.tm_sec);
				time_t linuxTime=time(0);
				localtime_r(&linuxTime, &now);
				eDebug("[eDVBLocalTimerHandler] Receiver time is %02d:%02d:%02d",
					now.tm_hour,
					now.tm_min,
					now.tm_sec);
				time_difference = rtc_time - linuxTime;
				eDebug("[eDVBLocalTimerHandler] RTC to Receiver time difference is %ld seconds", linuxTime - rtc_time );
				if ( time_difference )
				{
					eDebug("[eDVBLocalTimerHandler] set Linux Time to RTC Time");
					timeval tnow;
					gettimeofday(&tnow,0);
					tnow.tv_sec=rtc_time;
					settimeofday(&tnow,0);
				}
				else if ( !time_difference )
					eDebug("[eDVBLocalTimerHandler] no change needed");
				else
					eDebug("[eDVBLocalTimerHandler] set to RTC time");
				/*emit*/ m_timeUpdated();
			}
			else
				eDebug("[eDVBLocalTimerHandler]    getRTC returned time=0. RTC problem?");
		}
	}
	else
	{
		std::map< eDVBChannelID, int >::iterator it( m_timeOffsetMap.find( chan->getChannelID() ) );

 // current linux time
		time_t linuxTime = time(0);

	// difference between current enigma time and transponder time
		int enigma_diff = tp_time-linuxTime;

		int new_diff=0;

		bool updated = m_time_ready;

		if ( m_time_ready )  // ref time ready?
		{
			// difference between reference time (current enigma time)
			// and the transponder time
			eDebug("[eDVBLocalTimerHandler] diff is %d", enigma_diff);
			if ( abs(enigma_diff) < 120 )
			{
				eDebug("[eDVBLocalTimerHandler] diff < 120 .. use Transponder Time");
				m_timeOffsetMap[chan->getChannelID()] = 0;
				new_diff = enigma_diff;
			}
			else if ( it != m_timeOffsetMap.end() ) // correction saved?
			{
				eDebug("[eDVBLocalTimerHandler] we have correction %d", it->second);
				time_t CorrectedTpTime = tp_time+it->second;
				int ddiff = CorrectedTpTime-linuxTime;
				eDebug("[eDVBLocalTimerHandler] diff after add correction is %d", ddiff);
				if ( abs(it->second) < 300 ) // stored correction < 5 min
				{
					eDebug("[eDVBLocalTimerHandler] use stored correction(<5 min)");
					new_diff = ddiff;
				}
				else if ( getRTC() )
				{
					time_t rtc=getRTC();
					m_timeOffsetMap[chan->getChannelID()] = rtc-tp_time;
					new_diff = rtc-linuxTime;  // set enigma time to rtc
					eDebug("[eDVBLocalTimerHandler] update stored correction to %ld (calced against RTC time)", rtc-tp_time );
				}
				else if ( abs(ddiff) <= 120 )
				{
// with stored correction calced time difference is lower 2 min
// this don't help when a transponder have a clock running to slow or to fast
// then its better to have a DM7020 with always running RTC
					eDebug("[eDVBLocalTimerHandler] use stored correction(corr < 2 min)");
					new_diff = ddiff;
				}
				else  // big change in calced correction.. hold current time and update correction
				{
					eDebug("[eDVBLocalTimerHandler] update stored correction to %d", -enigma_diff);
					m_timeOffsetMap[chan->getChannelID()] = -enigma_diff;
				}
			}
			else
			{
				eDebug("[eDVBLocalTimerHandler] no correction found... store calced correction(%d)",-enigma_diff);
				m_timeOffsetMap[chan->getChannelID()] = -enigma_diff;
			}
		}
		else  // no time setted yet
		{
			if ( it != m_timeOffsetMap.end() )
			{
				enigma_diff += it->second;
				eDebug("[eDVBLocalTimerHandler] we have correction (%d)... use", it->second );
			}
			else
				eDebug("[eDVBLocalTimerHandler] dont have correction.. set Transponder Diff");
			new_diff=enigma_diff;
			m_time_ready=true;
		}

		time_t t = linuxTime+new_diff;
		m_last_tp_time_difference=tp_time-t;

		if (!new_diff &&
			updated) // overrride this check on first received TDT
		{
			eDebug("[eDVBLocalTimerHandler] not changed");
			return;
		}

		if ( !update_count )
		{
			// set rtc to calced transponder time when the first tdt is received on this
			// transponder
			setRTC(t);
			eDebug("[eDVBLocalTimerHandler] update RTC");
		}
		else if (getRTC())
		{
			if (abs(getRTC() - t) > 60)
			{
				eDebug("[eDVBLocalTimerHandler] difference between new linux time and RTC time is > 60 sec... transponder time looks not ok... use rtc time");
				t = getRTC();
			}
			else
				eDebug("[eDVBLocalTimerHandler] difference between linux time and RTC time is < 60 sec... so the transponder time looks ok");
		}
		else
			eDebug("[eDVBLocalTimerHandler] no RTC available :(");

		tm now;
		localtime_r(&t, &now);
		eDebug("[eDVBLocalTimerHandler] time update to %02d:%02d:%02d",
			now.tm_hour,
			now.tm_min,
			now.tm_sec);

		time_difference = t - linuxTime;   // calc our new linux_time -> enigma_time correction
		eDebug("[eDVBLocalTimerHandler] m_time_difference is %d", time_difference );

		if ( time_difference )
		{
			eDebug("[eDVBLocalTimerHandler] set Linux Time");
			timeval tnow;
			gettimeofday(&tnow,0);
			tnow.tv_sec=t;
			settimeofday(&tnow,0);
		}

 		 /*emit*/ m_timeUpdated();
	}

	if ( restart_tdt )
	{
		std::map<iDVBChannel*, channel_data>::iterator it =
			m_knownChannels.find(chan);
		if ( it != m_knownChannels.end() )
		{
			int updateCount = it->second.tdt->getUpdateCount();
			it->second.tdt = 0;
			it->second.tdt = new TDT(chan, updateCount);
			it->second.tdt->startTimer(TIME_UPDATE_INTERVAL);  // restart TDT for this transponder in 30min
		}
	}
}
Пример #3
0
void eDVBLocalTimeHandler::updateTime( time_t tp_time, eDVBChannel *chan, int update_count )
{
	int time_difference;
	bool restart_tdt = false;
	if (!tp_time)
		restart_tdt = true;
	else if (tp_time == -1)
	{
		restart_tdt = true;

		eDebug("[eDVBLocalTimerHandler] no transponder tuned... or no TDT/TOT avail .. try to use RTC :)");
		time_t rtc_time = getRTC();
		if (rtc_time) // RTC Ready?
		{
			tm now;

			localtime_r(&rtc_time, &now);
			eDebug("[eDVBLocalTimerHandler] RTC time is %02d:%02d:%02d", now.tm_hour, now.tm_min, now.tm_sec);
			time_t linuxTime=time(0);
			localtime_r(&linuxTime, &now);
			eDebug("[eDVBLocalTimerHandler] Receiver time is %02d:%02d:%02d", now.tm_hour, now.tm_min, now.tm_sec);
			time_difference = rtc_time - linuxTime;
			eDebug("[eDVBLocalTimerHandler] RTC to Receiver time difference is %ld seconds", linuxTime - rtc_time );

			if (time_difference)
			{
				if ((time_difference >= -15) && (time_difference <= 15))
				{
					timeval tdelta, tolddelta;

					// Slew small diffs ...
					// Even good transponders can differ by 0-5 sec, if we would step these
					// the system clock would permanentely jump around when zapping.

					tdelta.tv_sec = time_difference;

					if(adjtime(&tdelta, &tolddelta) == 0)
						eDebug("[eDVBLocalTimerHandler] slewing Linux Time by %03d seconds", time_difference);
					else
						eDebug("[eDVBLocalTimerHandler] slewing Linux Time by %03d seconds FAILED", time_difference);
				}
				else
				{
					timeval tnow;

					// ... only step larger diffs

					gettimeofday(&tnow, 0);
					tnow.tv_sec = rtc_time;
					settimeofday(&tnow, 0);
					linuxTime = time(0);
					localtime_r(&linuxTime, &now);
					eDebug("[eDVBLocalTimerHandler] stepped Linux Time to %02d:%02d:%02d", now.tm_hour, now.tm_min, now.tm_sec);
				}
			}
			else if ( !time_difference )
				eDebug("[eDVBLocalTimerHandler] no change needed");
			else
				eDebug("[eDVBLocalTimerHandler] set to RTC time");
			/*emit*/ m_timeUpdated();
		}
		else
			eDebug("[eDVBLocalTimerHandler]    getRTC returned time=0. RTC problem?");
	}
	else
	{
		std::map< eDVBChannelID, int >::iterator it( m_timeOffsetMap.find( chan->getChannelID() ) );

 // current linux time
		time_t linuxTime = time(0);

	// difference between current enigma time and transponder time
		int enigma_diff = tp_time-linuxTime;

		int new_diff=0;

		bool updated = m_time_ready;

		if ( m_time_ready )  // ref time ready?
		{
			// difference between reference time (current enigma time)
			// and the transponder time
			eDebug("[eDVBLocalTimerHandler] diff is %d", enigma_diff);
			if ( abs(enigma_diff) < 120 )
			{
				eDebug("[eDVBLocalTimerHandler] diff < 120 .. use Transponder Time");
				m_timeOffsetMap[chan->getChannelID()] = 0;
				new_diff = enigma_diff;
			}
			else if ( it != m_timeOffsetMap.end() ) // correction saved?
			{
				eDebug("[eDVBLocalTimerHandler] we have correction %d", it->second);
				time_t CorrectedTpTime = tp_time+it->second;
				int ddiff = CorrectedTpTime-linuxTime;
				eDebug("[eDVBLocalTimerHandler] diff after add correction is %d", ddiff);
				if ( abs(it->second) < 300 ) // stored correction < 5 min
				{
					eDebug("[eDVBLocalTimerHandler] use stored correction(<5 min)");
					new_diff = ddiff;
				}
				else if ( getRTC() )
				{
					time_t rtc=getRTC();
					m_timeOffsetMap[chan->getChannelID()] = rtc-tp_time;
					new_diff = rtc-linuxTime;  // set enigma time to rtc
					eDebug("[eDVBLocalTimerHandler] update stored correction to %ld (calced against RTC time)", rtc-tp_time );
				}
				else if ( abs(ddiff) <= 120 )
				{
// with stored correction calced time difference is lower 2 min
// this don't help when a transponder have a clock running to slow or to fast
// then its better to have a DM7020 with always running RTC
					eDebug("[eDVBLocalTimerHandler] use stored correction(corr < 2 min)");
					new_diff = ddiff;
				}
				else  // big change in calced correction.. hold current time and update correction
				{
					eDebug("[eDVBLocalTimerHandler] update stored correction to %d", -enigma_diff);
					m_timeOffsetMap[chan->getChannelID()] = -enigma_diff;
				}
			}
			else
			{
				eDebug("[eDVBLocalTimerHandler] no correction found... store calced correction(%d)",-enigma_diff);
				m_timeOffsetMap[chan->getChannelID()] = -enigma_diff;
			}
		}
		else  // no time setted yet
		{
			if ( it != m_timeOffsetMap.end() )
			{
				enigma_diff += it->second;
				eDebug("[eDVBLocalTimerHandler] we have correction (%d)... use", it->second );
			}
			else
				eDebug("[eDVBLocalTimerHandler] dont have correction.. set Transponder Diff");
			new_diff=enigma_diff;
			m_time_ready=true;
		}

		time_t t = linuxTime+new_diff;
		m_last_tp_time_difference=tp_time-t;

		if (!new_diff &&
			updated) // overrride this check on first received TDT
		{
			eDebug("[eDVBLocalTimerHandler] not changed");
			return;
		}

		if ( !update_count )
		{
			// set rtc to calced transponder time when the first tdt is received on this
			// transponder
			setRTC(t);
			eDebug("[eDVBLocalTimerHandler] update RTC");
		}
		else if (getRTC())
		{
			if (abs(getRTC() - t) > 60)
			{
				eDebug("[eDVBLocalTimerHandler] difference between new linux time and RTC time is > 60 sec... transponder time looks not ok... use rtc time");
				t = getRTC();
			}
			else
				eDebug("[eDVBLocalTimerHandler] difference between linux time and RTC time is < 60 sec... so the transponder time looks ok");
		}
		else
			eDebug("[eDVBLocalTimerHandler] no RTC available :(");

		tm now;
		localtime_r(&t, &now);
		eDebug("[eDVBLocalTimerHandler] time update to %02d:%02d:%02d",
			now.tm_hour,
			now.tm_min,
			now.tm_sec);

		time_difference = t - linuxTime;   // calc our new linux_time -> enigma_time correction
		eDebug("[eDVBLocalTimerHandler] m_time_difference is %d", time_difference );

		if ( time_difference )
		{
			eDebug("[eDVBLocalTimerHandler] set Linux Time");
			timeval tnow;
			gettimeofday(&tnow,0);
			tnow.tv_sec=t;
			settimeofday(&tnow,0);
		}

 		 /*emit*/ m_timeUpdated();
	}

	if ( restart_tdt )
	{
		std::map<iDVBChannel*, channel_data>::iterator it =
			m_knownChannels.find(chan);
		if ( it != m_knownChannels.end() )
		{
			int system = iDVBFrontend::feSatellite;
			ePtr<iDVBFrontendParameters> parms;
			chan->getCurrentFrontendParameters(parms);
			if (parms)
			{
				parms->getSystem(system);
			}

			int updateCount = it->second.timetable->getUpdateCount();
			it->second.timetable = NULL;

			if (system == iDVBFrontend::feATSC)
			{
				it->second.timetable = new STT(chan, updateCount);
			}
			else
			{
				it->second.timetable = new TDT(chan, updateCount);
			}
			it->second.timetable->startTimer(TIME_UPDATE_INTERVAL); // restart TDT for this transponder in 30min
		}
	}
}