summaryrefslogtreecommitdiff
path: root/util.c
diff options
context:
space:
mode:
Diffstat (limited to 'util.c')
-rw-r--r--util.c169
1 files changed, 161 insertions, 8 deletions
diff --git a/util.c b/util.c
index 6df6137..bf5455a 100644
--- a/util.c
+++ b/util.c
@@ -5,6 +5,8 @@
* Author: d.petrovski
*/
#include "util.h"
+#include "log.h"
+#include "equivhandler.h"
#include <vdr/channels.h>
#include <vdr/thread.h>
#include <vdr/epg.h>
@@ -21,6 +23,12 @@ int Yesterday;
int YesterdayEpoch;
int YesterdayEpochUTC;
+struct hufftab *tables[2][128];
+int table_size[2][128];
+
+EFormat Format;
+cEquivHandler* EquivHandler;
+
cChannel *GetChannelByID(tChannelID & channelID, bool searchOtherPos)
{
cChannel *VC = Channels.GetByChannelID(channelID, true);
@@ -155,7 +163,7 @@ class cAddEventThread : public cThread
private:
cTimeMs LastHandleEvent;
// cList<cAddEventListItem> *list;
- std::map<tChannelID,cList<cEvent *>*,tChannelIDCompare> *map_list;
+ std::map<tChannelID,cList<cEvent>*,tChannelIDCompare> *map_list;
enum { INSERT_TIMEOUT_IN_MS = 10000 };
protected:
virtual void Action(void);
@@ -169,14 +177,14 @@ cAddEventThread::cAddEventThread(void)
:cThread("cAddEventThread"), LastHandleEvent()
{
// list = new cList<cAddEventListItem>;
- map_list = new std::map<tChannelID,cList<cEvent *>*,tChannelIDCompare>;
+ map_list = new std::map<tChannelID,cList<cEvent>*,tChannelIDCompare>;
}
cAddEventThread::~cAddEventThread(void)
{
LOCK_THREAD;
// list->cList::Clear();
- std::map<tChannelID,cList<cEvent *>*,tChannelIDCompare>::iterator it;
+ std::map<tChannelID,cList<cEvent>*,tChannelIDCompare>::iterator it;
for ( it=map_list->begin() ; it != map_list->end(); it++ )
(*it).second->cList::Clear();
Cancel(3);
@@ -197,21 +205,28 @@ void cAddEventThread::Action(void)
// EpgHandlers.DropOutdated(schedule, e->GetEvent()->StartTime(), e->GetEvent()->EndTime(), e->GetEvent()->TableID(), e->GetEvent()->Version());
// list->Del(e);
// }
- std::map<tChannelID,cList<cEvent *>*,tChannelIDCompare>::iterator it;
+ std::map<tChannelID,cList<cEvent>*,tChannelIDCompare>::iterator it;
it=map_list->begin();
while (schedules && it != map_list->end()) {
cSchedule *schedule = (cSchedule *)schedules->GetSchedule(Channels.GetByChannelID((*it).first), true);
while (((*it).second->First()) != NULL) {
- cEvent* event = *(*it).second->First();
+ cEvent* event = (*it).second->First();
cEvent *pEqvEvent = (cEvent *) schedule->GetEvent (event->EventID(), event->StartTime());
- if (pEqvEvent)
+ if (pEqvEvent){
+ LogD (0, prep("schedule->DelEvent(event)"));
schedule->DelEvent(pEqvEvent);
+ }
- schedule->AddEvent(event);
+ LogD (0, prep("schedule->AddEvent(event)"));
+ //cCondWait::SleepMs(10);
+ if (event)
+ schedule->AddEvent(event);
(*it).second->Del(event);
}
EpgHandlers.SortSchedule(schedule);
+ //sortSchedules(schedules, (*it).first);
+ //schedule->Sort();
delete (*it).second;
map_list->erase(it);
it=map_list->begin();
@@ -224,16 +239,21 @@ void cAddEventThread::Action(void)
void cAddEventThread::AddEvent(cEvent *Event, tChannelID ChannelID)
{
+ LogD (0, prep("AddEventT start"));
LOCK_THREAD;
+ LogD (0, prep("AddEventT lock "));
if (map_list->empty() || map_list->count(ChannelID) == 0) {
- cList<cEvent *>* list = new cList<cEvent *>;
+ LogD (0, prep("AddEventT if"));
+ cList<cEvent>* list = new cList<cEvent>;
list->Add(Event);
map_list->insert(std::make_pair(ChannelID, list));
} else {
+ LogD (0, prep("AddEventT else"));
(*map_list->find(ChannelID)).second->Add(Event);
}
// list->Add(new cAddEventListItem(Event, ChannelID));
LastHandleEvent.Set(INSERT_TIMEOUT_IN_MS);
+ LogD (0, prep("AddEventT end"));
}
static cAddEventThread AddEventThread;
@@ -242,11 +262,144 @@ static cAddEventThread AddEventThread;
void AddEvent(cEvent *Event, tChannelID ChannelID)
{
+ LogD (0, prep("AddEvent"));
AddEventThread.AddEvent(Event, ChannelID);
if (!AddEventThread.Active())
AddEventThread.Start();
}
+/** \brief Decode an EPG string as necessary
+ *
+ * \param src - Possibly encoded string
+ * \param size - Size of the buffer
+ *
+ * \retval NULL - Can't decode
+ * \return A decoded string
+ */
+char *freesat_huffman_decode (const unsigned char *src, size_t size)
+{
+ int tableid;
+// freesat_decode_error = 0;
+
+ if (src[0] == 0x1f && (src[1] == 1 || src[1] == 2)) {
+ int uncompressed_len = 30;
+ char *uncompressed = (char *) calloc (1, uncompressed_len + 1);
+ unsigned value = 0, byte = 2, bit = 0;
+ int p = 0;
+ unsigned char lastch = START;
+
+ tableid = src[1] - 1;
+ while (byte < 6 && byte < size) {
+ value |= src[byte] << ((5 - byte) * 8);
+ byte++;
+ }
+ //freesat_table_load (); /**< Load the tables as necessary */
+
+ do {
+ bool found = false;
+ unsigned bitShift = 0;
+ if (lastch == ESCAPE) {
+ char nextCh = (value >> 24) & 0xff;
+ found = true;
+ // Encoded in the next 8 bits.
+ // Terminated by the first ASCII character.
+ bitShift = 8;
+ if ((nextCh & 0x80) == 0)
+ lastch = nextCh;
+ if (p >= uncompressed_len) {
+ uncompressed_len += 10;
+ uncompressed = (char *) REALLOC (uncompressed, uncompressed_len + 1);
+ }
+ uncompressed[p++] = nextCh;
+ uncompressed[p] = 0;
+ } else {
+ int j;
+ for (j = 0; j < table_size[tableid][lastch]; j++) {
+ unsigned mask = 0, maskbit = 0x80000000;
+ short kk;
+ for (kk = 0; kk < tables[tableid][lastch][j].bits; kk++) {
+ mask |= maskbit;
+ maskbit >>= 1;
+ }
+ if ((value & mask) == tables[tableid][lastch][j].value) {
+ char nextCh = tables[tableid][lastch][j].next;
+ bitShift = tables[tableid][lastch][j].bits;
+ if (nextCh != STOP && nextCh != ESCAPE) {
+ if (p >= uncompressed_len) {
+ uncompressed_len += 10;
+ uncompressed = (char *) REALLOC (uncompressed, uncompressed_len + 1);
+ }
+ uncompressed[p++] = nextCh;
+ uncompressed[p] = 0;
+ }
+ found = true;
+ lastch = nextCh;
+ break;
+ }
+ }
+ }
+ if (found) {
+ // Shift up by the number of bits.
+ unsigned b;
+ for (b = 0; b < bitShift; b++) {
+ value = (value << 1) & 0xfffffffe;
+ if (byte < size)
+ value |= (src[byte] >> (7 - bit)) & 1;
+ if (bit == 7) {
+ bit = 0;
+ byte++;
+ } else
+ bit++;
+ }
+ } else {
+ LogE (0, prep("Missing table %d entry: <%s>"), tableid + 1, uncompressed);
+ // Entry missing in table.
+ return uncompressed;
+ }
+ } while (lastch != STOP && value != 0);
+
+ return uncompressed;
+ }
+ return NULL;
+}
+
+void decodeText2 (const unsigned char *from, int len, char *buffer, int buffsize)
+{
+ if (from[0] == 0x1f) {
+ char *temp = freesat_huffman_decode (from, len);
+ if (temp) {
+ len = strlen (temp);
+ len = len < buffsize - 1 ? len : buffsize - 1;
+ strncpy (buffer, temp, len);
+ buffer[len] = 0;
+ free (temp);
+ return;
+ }
+ }
+
+ SI::String convStr;
+ SI::CharArray charArray;
+ charArray.assign(from, len);
+ convStr.setData(charArray, len);
+ //LogE(5, prep("decodeText2 from %s - length %d"), from, len);
+ convStr.getText(buffer, buffsize);
+ //LogE(5, prep("decodeText2 buffer %s - buffsize %d"), buffer, buffsize);
+}
+
+void sortSchedules(cSchedules * Schedules, tChannelID channelID){
+
+ LogD(3, prep("Start sortEquivalent %s"), *channelID.ToString());
+
+ cChannel *pChannel = GetChannelByID (channelID, false);
+ cSchedule *pSchedule;
+ if (pChannel) {
+ pSchedule = (cSchedule *) (Schedules->GetSchedule(pChannel, true));
+ pSchedule->Sort();
+ Schedules->SetModified(pSchedule);
+ }
+ if (EquivHandler->getEquiChanMap().count(*channelID.ToString()) > 0)
+ EquivHandler->sortEquivalents(channelID, Schedules);
+}
}