/// <summary> /// timer callback. /// This method is called by a timer every 30 seconds to wake up the epg grabber /// the epg grabber will check if its time to grab the epg for a channel /// and ifso it starts the grabbing process /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void _epgTimer_Elapsed(object sender, System.Timers.ElapsedEventArgs e) { //security check, dont allow re-entrancy here if (_reEntrant) { return; } try { _reEntrant = true; //if epg grabber is idle, then grab epg for the next channel if (_state == EpgState.Idle) { return; } else if (_state == EpgState.Grabbing) { //if we are grabbing epg, then check if card is still idle if (_user.CardId >= 0) { if (!IsCardIdle(_user)) { //not idle? then cancel epg grabbing if (_state != EpgState.Idle) { Log.Epg("EpgCard: Canceled epg, card is not idle:{0}", _user.CardId); } _tvController.AbortEPGGrabbing(_user.CardId); _state = EpgState.Idle; _user.CardId = -1; _currentTransponder.InUse = false; return; } } //wait until grabbing has finished TimeSpan ts = DateTime.Now - _grabStartTime; if (ts.TotalMinutes > _epgTimeOut) { //epg grabber timed out. Update database and go back to idle mode Log.Epg("EpgCard: card: {0} timeout after {1} mins", _user.CardId, ts.TotalMinutes); _tvController.AbortEPGGrabbing(_user.CardId); Log.Epg("EpgCard: Aborted epg grab"); } else { Log.Epg("EpgCard: allow grabbing for {0} seconds on card {1}", ts.TotalSeconds, _user.CardId); } } } catch (Exception ex) { Log.Error("EpgCard: Error in EPG timer - {0}", ex.ToString()); } finally { _reEntrant = false; } }
public bool IsActivationCriteriaSame(EpgState state) { bool returnState = true; if (state == null || state.ActivationCriterias == null || this.ActivationCriterias == null) { returnState = false; } else { if (this.ActivationCriterias.Count == state.ActivationCriterias.Count) { for (int index = 0; index < this.ActivationCriterias.Count; index++) { if (this.ActivationCriterias[index] != state.ActivationCriterias[index]) { returnState = false; break; } } } else { returnState = false; } } return(returnState); }
/// <summary> /// Grabs the epg. /// </summary> public void GrabEpg() { _tvController.OnTvServerEvent += _eventHandler; TvBusinessLayer layer = new TvBusinessLayer(); Setting s = layer.GetSetting("timeoutEPG", "10"); if (Int32.TryParse(s.Value, out _epgTimeOut) == false) { _epgTimeOut = 10; } _currentTransponder = TransponderList.Instance.CurrentTransponder; Channel channel = _currentTransponder.CurrentChannel; Log.Epg("EpgCard: grab epg on card: #{0} transponder: #{1} ch:{2} ", _card.IdCard, TransponderList.Instance.CurrentIndex, channel.DisplayName); _state = EpgState.Idle; _isRunning = true; _user = UserFactory.CreateEpgUser(); if (GrabEpgForChannel(channel, _currentTransponder.Tuning, _card)) { Log.Epg("EpgCard: card: {0} starting to grab {1}", _user.CardId, _currentTransponder.Tuning.ToString()); _currentTransponder.InUse = true; //succeeded, then wait for epg to be received _state = EpgState.Grabbing; _grabStartTime = DateTime.Now; _epgTimer.Enabled = true; return; } Log.Epg("EpgCard: unable to grab epg transponder: {0} ch: {1} started on {2}", TransponderList.Instance.CurrentIndex, channel.DisplayName, _user.CardId); Log.Epg("{0}", _currentTransponder.Tuning.ToString()); }
/// <summary> /// workerthread which will update the database with the new epg received /// </summary> private void UpdateDatabaseThread() { Thread.CurrentThread.Priority = ThreadPriority.Lowest; //if card is not idle anymore we return if (IsCardIdle(_user) == false) { _currentTransponder.InUse = false; return; } Log.Epg("Epg: card:{0} Updating database with new programs", _user.CardId); bool timeOut = false; _dbUpdater.ReloadConfig(); try { foreach (EpgChannel epgChannel in _epg) { _dbUpdater.UpdateEpgForChannel(epgChannel); if (_state != EpgState.Updating) { Log.Epg("Epg: card:{0} stopped updating state changed", _user.CardId); timeOut = true; return; } if (IsCardIdle(_user) == false) { Log.Epg("Epg: card:{0} stopped updating card not idle", _user.CardId); timeOut = true; return; } } _epg.Clear(); Schedule.SynchProgramStatesForAll(); Log.Epg("Epg: card:{0} Finished updating the database.", _user.CardId); } catch (Exception ex) { Log.Write(ex); } finally { if (timeOut == false) { _currentTransponder.OnTimeOut(); } if (_state != EpgState.Idle && _user.CardId >= 0) { _tvController.StopGrabbingEpg(_user); _tvController.PauseCard(_user); } _currentTransponder.InUse = false; _state = EpgState.Idle; _user.CardId = -1; _tvController.Fire(this, new TvServerEventArgs(TvServerEventType.ProgramUpdated)); } }
/// <summary> /// Gets called when epg has been cancelled /// Should be overriden by the class /// </summary> public override void OnEpgCancelled() { Log.Epg("epg grabber:epg cancelled"); if (_state == EpgState.Idle) { return; } _state = EpgState.Idle; _tvController.StopGrabbingEpg(_user); _user.CardId = -1; _currentTransponder.InUse = false; return; }
/// <summary> /// Constructor /// </summary> /// <param name="controller">instance of a TVController</param> /// <param name="card">The card</param> public EpgCard(TVController controller, Card card) { _card = card; _user = UserFactory.CreateEpgUser(); _tvController = controller; _grabStartTime = DateTime.MinValue; _state = EpgState.Idle; _epgTimer.Interval = 30000; _epgTimer.Elapsed += _epgTimer_Elapsed; _eventHandler = controller_OnTvServerEvent; _dbUpdater = new EpgDBUpdater(_tvController, "IdleEpgGrabber", true); }
/// <summary> /// Stops this instance. /// </summary> public void Stop() { if (_user.CardId >= 0) { Log.Epg("EpgCard: card: {0} stop grabbing", _user.CardId); _tvController.StopGrabbingEpg(_user); } if (_currentTransponder != null) { _currentTransponder.InUse = false; } _tvController.OnTvServerEvent -= _eventHandler; _epgTimer.Enabled = false; _isRunning = false; _state = EpgState.Idle; _user.CardId = -1; }
private void HighlightBasedOnTitle(EpgState state, string navigationState) { String dictionaryValue = ""; Dictionary <EnumEpgKeys, String> parentScrnDictionary = new Dictionary <EnumEpgKeys, String>(); try { dictionaryValue = EPG.Utils.EPGStateMachine.GetDictionaryValueForItem(state, navigationState); } catch { EPG.Utils.LogCommentWarning("Dictionary value is not defined for the " + navigationState + ". Taking item name instead."); dictionaryValue = navigationState; } parentScrnDictionary.Clear(); parentScrnDictionary.Add(EnumEpgKeys.TITLE, dictionaryValue); EPG.Utils.HighlightOption(state, parentScrnDictionary); }
/// <summary> /// Constructor /// </summary> /// <param name="controller">instance of a TVController</param> /// <param name="card">The card</param> public EpgCard(TVController controller, Card card) { _card = card; _user = new User("epg", false, -1); _tvController = controller; _grabStartTime = DateTime.MinValue; _state = EpgState.Idle; _epgTimer.Interval = 30000; _epgTimer.Elapsed += _epgTimer_Elapsed; _eventHandler = controller_OnTvServerEvent; _dbUpdater = new EpgDBUpdater(_tvController, "IdleEpgGrabber", true); }
/// <summary> /// timer callback. /// This method is called by a timer every 30 seconds to wake up the epg grabber /// the epg grabber will check if its time to grab the epg for a channel /// and ifso it starts the grabbing process /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void _epgTimer_Elapsed(object sender, System.Timers.ElapsedEventArgs e) { //security check, dont allow re-entrancy here if (_reEntrant) return; try { _reEntrant = true; //if epg grabber is idle, then grab epg for the next channel if (_state == EpgState.Idle) { return; } else if (_state == EpgState.Grabbing) { //if we are grabbing epg, then check if card is still idle if (_user.CardId >= 0) { if (!IsCardIdle(_user)) { //not idle? then cancel epg grabbing if (_state != EpgState.Idle) { Log.Epg("EpgCard: Canceled epg, card is not idle:{0}", _user.CardId); } _tvController.AbortEPGGrabbing(_user.CardId); _state = EpgState.Idle; _user.CardId = -1; _currentTransponder.InUse = false; return; } } //wait until grabbing has finished TimeSpan ts = DateTime.Now - _grabStartTime; if (ts.TotalMinutes > _epgTimeOut) { //epg grabber timed out. Update database and go back to idle mode Log.Epg("EpgCard: card: {0} timeout after {1} mins", _user.CardId, ts.TotalMinutes); _tvController.AbortEPGGrabbing(_user.CardId); Log.Epg("EpgCard: Aborted epg grab"); } else { Log.Epg("EpgCard: allow grabbing for {0} seconds on card {1}", ts.TotalSeconds, _user.CardId); } } } catch (Exception ex) { Log.Error("EpgCard: Error in EPG timer - {0}", ex.ToString()); } finally { _reEntrant = false; } }
/// <summary> /// Grabs the epg. /// </summary> public void GrabEpg() { _tvController.OnTvServerEvent += _eventHandler; TvBusinessLayer layer = new TvBusinessLayer(); Setting s = layer.GetSetting("timeoutEPG", "10"); if (Int32.TryParse(s.Value, out _epgTimeOut) == false) { _epgTimeOut = 10; } _currentTransponder = TransponderList.Instance.CurrentTransponder; Channel channel = _currentTransponder.CurrentChannel; Log.Epg("EpgCard: grab epg on card: #{0} transponder: #{1} ch:{2} ", _card.IdCard, TransponderList.Instance.CurrentIndex, channel.DisplayName); _state = EpgState.Idle; _isRunning = true; _user = new User("epg", false, -1); if (GrabEpgForChannel(channel, _currentTransponder.Tuning, _card)) { Log.Epg("EpgCard: card: {0} starting to grab {1}", _user.CardId, _currentTransponder.Tuning.ToString()); _currentTransponder.InUse = true; //succeeded, then wait for epg to be received _state = EpgState.Grabbing; _grabStartTime = DateTime.Now; _epgTimer.Enabled = true; return; } Log.Epg("EpgCard: unable to grab epg transponder: {0} ch: {1} started on {2}", TransponderList.Instance.CurrentIndex, channel.DisplayName, _user.CardId); Log.Epg("{0}", _currentTransponder.Tuning.ToString()); }
/// <summary> /// Callback fired by the tvcontroller when EPG data has been received /// The method checks if epg grabbing was in progress and ifso creates a new workerthread /// to update the database with the new epg data /// </summary> public override int OnEpgReceived() { try { //is epg grabbing in progress? /*if (_state == EpgState.Idle) { Log.Epg("Epg: card:{0} OnEpgReceived while idle", _user.CardId); return 0; }*/ //is epg grabber already updating the database? if (_state == EpgState.Updating) { Log.Epg("Epg: card:{0} OnEpgReceived while updating", _user.CardId); return 0; } //is the card still idle? if (IsCardIdle(_user) == false) { Log.Epg("Epg: card:{0} OnEpgReceived but card is not idle", _user.CardId); _state = EpgState.Idle; _tvController.StopGrabbingEpg(_user); _user.CardId = -1; _currentTransponder.InUse = false; return 0; } List<EpgChannel> epg = _tvController.Epg(_user.CardId) ?? new List<EpgChannel>(); //did we receive epg info? if (epg.Count == 0) { //no epg found for this transponder Log.Epg("Epg: card:{0} no epg found", _user.CardId); _currentTransponder.InUse = false; _currentTransponder.OnTimeOut(); _state = EpgState.Idle; _tvController.StopGrabbingEpg(_user); _tvController.PauseCard(_user); _user.CardId = -1; _currentTransponder.InUse = false; return 0; } //create worker thread to update the database Log.Epg("Epg: card:{0} received epg for {1} channels", _user.CardId, epg.Count); _state = EpgState.Updating; _epg = epg; Thread workerThread = new Thread(UpdateDatabaseThread); workerThread.IsBackground = true; workerThread.Name = "EPG Update thread"; workerThread.Start(); } catch (Exception ex) { Log.Write(ex); } return 0; }
/// <summary> /// Callback fired by the tvcontroller when EPG data has been received /// The method checks if epg grabbing was in progress and ifso creates a new workerthread /// to update the database with the new epg data /// </summary> public override int OnEpgReceived() { try { //is epg grabbing in progress? /*if (_state == EpgState.Idle) { Log.Epg("Epg: card:{0} OnEpgReceived while idle", _user.CardId); return 0; }*/ //is epg grabber already updating the database? if (_state == EpgState.Updating) { Log.Epg("Epg: card:{0} OnEpgReceived while updating", _user.CardId); return 0; } // It is not safe to stop the tuner graph from here because we're in // a callback that has been triggered during sample processing. Start // a thread to stop the graph safely... //is the card still idle? if (IsCardIdle(_user) == false) { Log.Epg("Epg: card:{0} OnEpgReceived but card is not idle", _user.CardId); Thread stopThread = new Thread(Stop); stopThread.IsBackground = true; stopThread.Name = "EPG grabber stop thread"; stopThread.Start(); return 0; } List<EpgChannel> epg = _tvController.Epg(_user.CardId) ?? new List<EpgChannel>(); //did we receive epg info? if (epg.Count == 0) { //no epg found for this transponder Log.Epg("Epg: card:{0} no epg found", _user.CardId); _currentTransponder.OnTimeOut(); Thread stopThread = new Thread(Stop); stopThread.IsBackground = true; stopThread.Name = "EPG grabber stop thread"; stopThread.Start(); return 0; } //create worker thread to update the database Log.Epg("Epg: card:{0} received epg for {1} channels", _user.CardId, epg.Count); _state = EpgState.Updating; _epg = epg; Thread workerThread = new Thread(UpdateDatabaseThread); workerThread.IsBackground = true; workerThread.Name = "EPG Update thread"; workerThread.Start(); } catch (Exception ex) { Log.Write(ex); } return 0; }
/// <summary> /// Callback fired by the tvcontroller when EPG data has been received /// The method checks if epg grabbing was in progress and ifso creates a new workerthread /// to update the database with the new epg data /// </summary> public override int OnEpgReceived() { try { //is epg grabbing in progress? /*if (_state == EpgState.Idle) * { * Log.Epg("Epg: card:{0} OnEpgReceived while idle", _user.CardId); * return 0; * }*/ //is epg grabber already updating the database? if (_state == EpgState.Updating) { Log.Epg("Epg: card:{0} OnEpgReceived while updating", _user.CardId); return(0); } //is the card still idle? if (IsCardIdle(_user) == false) { Log.Epg("Epg: card:{0} OnEpgReceived but card is not idle", _user.CardId); _state = EpgState.Idle; _tvController.StopGrabbingEpg(_user); _user.CardId = -1; _currentTransponder.InUse = false; return(0); } List <EpgChannel> epg = _tvController.Epg(_user.CardId) ?? new List <EpgChannel>(); //did we receive epg info? if (epg.Count == 0) { //no epg found for this transponder Log.Epg("Epg: card:{0} no epg found", _user.CardId); _currentTransponder.InUse = false; _currentTransponder.OnTimeOut(); _state = EpgState.Idle; _tvController.StopGrabbingEpg(_user); _tvController.PauseCard(_user); _user.CardId = -1; _currentTransponder.InUse = false; return(0); } //create worker thread to update the database Log.Epg("Epg: card:{0} received epg for {1} channels", _user.CardId, epg.Count); _state = EpgState.Updating; _epg = epg; Thread workerThread = new Thread(UpdateDatabaseThread); workerThread.IsBackground = true; workerThread.Name = "EPG Update thread"; workerThread.Start(); } catch (Exception ex) { Log.Write(ex); } return(0); }
/// <summary> /// Callback fired by the tvcontroller when EPG data has been received /// The method checks if epg grabbing was in progress and ifso creates a new workerthread /// to update the database with the new epg data /// </summary> public override int OnEpgReceived() { try { //is epg grabbing in progress? /*if (_state == EpgState.Idle) * { * Log.Epg("Epg: card:{0} OnEpgReceived while idle", _user.CardId); * return 0; * }*/ //is epg grabber already updating the database? if (_state == EpgState.Updating) { Log.Epg("Epg: card:{0} OnEpgReceived while updating", _user.CardId); return(0); } // It is not safe to stop the tuner graph from here because we're in // a callback that has been triggered during sample processing. Start // a thread to stop the graph safely... //is the card still idle? if (IsCardIdle(_user) == false) { Log.Epg("Epg: card:{0} OnEpgReceived but card is not idle", _user.CardId); Thread stopThread = new Thread(Stop); stopThread.IsBackground = true; stopThread.Name = "EPG grabber stop thread"; stopThread.Start(); return(0); } List <EpgChannel> epg = _tvController.Epg(_user.CardId) ?? new List <EpgChannel>(); //did we receive epg info? if (epg.Count == 0) { //no epg found for this transponder Log.Epg("Epg: card:{0} no epg found", _user.CardId); _currentTransponder.OnTimeOut(); Thread stopThread = new Thread(Stop); stopThread.IsBackground = true; stopThread.Name = "EPG grabber stop thread"; stopThread.Start(); return(0); } //create worker thread to update the database Log.Epg("Epg: card:{0} received epg for {1} channels", _user.CardId, epg.Count); _state = EpgState.Updating; _epg = epg; Thread workerThread = new Thread(UpdateDatabaseThread); workerThread.IsBackground = true; workerThread.Name = "EPG Update thread"; workerThread.Start(); } catch (Exception ex) { Log.Write(ex); } return(0); }
protected override void Execute() { // *** WORKAROUND to navigate in VOD catalog (FLUU) *** if (namedNavigation == "STATE:STORE_ADULT_ASSET_FROM_ADULT_CATEGORY") { string title = ""; string expItem = "Infideles"; for (int i = 0; i < 3; i++) { try { EPG.Utils.SendIR("SELECT_UP"); } catch { } EPG.Utils.GetEpgInfo("title", ref title); if (title == expItem) { break; } } EPG.Utils.GetEpgInfo("title", ref title); if (title != expItem) { ExceptionUtils.ThrowEx(new EAException(ExitCodes.NavigationFailure, "Failed to navigate to '" + expItem + "'")); } else { return; } } // *** END WORKAROUND (FLUU) *** EpgState state = new EpgState(); EpgState prevState = new EpgState(); bool sameStateAsPrevious = false; string namedNavigationPrefix = "STATE:"; try { if (namedNavigation.Contains(namedNavigationPrefix)) { navigationPath = EPG.Utils.EPGStateMachine.GetNavigationPath(namedNavigation); } else { navigationPath = namedNavigation; } } catch { EPG.Utils.LogCommentFail("Failed to get the full path for the Named Navigation: " + namedNavigation); } /*split the given Navigationpath with a delimitter '/'. * /* */ navigationStatesArray = TrimAndReplaceNavPath(navigationPath); int navigationIndex = 0; /* For each state in the navigation path, check if its possible to perform IEX navigation. * if yes, continue fetching the next in the Navigation-list. * Else, Navigate till the last possible path and for the remaining part, * call the Highlightoption() API. */ /*navigationItem can be local - it holds different values according to context !!!*/ for (int numberOfPossibleNavigations = 0; numberOfPossibleNavigations < navigationStatesArray.Length; numberOfPossibleNavigations++) { navigationItem = navigationStatesArray[numberOfPossibleNavigations]; /*Check wehther the current navigation item is a state or not*/ try { state = EPG.Utils.EPGStateMachine.GetState(navigationItem); } catch { EPG.Utils.LogCommentInfo("Exception:: state is not defined for the entry:" + navigationItem); state = null; } if (state == null) { /*If its not a state, make sure that the item navigation is possible * else, We need to call HighlightOption Method with * its parent Menu Layout type */ bool isIEXNavigation = true; try { isIEXNavigation = prevState.Menu.GetNavigationType(navigationStatesArray[numberOfPossibleNavigations]); } catch { EPG.Utils.LogCommentInfo("StandardNavigation is not defined for the item" + navigationItem + " in the EPGStateMachine.Assuming IEX Navigation is True in this case."); isIEXNavigation = true; } if (!isIEXNavigation || sameStateAsPrevious || prevState.IsMultiLineMenu()) { NavigateConstructedPath(navigationIndex, numberOfPossibleNavigations, navigationStatesArray); /* Fetch the layout of the current option from the previous screen * and pass it to the HighlightOption() */ HighlightBasedOnTitle(prevState, navigationStatesArray[numberOfPossibleNavigations]); if (numberOfPossibleNavigations != navigationStatesArray.Length - 1) { //Send select to enter the state EPG.Utils.SendIR("SELECT"); } /*Increment the StartIndex value by one to make it to move to the next navigation in the list*/ navigationIndex = numberOfPossibleNavigations + 1; } } else if (state.IsActivationCriteriaSame(prevState)) { sameStateAsPrevious = true; bool isPopUp = false; //Navigate the part before NavigateConstructedPath(navigationIndex, numberOfPossibleNavigations, navigationStatesArray); //Highlight the required state entry and enter it HighlightBasedOnTitle(prevState, navigationStatesArray[numberOfPossibleNavigations]); try { foreach (Item item in prevState.Menu.Items) { if (item.Name == navigationItem) { isPopUp = item.IsPopup; break; } } } catch { EPG.Utils.LogCommentInfo("State is not defined in EPG state machine so handling it as a non pop up"); } if (numberOfPossibleNavigations != navigationStatesArray.Length - 1 && !isPopUp) { //Send select to enter the state EPG.Utils.SendIR("SELECT"); } /*Increment the StartIndex value by one to make it to move to the next navigation in the list*/ navigationIndex = numberOfPossibleNavigations + 1; } prevState = state; } if (isCompleteIEXNavigation) { EPG.Utils.EPG_Milestones_Navigate(navigationPath); } //TODO:: Add validation dictionary later if required EPG.Utils.LogCommentInfo("Exiting the NavigateAndHighlight() EA"); }