From 404448e925e6a02712a29ad5c503badec9d488bb Mon Sep 17 00:00:00 2001 From: ZXGuesser Date: Mon, 17 Aug 2020 06:09:17 +0100 Subject: [PATCH] Better handling of adding and removing packet 29 --- filemonitor.cpp | 12 +---- packetmag.cpp | 56 +++++++++++++------- packetmag.h | 14 +++-- pagelist.cpp | 129 +++++++++++++++++++++------------------------- pagelist.h | 6 +-- ttxpage.h | 11 ++-- ttxpagestream.cpp | 2 + ttxpagestream.h | 7 ++- 8 files changed, 120 insertions(+), 117 deletions(-) diff --git a/filemonitor.cpp b/filemonitor.cpp index 9a32a92..c9dbf7d 100644 --- a/filemonitor.cpp +++ b/filemonitor.cpp @@ -175,11 +175,7 @@ int FileMonitor::readDirectory(std::string path){ q->SetUpdatedFlag(true); } - if (_pageList->CheckForPacket29(q)) - { - std::cerr << "[FileMonitor::run] found packet 29" << std::endl; - _pageList->GetMagazines()[mag]->SetPacket29(_pageList->GetPacket29(mag)); - } + _pageList->CheckForPacket29(q); q->SetModifiedTime(attrib.st_mtime); // unlock @@ -234,11 +230,7 @@ int FileMonitor::readDirectory(std::string path){ } } - if (_pageList->CheckForPacket29(q)) - { - std::cerr << "[FileMonitor::run] found packet 29" << std::endl; - _pageList->GetMagazines()[mag]->SetPacket29(_pageList->GetPacket29(mag)); - } + _pageList->CheckForPacket29(q); } else std::cerr << "[FileMonitor::run] Failed to add" << dirp->d_name << std::endl; // should never happen diff --git a/packetmag.cpp b/packetmag.cpp index 0ce2a57..0f8ddc5 100644 --- a/packetmag.cpp +++ b/packetmag.cpp @@ -16,6 +16,7 @@ PacketMag::PacketMag(uint8_t mag, std::list* pageSet, ttx::Config _thisRow(0), _lastTxt(nullptr), _nextPacket29DC(0), + _hasPacket29(false), _magRegion(0), _specialPagesFlipFlop(false), _waitingForField(0) @@ -73,23 +74,28 @@ Packet* PacketMag::GetPacket(Packet* p) switch (_state) { case PACKETSTATE_HEADER: // Start to send out a new page, which may be a simple page or one of a carousel - if (GetEvent(EVENT_PACKET_29)) + if (GetEvent(EVENT_PACKET_29) && _hasPacket29) { - while (_packet29[_nextPacket29DC] == nullptr) + if (_mtx.try_lock()) // skip if unable to get lock { - _nextPacket29DC++; - } - - if (_nextPacket29DC >= MAXPACKET29TYPES) - { - _nextPacket29DC = 0; - ClearEvent(EVENT_PACKET_29); - } - else - { - p->SetRow(_magNumber, 29, _packet29[_nextPacket29DC]->GetLine(), CODING_13_TRIPLETS); - _nextPacket29DC++; - return p; + while (_packet29[_nextPacket29DC] == nullptr) + { + _nextPacket29DC++; + } + + if (_nextPacket29DC >= MAXPACKET29TYPES) + { + _nextPacket29DC = 0; + ClearEvent(EVENT_PACKET_29); + } + else + { + p->SetRow(_magNumber, 29, _packet29[_nextPacket29DC]->GetLine(), CODING_13_TRIPLETS); + _nextPacket29DC++; + _mtx.unlock(); // unlock before we return! + return p; + } + _mtx.unlock(); // we got a lock so unlock again } } _specialPagesFlipFlop = !_specialPagesFlipFlop; // toggle the flag so that we interleave special pages and regular pages during the special pages event so that rolling headers aren't stopped completely @@ -420,10 +426,9 @@ bool PacketMag::IsReady(bool force) } }; -void PacketMag::SetPacket29(TTXLine *lines[MAXPACKET29TYPES]){ - //std::cerr << "[PacketMag::setPacket29]" << std::endl; - for (int i=0;iGetCharAt(2) & 0x30) >> 4) | ((_packet29[2]->GetCharAt(3) & 0x3) << 2); } } + +void PacketMag::DeletePacket29(){ + _mtx.lock(); + for (int i=0;i +#include #include #include "ttxpagestream.h" #include "carousel.h" @@ -42,8 +43,10 @@ class PacketMag : public PacketSource void SetPriority(uint8_t priority) { _priority = priority; } bool IsReady(bool force=false); - - void SetPacket29(TTXLine *lines[MAXPACKET29TYPES]); + + void SetPacket29(int i, TTXLine *line); + bool GetPacket29Flag() { return _hasPacket29; }; + void DeletePacket29(); protected: @@ -63,10 +66,13 @@ class PacketMag : public PacketSource PacketState _state; /// State machine to sequence packet types uint8_t _thisRow; // The current line that we are outputting TTXLine* _lastTxt; // The text of the last row that we fetched. Used for enhanced packets - + + int _nextPacket29DC; TTXLine* _packet29[MAXPACKET29TYPES]; // space to store magazine related enhancement packets TTXLine* _nextPacket29; - int _nextPacket29DC; + bool _hasPacket29; + std::mutex _mtx; // Mutex to interlock packet 29 from filemonitor + int _magRegion; int _status; int _region; diff --git a/pagelist.cpp b/pagelist.cpp index ceef02c..9ff27e1 100644 --- a/pagelist.cpp +++ b/pagelist.cpp @@ -12,10 +12,6 @@ PageList::PageList(Configure *configure) : for (int i=0;i<8;i++) { _mag[i]=nullptr; - for (int j=0;jSetPacket29(_magPacket29[i]); } - - + + // Load files + if (ReadDirectory(filepath)) + return errno; + PopulatePageTypeLists(); // add pages to the appropriate lists for their type // Just for testing @@ -112,14 +104,15 @@ int PageList::ReadDirectory(std::string filepath) // If the page loaded, then push it into the appropriate magazine if (q->Loaded()) { - q->GetPageCount(); // Use for the side effect of renumbering the subcodes - + q->GetPageCount(); // Use for the side effect of renumbering the subcodes + + CheckForPacket29(q); + } + int mag=(q->GetPageNumber() >> 16) & 0x7; _pageList[mag].push_back(*q); // This copies. But we can't copy a mutex - if (CheckForPacket29(q)) - std::cerr << "[PageList::LoadPageList] found packet 29" << std::endl; - } + } } closedir(dp); @@ -129,54 +122,50 @@ int PageList::ReadDirectory(std::string filepath) void PageList::AddPage(TTXPageStream* page) { - int mag=(page->GetPageNumber() >> 16) & 0x7; - _pageList[mag].push_back(*page); - if (CheckForPacket29(page)) - { - std::cerr << "[PageList::AddPage] found packet 29" << std::endl; - _mag[mag]->SetPacket29(_magPacket29[mag]); - } + int mag=(page->GetPageNumber() >> 16) & 0x7; + _pageList[mag].push_back(*page); } -bool PageList::CheckForPacket29(TTXPageStream* page) +void PageList::CheckForPacket29(TTXPageStream* page) { - if (page->IsCarousel()) // page mFF should never be a carousel and this code leads to a crash if it is so bail out now - return false; - int Packet29Flag = false; - int mag=(page->GetPageNumber() >> 16) & 0x7; - if (((page->GetPageNumber() >> 8) & 0xFF) == 0xFF) - { - // only read packet 29 from page mFF - - // clear any previous packet 29 - _magPacket29[mag][0] = nullptr; - _magPacket29[mag][1] = nullptr; - _magPacket29[mag][2] = nullptr; - TTXLine* tempLine = page->GetTxRow(29); - while (tempLine != nullptr) - { - //std::cerr << "page includes packet 29" << std::endl; - switch (tempLine->GetCharAt(0)) - { - case '@': - Packet29Flag = true; - _magPacket29[mag][0] = new TTXLine(tempLine->GetLine(), true); - break; - case 'A': - Packet29Flag = true; - _magPacket29[mag][1] = new TTXLine(tempLine->GetLine(), true); - break; - case 'D': - Packet29Flag = true; - _magPacket29[mag][2] = new TTXLine(tempLine->GetLine(), true); - break; - } - - tempLine = tempLine->GetNextLine(); - // loop until every row 29 is copied - } - } - return Packet29Flag; + if (page->IsCarousel()) // page mFF should never be a carousel and this code leads to a crash if it is so bail out now + return; + + bool Packet29Flag = false; + int mag=(page->GetPageNumber() >> 16) & 0x7; + if (((page->GetPageNumber() >> 8) & 0xFF) == 0xFF) // Only read packet 29 from page mFF + { + if (_mag[mag]->GetPacket29Flag() == false) // Only allow one file to set packet29 per magazine + { + TTXLine* tempLine = page->GetTxRow(29); + + while (tempLine != nullptr) + { + switch (tempLine->GetCharAt(0)) + { + case '@': + Packet29Flag = true; + _mag[mag]->SetPacket29(0, new TTXLine(tempLine->GetLine(), true)); + break; + case 'A': + Packet29Flag = true; + _mag[mag]->SetPacket29(1, new TTXLine(tempLine->GetLine(), true)); + break; + case 'D': + Packet29Flag = true; + _mag[mag]->SetPacket29(2, new TTXLine(tempLine->GetLine(), true)); + break; + } + + tempLine = tempLine->GetNextLine(); + // loop until every row 29 is copied + } + page->SetPacket29Flag(Packet29Flag); // mark the page + } + + if (Packet29Flag) + std::cerr << "[PageList::CheckForPacket29] Added packet 29 for magazine " << ((mag == 0)?8:mag) << std::endl; + } } // Find a page by filename @@ -384,7 +373,7 @@ void PageList::ClearFlags() TTXPageStream* ptr; ptr=&(*p); // Don't unmark a file that was MARKED. Once condemned it won't be pardoned - if (ptr->GetStatusFlag()==TTXPageStream::FOUND) + if (ptr->GetStatusFlag()==TTXPageStream::FOUND || ptr->GetStatusFlag()==TTXPageStream::NEW) { ptr->SetState(TTXPageStream::NOTFOUND); } @@ -403,13 +392,11 @@ void PageList::DeleteOldPages() ptr=&(*p); if (ptr->GetStatusFlag()==TTXPageStream::GONE) { - if (((ptr->GetPageNumber() >> 8) & 0xFF) == 0xFF) + if (ptr->GetPacket29Flag()) { - // page mFF - make sure packet 29 is removed - _magPacket29[mag][0] = nullptr; - _magPacket29[mag][1] = nullptr; - _magPacket29[mag][2] = nullptr; - _mag[mag]->SetPacket29(_magPacket29[mag]); + // Packet 29 was loaded from this page, so remove it. + _mag[mag]->DeletePacket29(); + std::cerr << "[PageList::DeleteOldPages] Removing packet 29 from magazine " << ((mag == 0)?8:mag) << std::endl; } //std::cerr << "[PageList::DeleteOldPages] Deleted " << ptr->GetSourcePage() << std::endl; diff --git a/pagelist.h b/pagelist.h index 1d51a34..88a93ee 100644 --- a/pagelist.h +++ b/pagelist.h @@ -88,9 +88,7 @@ class PageList */ TTXPageStream* FirstPage(); - bool CheckForPacket29(TTXPageStream* page); - - TTXLine** GetPacket29(int mag){ return _magPacket29[mag];}; + void CheckForPacket29(TTXPageStream* page); private: Configure* _configure; // The configuration object @@ -103,8 +101,6 @@ class PageList */ void PopulatePageTypeLists(); - TTXLine* _magPacket29[8][MAXPACKET29TYPES]; - // iterators through selected pages. (use the same iterator for D command and MD, L etc.) uint8_t _iterMag; /// Magazine number for the iterator std::list::iterator _iter; /// pages in a magazine diff --git a/ttxpage.h b/ttxpage.h index 740b562..fc13e84 100644 --- a/ttxpage.h +++ b/ttxpage.h @@ -204,10 +204,9 @@ class TTXPage void SetSelected(bool value){_Selected=value;}; /// Set the selected state to value bool Selected(){return _Selected;}; /// Return the selected state - + protected: bool m_LoadTTI(std::string filename); - int m_cycletimeseconds; // CT int m_fastextlinks[6]; // FL int m_PageNumber; // PN @@ -216,7 +215,6 @@ class TTXPage // Private objects TTXPage* m_SubPage; TTXLine* m_pLine[MAXROW+1]; - std::string m_destination; // DS std::string m_sourcepage; // SP std::string m_description; // DE @@ -227,13 +225,12 @@ class TTXPage unsigned int m_lastpacket; PageCoding m_pagecoding; PageFunction m_pagefunction; - // Private functions - void m_Init(); - bool m_Loaded; bool _Selected; /// True if this page has been selected. - bool _fileChanged; // page was reloaded by the filemonitor + + // Private functions + void m_Init(); }; diff --git a/ttxpagestream.cpp b/ttxpagestream.cpp index 5761478..f10ccbc 100644 --- a/ttxpagestream.cpp +++ b/ttxpagestream.cpp @@ -4,6 +4,7 @@ TTXPageStream::TTXPageStream() : _transitionTime(0), _CarouselPage(NULL), _fileStatus(NEW), + _loadedPacket29(false), _isCarousel(false), _isSpecial(false), _isNormal(false), @@ -18,6 +19,7 @@ TTXPageStream::TTXPageStream(std::string filename) : _transitionTime(0), _CarouselPage(NULL), _fileStatus(NEW), + _loadedPacket29(false), _isCarousel(false), _isSpecial(false), _isNormal(false), diff --git a/ttxpagestream.h b/ttxpagestream.h index 28b9e93..5bf626f 100644 --- a/ttxpagestream.h +++ b/ttxpagestream.h @@ -119,6 +119,9 @@ class TTXPageStream : public TTXPage // Todo: These are migrating to TTXPage void SetSelected(bool value){_Selected=value;}; /// Set the selected state to value bool Selected(){return _Selected;}; /// Return the selected state + + void SetPacket29Flag(bool value){_loadedPacket29=value;}; // Used by PageList::CheckForPacket29 + bool GetPacket29Flag(){return _loadedPacket29;}; // Used by PageList::DeleteOldPages protected: @@ -133,7 +136,9 @@ class TTXPageStream : public TTXPage // Things that affect the display list time_t _modifiedTime; /// Poll this in case the source file changes (Used to detect updates) Status _fileStatus; /// Used to mark if we found the file. (Used to detect deletions) - + + bool _loadedPacket29; // Packet 29 for magazine was loaded from this page. Should only be set on one page in each magazine. + bool _Selected; /// Marked as selected by the inserter P command bool _isCarousel;