From 368120c479441732f7076768e1598442bccd1585 Mon Sep 17 00:00:00 2001 From: James Turner Date: Wed, 25 Apr 2018 21:34:17 +0100 Subject: [PATCH 01/16] Track a root property on subsystem-manager --- simgear/structure/subsystem_mgr.cxx | 12 ++++++++ simgear/structure/subsystem_mgr.hxx | 16 ++++++++++ simgear/structure/subsystem_test.cxx | 44 +++++++++++++++++++++++++--- 3 files changed, 68 insertions(+), 4 deletions(-) diff --git a/simgear/structure/subsystem_mgr.cxx b/simgear/structure/subsystem_mgr.cxx index ac46eeab..52ca6fda 100644 --- a/simgear/structure/subsystem_mgr.cxx +++ b/simgear/structure/subsystem_mgr.cxx @@ -28,6 +28,7 @@ #include "exception.hxx" #include "subsystem_mgr.hxx" +#include #include #include "SGSmplstat.hxx" @@ -966,5 +967,16 @@ void SGSubsystemMgr::notifyDelegatesDidChange(SGSubsystem* sub, State state) { d->didChange(sub, state); }); } +void SGSubsystemMgr::set_root_node(SGPropertyNode_ptr node) +{ + _rootNode = node; +} + +SGPropertyNode_ptr +SGSubsystemMgr::root_node() const +{ + return _rootNode; +} + // end of subsystem_mgr.cxx diff --git a/simgear/structure/subsystem_mgr.hxx b/simgear/structure/subsystem_mgr.hxx index 26674a02..63257dc9 100644 --- a/simgear/structure/subsystem_mgr.hxx +++ b/simgear/structure/subsystem_mgr.hxx @@ -33,6 +33,7 @@ #include #include #include +#include class TimingInfo { @@ -433,6 +434,8 @@ typedef SGSharedPtr SGSubsystemGroupRef; class SGSubsystemMgr : public SGSubsystem { public: + SGSubsystemMgr(const SGSubsystemMgr&) = delete; + SGSubsystemMgr& operator=(const SGSubsystemMgr&) = delete; /** * Types of subsystem groups. @@ -483,6 +486,18 @@ public: void reportTiming(); void setReportTimingCb(void* userData,SGSubsystemTimingCb cb) {reportTimingCb = cb;reportTimingUserData = userData;} + /** + * @brief set the root property node for this subsystem manager + * subsystems can retrieve this value during init/bind (or at any time) + * to base their own properties trees off of. + */ + void set_root_node(SGPropertyNode_ptr node); + + /** + * @brief retrieve the root property node for this subsystem manager + */ + SGPropertyNode_ptr root_node() const; + template T* get_subsystem() const { @@ -631,6 +646,7 @@ private: std::vector _groups; unsigned int _initPosition = 0; bool _destructorActive = false; + SGPropertyNode_ptr _rootNode; // non-owning reference, this is to accelerate lookup // by name which otherwise needs a full walk of the entire tree diff --git a/simgear/structure/subsystem_test.cxx b/simgear/structure/subsystem_test.cxx index cb07e902..90bcab5f 100644 --- a/simgear/structure/subsystem_test.cxx +++ b/simgear/structure/subsystem_test.cxx @@ -7,6 +7,7 @@ #include #include #include +#include using std::string; using std::cout; @@ -26,6 +27,12 @@ public: wasInited = true; } + void bind() override + { + auto node = get_manager()->root_node(); + node->setIntValue("mysub/foo", 42); + } + void update(double dt) override { @@ -44,6 +51,12 @@ public: } + void bind() override + { + auto node = get_manager()->root_node(); + node->setIntValue("anothersub/bar", 172); + } + void update(double dt) override { lastUpdateTime = dt; @@ -297,10 +310,6 @@ void testIncrementalInit() break; } - for (auto ev : d->events) { - std::cerr << "ev:" << ev.nameForEvent() << std::endl; - } - SG_VERIFY(mySub->wasInited); SG_VERIFY(d->hasEvent("mysub-will-init")); @@ -392,6 +401,32 @@ void testSuspendResume() SG_CHECK_EQUAL_EP(5.0, radio2->lastUpdateTime); } +void testPropertyRoot() +{ + SGSharedPtr manager = new SGSubsystemMgr; + SGPropertyNode_ptr props(new SGPropertyNode); + manager->set_root_node(props); + + auto d = new RecorderDelegate; + manager->addDelegate(d); + + manager->add(); + auto anotherSub = manager->add(); + auto instruments = manager->add(); + + auto radio1 = manager->createInstance("nav1"); + auto radio2 = manager->createInstance("nav2"); + + instruments->set_subsystem(radio1); + instruments->set_subsystem(radio2); + + manager->bind(); + manager->init(); + + SG_CHECK_EQUAL(props->getIntValue("mysub/foo"), 42); + SG_CHECK_EQUAL(props->getIntValue("anothersub/bar"), 172); +} + /////////////////////////////////////////////////////////////////////////////// @@ -402,6 +437,7 @@ int main(int argc, char* argv[]) testSubGrouping(); testIncrementalInit(); testSuspendResume(); + testPropertyRoot(); cout << __FILE__ << ": All tests passed" << endl; return EXIT_SUCCESS; From 8b4ace6fb8889b1ed7ec8f2493c59d2e3e3bd606 Mon Sep 17 00:00:00 2001 From: James Turner Date: Wed, 25 Apr 2018 22:20:12 +0100 Subject: [PATCH 02/16] Subsystems: stub code for smart add+remove Groups track their state, which will enable them to correctly transition added and removed children in the future. Only stubbed for now, to avoid breakage on the FG side. --- simgear/structure/subsystem_mgr.cxx | 30 ++++++++++++++++++++++++++++ simgear/structure/subsystem_mgr.hxx | 6 +++++- simgear/structure/subsystem_test.cxx | 9 +++++++-- 3 files changed, 42 insertions(+), 3 deletions(-) diff --git a/simgear/structure/subsystem_mgr.cxx b/simgear/structure/subsystem_mgr.cxx index 52ca6fda..033bb244 100644 --- a/simgear/structure/subsystem_mgr.cxx +++ b/simgear/structure/subsystem_mgr.cxx @@ -157,6 +157,7 @@ SGSubsystemMgr* SGSubsystem::get_manager() const std::string SGSubsystem::nameForState(State s) { switch (s) { + case State::INVALID: return "invalid"; case State::INIT: return "init"; case State::REINIT: return "reinit"; case State::POSTINIT: return "post-init"; @@ -216,11 +217,13 @@ SGSubsystemGroup::~SGSubsystemGroup () void SGSubsystemGroup::init () { + assert(_state == State::BIND); forEach([this](SGSubsystem* s){ this->notifyWillChange(s, State::INIT); s->init(); this->notifyDidChange(s, State::INIT); }); + _state = State::INIT; } SGSubsystem::InitStatus @@ -233,11 +236,13 @@ SGSubsystemGroup::incrementalInit() // termination test if (_initPosition >= static_cast(_members.size())) { + _state = State::INIT; return INIT_DONE; } if (_initPosition < 0) { // first call + assert(_state == State::BIND); _initPosition = 0; notifyWillChange(_members.front()->subsystem, State::INIT); } @@ -279,11 +284,13 @@ void SGSubsystemGroup::reverseForEach(std::function f) void SGSubsystemGroup::postinit () { + assert(_state == State::INIT); forEach([this](SGSubsystem* s){ this->notifyWillChange(s, State::POSTINIT); s->postinit(); this->notifyDidChange(s, State::POSTINIT); }); + _state = State::POSTINIT; } void @@ -304,6 +311,7 @@ SGSubsystemGroup::shutdown () s->shutdown(); this->notifyDidChange(s, State::SHUTDOWN); }); + _state = State::SHUTDOWN; _initPosition = -1; } @@ -315,6 +323,7 @@ SGSubsystemGroup::bind () s->bind(); this->notifyDidChange(s, State::BIND); }); + _state = State::BIND; } void @@ -325,6 +334,7 @@ SGSubsystemGroup::unbind () s->unbind(); this->notifyDidChange(s, State::UNBIND); }); + _state = State::UNBIND; } void @@ -420,6 +430,16 @@ SGSubsystemGroup::set_subsystem (const string &name, SGSubsystem * subsystem, member->min_step_sec = min_step_sec; subsystem->set_group(this); notifyDidChange(subsystem, State::ADD); + + if (_state != State::INVALID) { + SG_LOG(SG_GENERAL, SG_DEV_WARN, "TODO: implement SGSubsystemGroup transition when adding after init"); + // transition to the correct state + // bind + + // init + + // post-init + } } void @@ -457,6 +477,16 @@ SGSubsystemGroup::remove_subsystem(const string &name) if (it != _members.end()) { // found it, great const auto sub = (*it)->subsystem; + + if (_state != State::INVALID) { + // transition out correctly + SG_LOG(SG_GENERAL, SG_DEV_WARN, "TODO: implement SGSubsystemGroup transition when removing before shutdown"); + + // shutdown + + // unbind + } + notifyWillChange(sub, State::REMOVE); delete *it; _members.erase(it); diff --git a/simgear/structure/subsystem_mgr.hxx b/simgear/structure/subsystem_mgr.hxx index 63257dc9..6ce18dfc 100644 --- a/simgear/structure/subsystem_mgr.hxx +++ b/simgear/structure/subsystem_mgr.hxx @@ -288,7 +288,8 @@ public: SGSubsystemGroup* get_group() const; enum class State { - ADD, + INVALID = -1, + ADD = 0, BIND, INIT, POSTINIT, @@ -401,6 +402,9 @@ private: using MemberVec = std::vector; MemberVec _members; + // track the state of this group, so we can transition added/removed + // members correctly + SGSubsystem::State _state = SGSubsystem::State::INVALID; double _fixedUpdateTime; double _updateTimeRemainder; diff --git a/simgear/structure/subsystem_test.cxx b/simgear/structure/subsystem_test.cxx index 90bcab5f..cd604272 100644 --- a/simgear/structure/subsystem_test.cxx +++ b/simgear/structure/subsystem_test.cxx @@ -30,7 +30,8 @@ public: void bind() override { auto node = get_manager()->root_node(); - node->setIntValue("mysub/foo", 42); + if (node) + node->setIntValue("mysub/foo", 42); } void update(double dt) override @@ -54,7 +55,8 @@ public: void bind() override { auto node = get_manager()->root_node(); - node->setIntValue("anothersub/bar", 172); + if (node) + node->setIntValue("anothersub/bar", 172); } void update(double dt) override @@ -246,6 +248,7 @@ void testSubGrouping() // lookup of the group should also work SG_CHECK_EQUAL(manager->get_subsystem(), instruments); + manager->bind(); manager->init(); SG_VERIFY(instruments->wasInited); @@ -304,6 +307,7 @@ void testIncrementalInit() instruments->set_subsystem(radio1); instruments->set_subsystem(radio2); + manager->bind(); for ( ; ; ) { auto status = manager->incrementalInit(); if (status == SGSubsystemMgr::INIT_DONE) @@ -347,6 +351,7 @@ void testSuspendResume() instruments->set_subsystem(radio1); instruments->set_subsystem(radio2); + manager->bind(); manager->init(); manager->update(1.0); From 888d7fb2626c704930e35ff066527e708fbbac00 Mon Sep 17 00:00:00 2001 From: James Turner Date: Fri, 27 Apr 2018 12:07:10 +0100 Subject: [PATCH 03/16] Packages: archive-type support in catalogs MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Allow URLs which don’t encode the file extension to work --- simgear/package/CatalogTest.cxx | 50 ++++++++++++++++-- simgear/package/Install.cxx | 46 +++++++++++++--- simgear/package/catalogTest1/catalog.xml | 13 +++++ simgear/package/catalogTest1/movies-data.zip | Bin 0 -> 232 bytes .../catalogTest1/movies_6789/movie-list.json | 3 ++ 5 files changed, 103 insertions(+), 9 deletions(-) create mode 100644 simgear/package/catalogTest1/movies-data.zip create mode 100644 simgear/package/catalogTest1/movies_6789/movie-list.json diff --git a/simgear/package/CatalogTest.cxx b/simgear/package/CatalogTest.cxx index 6a4446c0..f61763c2 100644 --- a/simgear/package/CatalogTest.cxx +++ b/simgear/package/CatalogTest.cxx @@ -92,6 +92,11 @@ public: path = ss.str(); } } + + // return zip data for this computed URL + if (path.find("/catalogTest1/movies") == 0) { + path = "/catalogTest1/movies-data.zip"; + } localPath.append(path); @@ -152,7 +157,7 @@ int parseTest() SG_CHECK_EQUAL(cat->description(), "First test catalog"); // check the packages too - SG_CHECK_EQUAL(cat->packages().size(), 4); + SG_CHECK_EQUAL(cat->packages().size(), 5); pkg::PackageRef p1 = cat->packages().front(); SG_CHECK_EQUAL(p1->catalog(), cat.ptr()); @@ -326,7 +331,7 @@ void testAddCatalog(HTTP::Client* cl) p.append("org.flightgear.test.catalog1"); p.append("catalog.xml"); SG_VERIFY(p.exists()); - SG_CHECK_EQUAL(root->allPackages().size(), 4); + SG_CHECK_EQUAL(root->allPackages().size(), 5); SG_CHECK_EQUAL(root->catalogs().size(), 1); pkg::PackageRef p1 = root->getPackageById("alpha"); @@ -559,6 +564,43 @@ void testInstallTarPackage(HTTP::Client* cl) SG_VERIFY(p.exists()); } +void testInstallArchiveType(HTTP::Client* cl) +{ + global_catalogVersion = 0; + SGPath rootPath(simgear::Dir::current().path()); + rootPath.append("pkg_install_archive_type"); + simgear::Dir pd(rootPath); + pd.removeChildren(); + + pkg::RootRef root(new pkg::Root(rootPath, "8.1.2")); + // specify a test dir + root->setHTTPClient(cl); + + pkg::CatalogRef c = pkg::Catalog::createFromUrl(root.ptr(), "http://localhost:2000/catalogTest1/catalog.xml"); + waitForUpdateComplete(cl, root); + + pkg::PackageRef p1 = root->getPackageById("org.flightgear.test.catalog1.movies"); + SG_CHECK_EQUAL(p1->id(), "movies"); + pkg::InstallRef ins = p1->install(); + + SG_VERIFY(ins->isQueued()); + + waitForUpdateComplete(cl, root); + SG_VERIFY(p1->isInstalled()); + SG_VERIFY(p1->existingInstall() == ins); + + // verify on disk state + SGPath p(rootPath); + p.append("org.flightgear.test.catalog1"); + p.append("Aircraft"); + p.append("movies_6789"); // FIXME once archive-dir support is decided + + SG_CHECK_EQUAL(p, ins->path()); + + p.append("movie-list.json"); + SG_VERIFY(p.exists()); +} + void testDisableDueToVersion(HTTP::Client* cl) { global_catalogVersion = 0; @@ -915,7 +957,9 @@ int main(int argc, char* argv[]) testRefreshCatalog(&cl); testInstallTarPackage(&cl); - + + testInstallArchiveType(&cl); + testDisableDueToVersion(&cl); testOfflineMode(&cl); diff --git a/simgear/package/Install.cxx b/simgear/package/Install.cxx index 7e22f0f2..96cd11e6 100644 --- a/simgear/package/Install.cxx +++ b/simgear/package/Install.cxx @@ -57,6 +57,10 @@ public: throw sg_exception("no package download URLs"); } + if (m_owner->package()->properties()->hasChild("archive-type")) { + setArchiveTypeFromExtension(m_owner->package()->properties()->getStringValue("archive-type")); + } + // TODO randomise order of m_urls m_extractPath = aOwner->path().dir(); @@ -196,7 +200,22 @@ protected: } private: - + void setArchiveTypeFromExtension(const std::string& ext) + { + if (ext.empty()) + return; + + if (ext == "zip") { + m_archiveType = ZIP; + return; + } + + if ((ext == "tar.gz") || (ext == "tgz")) { + m_archiveType = TAR_GZ; + return; + } + } + void extractCurrentFile(unzFile zip, char* buffer, size_t bufferSize) { unz_file_info fileInfo; @@ -262,14 +281,22 @@ private: { const std::string u(url()); const size_t ul(u.length()); - if (u.rfind(".zip") == (ul - 4)) { - return extractUnzip(); + + if (m_archiveType == AUTO_DETECT) { + if (u.rfind(".zip") == (ul - 4)) { + m_archiveType = ZIP; + } else if (u.rfind(".tar.gz") == (ul - 7)) { + m_archiveType = TAR_GZ; + } + // we will fall through to the error case now } - - if (u.rfind(".tar.gz") == (ul - 7)) { + + if (m_archiveType == ZIP) { + return extractUnzip(); + } else if (m_archiveType == TAR_GZ) { return extractTar(); } - + SG_LOG(SG_IO, SG_WARN, "unsupported archive format:" << u); return false; } @@ -330,7 +357,14 @@ private: m_owner->installResult(aReason); } + enum ArchiveType { + AUTO_DETECT = 0, + ZIP, + TAR_GZ + }; + InstallRef m_owner; + ArchiveType m_archiveType = AUTO_DETECT; string_list m_urls; SG_MD5_CTX m_md5; std::string m_buffer; diff --git a/simgear/package/catalogTest1/catalog.xml b/simgear/package/catalogTest1/catalog.xml index 26fb7025..1b8b7b59 100644 --- a/simgear/package/catalogTest1/catalog.xml +++ b/simgear/package/catalogTest1/catalog.xml @@ -177,4 +177,17 @@ 360 acf9eb89cf396eb42f8823d9cdf17584 + + + + movies + movies files for test catalog aircraft + 10 + movies_6789 + + http://localhost:2000/catalogTest1/movies?wierd=foo;bar=thing + zip + 232 + e5f89c3f1ed1bdda16174c868f3c7b30 + diff --git a/simgear/package/catalogTest1/movies-data.zip b/simgear/package/catalogTest1/movies-data.zip new file mode 100644 index 0000000000000000000000000000000000000000..695ec1e789ed6f4eb0bf0011b3586ed7a5ab5b06 GIT binary patch literal 232 zcmWIWW@h1H00E}h**;xAK1`JXvO!oHNap63Wu_L#o0(f!>Vw(3Ihn;JdRfK!d7&Yk z49v{`9z}t0X$3a}Bg8tOIPBm4e(}U sl4HhYr36qn0|U?;h9!+47G4LiLL7i*d4M-78%Qf75GDfYLJ)@m0GCBI;{X5v literal 0 HcmV?d00001 diff --git a/simgear/package/catalogTest1/movies_6789/movie-list.json b/simgear/package/catalogTest1/movies_6789/movie-list.json new file mode 100644 index 00000000..13be6b27 --- /dev/null +++ b/simgear/package/catalogTest1/movies_6789/movie-list.json @@ -0,0 +1,3 @@ +{ + "id": "awesomething" +} \ No newline at end of file From 6db59c64aa8e08d5b4a7da4515669de06d44bbfa Mon Sep 17 00:00:00 2001 From: James Turner Date: Fri, 27 Apr 2018 13:59:11 +0100 Subject: [PATCH 04/16] Subsystems: change naming scheme, add accessors Add some hopefully clearer accessors for the subsystem naming, and some comments documenting what is stored where. --- simgear/structure/subsystem_mgr.cxx | 25 ++++++++++++++-- simgear/structure/subsystem_mgr.hxx | 20 ++++++++++++- simgear/structure/subsystem_test.cxx | 43 ++++++++++++++++------------ 3 files changed, 67 insertions(+), 21 deletions(-) diff --git a/simgear/structure/subsystem_mgr.cxx b/simgear/structure/subsystem_mgr.cxx index 033bb244..3205b746 100644 --- a/simgear/structure/subsystem_mgr.cxx +++ b/simgear/structure/subsystem_mgr.cxx @@ -33,6 +33,7 @@ #include "SGSmplstat.hxx" const int SG_MAX_SUBSYSTEM_EXCEPTIONS = 4; +const char SUBSYSTEM_NAME_SEPARATOR = '.'; using std::string; using State = SGSubsystem::State; @@ -137,6 +138,26 @@ void SGSubsystem::set_name(const std::string &n) _name = n; } +std::string SGSubsystem::typeName() const +{ + auto pos = _name.find(SUBSYSTEM_NAME_SEPARATOR); + if (pos == std::string::npos) { + return _name; + } + + return _name.substr(0, pos); +} + +std::string SGSubsystem::instanceName() const +{ + auto pos = _name.find(SUBSYSTEM_NAME_SEPARATOR); + if (pos == std::string::npos) { + return {}; + } + + return _name.substr(pos+1); +} + void SGSubsystem::set_group(SGSubsystemGroup* group) { _group = group; @@ -815,7 +836,7 @@ SGSubsystemMgr::get_subsystem (const string &name) const SGSubsystem* SGSubsystemMgr::get_subsystem(const std::string &name, const std::string& instanceName) const { - return get_subsystem(name + "-" + instanceName); + return get_subsystem(name + SUBSYSTEM_NAME_SEPARATOR + instanceName); } @@ -954,7 +975,7 @@ SGSubsystemMgr::createInstance(const std::string& name, const std::string& insta throw sg_exception("SGSubsystemMgr::create: functor failed to create an instsance of " + name); } - const auto combinedName = name + "-" + instanceName; + const auto combinedName = name + SUBSYSTEM_NAME_SEPARATOR + instanceName; ref->set_name(combinedName); return ref; } diff --git a/simgear/structure/subsystem_mgr.hxx b/simgear/structure/subsystem_mgr.hxx index 6ce18dfc..0f3dd3b9 100644 --- a/simgear/structure/subsystem_mgr.hxx +++ b/simgear/structure/subsystem_mgr.hxx @@ -276,9 +276,23 @@ public: */ void stamp(const std::string& name); + /** + * composite name for this subsystem (type name & optional instance name) + */ std::string name() const { return _name; } + /** + * @brief the type (class)-specific part of the subsystem name. + */ + std::string typeName() const; + + /** + * @brief the instance part of the subsystem name. Empty if this + * subsystem is not instanced + */ + std::string instanceName() const; + virtual bool is_group() const { return false; } @@ -313,7 +327,11 @@ protected: void set_group(SGSubsystemGroup* group); - std::string _name; + /// composite name for the subsystem (type name and instance name if this + /// is an instanced subsystem. (Since this member was originally defined as + /// protected, not private, we can't rename it easily) + std::string _name; + bool _suspended = false; eventTimeVec timingInfo; diff --git a/simgear/structure/subsystem_test.cxx b/simgear/structure/subsystem_test.cxx index cd604272..dfc816d0 100644 --- a/simgear/structure/subsystem_test.cxx +++ b/simgear/structure/subsystem_test.cxx @@ -170,7 +170,9 @@ void testRegistrationAndCreation() SG_VERIFY(anotherSub); SG_CHECK_EQUAL(anotherSub->name(), AnotherSub::subsystemName()); SG_CHECK_EQUAL(anotherSub->name(), std::string("anothersub")); - + SG_CHECK_EQUAL(anotherSub->typeName(), std::string("anothersub")); + SG_CHECK_EQUAL(anotherSub->instanceName(), std::string()); + auto radio1 = manager->createInstance("nav1"); auto radio2 = manager->createInstance("nav2"); @@ -236,14 +238,16 @@ void testSubGrouping() auto radio1 = manager->createInstance("nav1"); auto radio2 = manager->createInstance("nav2"); - SG_CHECK_EQUAL(radio1->name(), std::string("fake-radio-nav1")); - SG_CHECK_EQUAL(radio2->name(), std::string("fake-radio-nav2")); - + SG_CHECK_EQUAL(radio1->name(), std::string("fake-radio.nav1")); + SG_CHECK_EQUAL(radio2->name(), std::string("fake-radio.nav2")); + SG_CHECK_EQUAL(radio1->typeName(), std::string("fake-radio")); + SG_CHECK_EQUAL(radio2->instanceName(), std::string("nav2")); + instruments->set_subsystem(radio1); instruments->set_subsystem(radio2); - SG_VERIFY(d->hasEvent("fake-radio-nav1-did-add")); - SG_VERIFY(d->hasEvent("fake-radio-nav1-will-add")); + SG_VERIFY(d->hasEvent("fake-radio.nav1-did-add")); + SG_VERIFY(d->hasEvent("fake-radio.nav1-will-add")); // lookup of the group should also work SG_CHECK_EQUAL(manager->get_subsystem(), instruments); @@ -257,24 +261,27 @@ void testSubGrouping() SG_VERIFY(d->hasEvent("instruments-will-init")); SG_VERIFY(d->hasEvent("instruments-did-init")); - SG_VERIFY(d->hasEvent("fake-radio-nav1-will-init")); - SG_VERIFY(d->hasEvent("fake-radio-nav2-did-init")); + SG_VERIFY(d->hasEvent("fake-radio.nav1-will-init")); + SG_VERIFY(d->hasEvent("fake-radio.nav2-did-init")); manager->update(0.5); SG_CHECK_EQUAL_EP(0.5, instruments->lastUpdateTime); SG_CHECK_EQUAL_EP(0.5, radio1->lastUpdateTime); SG_CHECK_EQUAL_EP(0.5, radio2->lastUpdateTime); - SG_CHECK_EQUAL(radio1, instruments->get_subsystem("fake-radio-nav1")); - SG_CHECK_EQUAL(radio2, instruments->get_subsystem("fake-radio-nav2")); + SG_CHECK_EQUAL(0, instruments->get_subsystem("fake-radio")); + + + SG_CHECK_EQUAL(radio1, instruments->get_subsystem("fake-radio.nav1")); + SG_CHECK_EQUAL(radio2, instruments->get_subsystem("fake-radio.nav2")); // type-safe lookup of instanced SG_CHECK_EQUAL(radio1, manager->get_subsystem("nav1")); SG_CHECK_EQUAL(radio2, manager->get_subsystem("nav2")); - bool ok = manager->remove("fake-radio-nav2"); + bool ok = manager->remove("fake-radio.nav2"); SG_VERIFY(ok); - SG_VERIFY(instruments->get_subsystem("fake-radio-nav2") == nullptr); + SG_VERIFY(instruments->get_subsystem("fake-radio.nav2") == nullptr); manager->update(1.0); SG_CHECK_EQUAL_EP(1.0, instruments->lastUpdateTime); @@ -286,7 +293,7 @@ void testSubGrouping() manager->unbind(); SG_VERIFY(d->hasEvent("instruments-will-unbind")); SG_VERIFY(d->hasEvent("instruments-did-unbind")); - SG_VERIFY(d->hasEvent("fake-radio-nav1-will-unbind")); + SG_VERIFY(d->hasEvent("fake-radio.nav1-will-unbind")); } @@ -326,11 +333,11 @@ void testIncrementalInit() // SG_VERIFY(d->hasEvent("instruments-did-init")); - SG_VERIFY(d->hasEvent("fake-radio-nav1-will-init")); - SG_VERIFY(d->hasEvent("fake-radio-nav1-did-init")); + SG_VERIFY(d->hasEvent("fake-radio.nav1-will-init")); + SG_VERIFY(d->hasEvent("fake-radio.nav1-did-init")); - SG_VERIFY(d->hasEvent("fake-radio-nav2-will-init")); - SG_VERIFY(d->hasEvent("fake-radio-nav2-did-init")); + SG_VERIFY(d->hasEvent("fake-radio.nav2-will-init")); + SG_VERIFY(d->hasEvent("fake-radio.nav2-did-init")); @@ -364,7 +371,7 @@ void testSuspendResume() SG_VERIFY(d->hasEvent("anothersub-will-suspend")); SG_VERIFY(d->hasEvent("anothersub-did-suspend")); - SG_VERIFY(!d->hasEvent("radio1-will-suspend")); + SG_VERIFY(!d->hasEvent("fake-radio.nav1-will-suspend")); manager->update(0.5); From 831369f65385752ee9c3b6490da8f093b2211658 Mon Sep 17 00:00:00 2001 From: James Turner Date: Fri, 27 Apr 2018 15:25:13 +0100 Subject: [PATCH 05/16] Packages: add archive-path XML support Allow the in-archive file path to differ from the after-install path. Requested to allow easier operation with GitHub/Labs zip generation. --- simgear/package/CatalogTest.cxx | 2 +- simgear/package/Install.cxx | 9 ++++++++- simgear/package/catalogTest1/catalog.xml | 3 ++- 3 files changed, 11 insertions(+), 3 deletions(-) diff --git a/simgear/package/CatalogTest.cxx b/simgear/package/CatalogTest.cxx index f61763c2..8e752e82 100644 --- a/simgear/package/CatalogTest.cxx +++ b/simgear/package/CatalogTest.cxx @@ -593,7 +593,7 @@ void testInstallArchiveType(HTTP::Client* cl) SGPath p(rootPath); p.append("org.flightgear.test.catalog1"); p.append("Aircraft"); - p.append("movies_6789"); // FIXME once archive-dir support is decided + p.append("movies"); SG_CHECK_EQUAL(p, ins->path()); diff --git a/simgear/package/Install.cxx b/simgear/package/Install.cxx index 96cd11e6..78272005 100644 --- a/simgear/package/Install.cxx +++ b/simgear/package/Install.cxx @@ -169,7 +169,12 @@ protected: // build a path like /path/to/packages/org.some.catalog/Aircraft/extract_xxxx/MyAircraftDir SGPath extractedPath = m_extractPath; - extractedPath.append(m_owner->package()->dirName()); + if (m_owner->package()->properties()->hasChild("archive-path")) { + extractedPath.append(m_owner->package()->properties()->getStringValue("archive-path")); + } else { + extractedPath.append(m_owner->package()->dirName()); + } + // rename it to path/to/packages/org.some.catalog/Aircraft/MyAircraftDir bool ok = extractedPath.rename(m_owner->path()); @@ -179,6 +184,8 @@ protected: } // extract_xxxx directory is now empty, so remove it + // (note it might not be empty if the archive contained some other + // files, but we delete those in such a case if (m_extractPath.exists()) { simgear::Dir(m_extractPath).remove(); } diff --git a/simgear/package/catalogTest1/catalog.xml b/simgear/package/catalogTest1/catalog.xml index 1b8b7b59..2a46604f 100644 --- a/simgear/package/catalogTest1/catalog.xml +++ b/simgear/package/catalogTest1/catalog.xml @@ -183,10 +183,11 @@ movies movies files for test catalog aircraft 10 - movies_6789 + movies http://localhost:2000/catalogTest1/movies?wierd=foo;bar=thing zip + movies_6789 232 e5f89c3f1ed1bdda16174c868f3c7b30 From 5710d33dbfeb1919dfa9df0d977b4cbe0379bf10 Mon Sep 17 00:00:00 2001 From: James Turner Date: Wed, 2 May 2018 23:27:34 +0100 Subject: [PATCH 06/16] Subsystem commands in the manager MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Migrate and update these commands from FlightGear’s subsystem factory. Currently disabled until subsystem-factory is removed, to avoid duplicate registration. --- simgear/structure/subsystem_mgr.cxx | 242 +++++++++++++++++++++++++++- simgear/structure/subsystem_mgr.hxx | 7 + 2 files changed, 247 insertions(+), 2 deletions(-) diff --git a/simgear/structure/subsystem_mgr.cxx b/simgear/structure/subsystem_mgr.cxx index 3205b746..c5ae8cad 100644 --- a/simgear/structure/subsystem_mgr.cxx +++ b/simgear/structure/subsystem_mgr.cxx @@ -27,6 +27,7 @@ #include "exception.hxx" #include "subsystem_mgr.hxx" +#include "commands.hxx" #include #include @@ -614,7 +615,6 @@ void SGSubsystemGroup::set_manager(SGSubsystemMgr *manager) // Implementation of SGSubsystemGroup::Member //////////////////////////////////////////////////////////////////////// - SGSubsystemGroup::Member::Member () : name(""), subsystem(0), @@ -666,10 +666,29 @@ SGSubsystemGroup::Member::update (double delta_time_sec) // Implementation of SGSubsystemMgr. //////////////////////////////////////////////////////////////////////// +namespace { + SGSubsystemMgr* global_defaultSubsystemManager = nullptr; + + void registerSubsystemCommands(); + +} // end of anonymous namespace SGSubsystemMgr::SGSubsystemMgr () : _groups(MAX_GROUPS) { + if (global_defaultSubsystemManager == nullptr) { + // register ourselves as the default + global_defaultSubsystemManager = this; + } + + // disabled until subsystemfactory is removed from FlightGear +#if 0 + auto commandManager = SGCommandMgr::instance(); + if (commandManager && !commandManager->getCommand("add-subsystem")) { + registerSubsystemCommands(); + } +#endif + for (int i = 0; i < MAX_GROUPS; i++) { auto g = new SGSubsystemGroup; g->set_manager(this); @@ -680,7 +699,24 @@ SGSubsystemMgr::SGSubsystemMgr () : SGSubsystemMgr::~SGSubsystemMgr () { _destructorActive = true; - _groups.clear(); + _groups.clear(); + + // if we were the global one, null out the pointer so it doesn't dangle. + // don't do anything clever to track multiple subsystems for now; if we + // a smarter scheme, let's wait until it's clearer what that might be. + if (global_defaultSubsystemManager == this) { + global_defaultSubsystemManager = nullptr; + } +} + +SGSubsystemMgr* SGSubsystemMgr::getManager(const std::string& id) +{ + if (id.empty()) { + return global_defaultSubsystemManager; + } + + // remove me when if/when we supprot multiple subsystem instances + throw sg_exception("multiple subsystem instances not supported yet"); } void @@ -1029,5 +1065,207 @@ SGSubsystemMgr::root_node() const return _rootNode; } +namespace { + + bool + do_check_subsystem_running(const SGPropertyNode * arg, SGPropertyNode * root) + { + auto manager = SGSubsystemMgr::getManager({}); + return (manager->get_subsystem(arg->getStringValue("name")) != nullptr); + } + + + SGSubsystemMgr::GroupType mapGroupNameToType(const std::string& s) + { + if (s == "init") return SGSubsystemMgr::INIT; + if (s == "general") return SGSubsystemMgr::GENERAL; + if (s == "fdm") return SGSubsystemMgr::FDM; + if (s == "post-fdm") return SGSubsystemMgr::POST_FDM; + if (s == "display") return SGSubsystemMgr::DISPLAY; + if (s == "sound") return SGSubsystemMgr::SOUND; + + SG_LOG(SG_GENERAL, SG_ALERT, "unrecognized subsystem group:" << s); + return SGSubsystemMgr::GENERAL; + } + + bool + do_add_subsystem (const SGPropertyNode * arg, SGPropertyNode * root) + { + auto manager = SGSubsystemMgr::getManager({}); + std::string subsystem = arg->getStringValue("subsystem"); + + // allow override of the name but defaultt o the subsystem name + std::string name = arg->getStringValue("name"); + std::string instanceName = arg->getStringValue("instance"); + + if (name.empty()) { + // default name to subsystem name, but before we parse any instance name + name = subsystem; + } + + auto separatorPos = subsystem.find(SUBSYSTEM_NAME_SEPARATOR); + if (separatorPos != std::string::npos) { + if (!instanceName.empty()) { + SG_LOG(SG_GENERAL, SG_WARN, "Specified a composite subsystem name and an instance name, please do one or the other: " + << instanceName << " and " << subsystem); + return false; + } + + instanceName = subsystem.substr(separatorPos + 1); + subsystem = subsystem.substr(0, separatorPos); + } + + SGSubsystem* sub = nullptr; + if (!instanceName.empty()) { + sub = manager->createInstance(subsystem, instanceName); + } else { + sub = manager->create(subsystem); + } + + if (!sub) + return false; + + std::string groupArg = arg->getStringValue("group"); + SGSubsystemMgr::GroupType group = SGSubsystemMgr::GENERAL; + if (!groupArg.empty()) { + group = mapGroupNameToType(groupArg); + } + + double minTime = arg->getDoubleValue("min-time-sec", 0.0); + + const auto combinedName = subsystem + SUBSYSTEM_NAME_SEPARATOR + instanceName; + manager->add(combinedName.c_str(), + sub, + group, + minTime); + + if (arg->getBoolValue("do-bind-init", false)) { + sub->bind(); + sub->init(); + } + + return true; + } + + bool do_remove_subsystem(const SGPropertyNode * arg, SGPropertyNode * root) + { + auto manager = SGSubsystemMgr::getManager({}); + std::string name = arg->getStringValue("subsystem"); + + SGSubsystem* instance = manager->get_subsystem(name); + if (!instance) { + SG_LOG(SG_GENERAL, SG_ALERT, "do_remove_subsystem: unknown subsytem:" << name); + return false; + } + + // is it safe to always call these? let's assume so! + instance->shutdown(); + instance->unbind(); + + // unplug from the manager (this also deletes the instance!) + manager->remove(name.c_str()); + return true; + } + + /** + * Built-in command: reinitialize one or more subsystems. + * + * subsystem[*]: the name(s) of the subsystem(s) to reinitialize; if + * none is specified, reinitialize all of them. + */ + bool do_reinit (const SGPropertyNode * arg, SGPropertyNode * root) + { + bool result = true; + auto manager = SGSubsystemMgr::getManager({}); + + auto subsystems = arg->getChildren("subsystem"); + if (subsystems.empty()) { + SG_LOG(SG_GENERAL, SG_INFO, "do_reinit: reinit-ing subsystem manager"); + manager->reinit(); + } else { + for (auto sub : subsystems) { + const char * name = sub->getStringValue(); + SGSubsystem* subsystem = manager->get_subsystem(name); + if (subsystem == nullptr) { + result = false; + SG_LOG( SG_GENERAL, SG_ALERT, "Subsystem " << name << " not found" ); + } else { + subsystem->reinit(); + } + } + } + + return result; + } + + /** + * Built-in command: suspend one or more subsystems. + * + * subsystem[*] - the name(s) of the subsystem(s) to suspend. + */ + bool do_suspend (const SGPropertyNode * arg, SGPropertyNode * root) + { + bool result = true; + auto manager = SGSubsystemMgr::getManager({}); + + for (auto subNode : arg->getChildren("subsystem")) { + const char * name = subNode->getStringValue(); + SGSubsystem * subsystem = manager->get_subsystem(name); + if (subsystem == nullptr) { + result = false; + SG_LOG(SG_GENERAL, SG_ALERT, "Subsystem " << name << " not found"); + } else { + subsystem->suspend(); + } + } + return result; + } + + /** + * Built-in command: suspend one or more subsystems. + * + * subsystem[*] - the name(s) of the subsystem(s) to suspend. + */ + bool do_resume (const SGPropertyNode * arg, SGPropertyNode * root) + { + bool result = true; + auto manager = SGSubsystemMgr::getManager({}); + + for (auto subNode : arg->getChildren("subsystem")) { + const char * name = subNode->getStringValue(); + SGSubsystem * subsystem = manager->get_subsystem(name); + if (subsystem == nullptr) { + result = false; + SG_LOG(SG_GENERAL, SG_ALERT, "Subsystem " << name << " not found"); + } else { + subsystem->resume(); + } + } + return result; + } + + struct CommandDef { + const char * name; + SGCommandMgr::command_t command; + }; + + CommandDef built_ins[] = { + { "add-subsystem", do_add_subsystem }, + { "remove-subsystem", do_remove_subsystem }, + { "subsystem-running", do_check_subsystem_running }, + { "reinit", do_reinit }, + { "suspend", do_suspend }, + { "resume", do_resume }, + }; + + void registerSubsystemCommands() + { + auto commandManager = SGCommandMgr::instance(); + for (auto b : built_ins) { + commandManager->addCommand(b.name, b.command); + } + } + +} // anonymous namespace implementing subsystem commands // end of subsystem_mgr.cxx diff --git a/simgear/structure/subsystem_mgr.hxx b/simgear/structure/subsystem_mgr.hxx index 0f3dd3b9..b3cd71f9 100644 --- a/simgear/structure/subsystem_mgr.hxx +++ b/simgear/structure/subsystem_mgr.hxx @@ -658,6 +658,13 @@ public: void addDelegate(Delegate * d); void removeDelegate(Delegate * d); + + /** + * @brief return a particular subsystem manager by name. Passing an + * empty string retrived the default/global subsystem manager, assuming it + * has been created. + */ + static SGSubsystemMgr* getManager(const std::string& id); private: friend class SGSubsystem; friend class SGSubsystemGroup; From b6f5b4055769abaf851f05c393247ff33fe84ce1 Mon Sep 17 00:00:00 2001 From: James Turner Date: Thu, 3 May 2018 14:29:07 +0100 Subject: [PATCH 07/16] Speculative fix for global symbol issues for Edward MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Let’s see if an explicit static at file scope is better or different to an anonymous namespace scope --- simgear/structure/subsystem_mgr.cxx | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/simgear/structure/subsystem_mgr.cxx b/simgear/structure/subsystem_mgr.cxx index c5ae8cad..9bfe1b9b 100644 --- a/simgear/structure/subsystem_mgr.cxx +++ b/simgear/structure/subsystem_mgr.cxx @@ -668,9 +668,9 @@ SGSubsystemGroup::Member::update (double delta_time_sec) namespace { SGSubsystemMgr* global_defaultSubsystemManager = nullptr; - + void registerSubsystemCommands(); - + } // end of anonymous namespace SGSubsystemMgr::SGSubsystemMgr () : @@ -912,19 +912,19 @@ namespace { }; using SybsystemRegistrationVec = std::vector; - - SybsystemRegistrationVec global_registrations; - - SybsystemRegistrationVec::const_iterator findRegistration(const std::string& name) - { - auto it = std::find_if(global_registrations.begin(), - global_registrations.end(), - [name](const RegisteredSubsystemData& d) - { return name == d.name; }); - return it; - } } // of anonymous namespace +static SybsystemRegistrationVec global_registrations; + +SybsystemRegistrationVec::const_iterator findRegistration(const std::string& name) +{ + auto it = std::find_if(global_registrations.begin(), + global_registrations.end(), + [name](const RegisteredSubsystemData& d) + { return name == d.name; }); + return it; +} + void SGSubsystemMgr::registerSubsystem(const std::string& name, SubsystemFactoryFunctor f, GroupType group, From fd4ca1c811212c361128b5d1857a15c11a0f9ecb Mon Sep 17 00:00:00 2001 From: Edward d'Auvergne Date: Fri, 4 May 2018 09:02:08 +0200 Subject: [PATCH 08/16] Revert "Speculative fix for global symbol issues for Edward" This reverts commit b6f5b4055769abaf851f05c393247ff33fe84ce1. The changes did not solve the static init vector allocation issue. --- simgear/structure/subsystem_mgr.cxx | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/simgear/structure/subsystem_mgr.cxx b/simgear/structure/subsystem_mgr.cxx index 9bfe1b9b..c5ae8cad 100644 --- a/simgear/structure/subsystem_mgr.cxx +++ b/simgear/structure/subsystem_mgr.cxx @@ -668,9 +668,9 @@ SGSubsystemGroup::Member::update (double delta_time_sec) namespace { SGSubsystemMgr* global_defaultSubsystemManager = nullptr; - + void registerSubsystemCommands(); - + } // end of anonymous namespace SGSubsystemMgr::SGSubsystemMgr () : @@ -912,19 +912,19 @@ namespace { }; using SybsystemRegistrationVec = std::vector; + + SybsystemRegistrationVec global_registrations; + + SybsystemRegistrationVec::const_iterator findRegistration(const std::string& name) + { + auto it = std::find_if(global_registrations.begin(), + global_registrations.end(), + [name](const RegisteredSubsystemData& d) + { return name == d.name; }); + return it; + } } // of anonymous namespace -static SybsystemRegistrationVec global_registrations; - -SybsystemRegistrationVec::const_iterator findRegistration(const std::string& name) -{ - auto it = std::find_if(global_registrations.begin(), - global_registrations.end(), - [name](const RegisteredSubsystemData& d) - { return name == d.name; }); - return it; -} - void SGSubsystemMgr::registerSubsystem(const std::string& name, SubsystemFactoryFunctor f, GroupType group, From a232565b3ea2cde7212916ac70b4d94b1399be73 Mon Sep 17 00:00:00 2001 From: Edward d'Auvergne Date: Fri, 4 May 2018 09:09:15 +0200 Subject: [PATCH 09/16] SGSubsystemMgr: Bug fix for the global_registrations vector. The vector is now a static function variable that is returned by reference by the new getGlobalRegistrations() function, which remains in the anonymous namespace. This solves the issue of the global_registrations vector being populated during static init, but then been subsequently allocated and hence reset at the end of static init. --- simgear/structure/subsystem_mgr.cxx | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/simgear/structure/subsystem_mgr.cxx b/simgear/structure/subsystem_mgr.cxx index c5ae8cad..80c7ef0a 100644 --- a/simgear/structure/subsystem_mgr.cxx +++ b/simgear/structure/subsystem_mgr.cxx @@ -913,10 +913,15 @@ namespace { using SybsystemRegistrationVec = std::vector; - SybsystemRegistrationVec global_registrations; - + SybsystemRegistrationVec &getGlobalRegistrations() + { + static SybsystemRegistrationVec global_registrations; + return global_registrations; + } + SybsystemRegistrationVec::const_iterator findRegistration(const std::string& name) { + auto &global_registrations = getGlobalRegistrations(); auto it = std::find_if(global_registrations.begin(), global_registrations.end(), [name](const RegisteredSubsystemData& d) @@ -932,6 +937,7 @@ void SGSubsystemMgr::registerSubsystem(const std::string& name, double updateInterval, std::initializer_list deps) { + auto &global_registrations = getGlobalRegistrations(); if (findRegistration(name) != global_registrations.end()) { throw sg_exception("duplicate subsystem registration for: " + name); } @@ -945,6 +951,7 @@ void SGSubsystemMgr::registerSubsystem(const std::string& name, auto SGSubsystemMgr::defaultGroupFor(const char* name) -> GroupType { auto it = findRegistration(name); + auto &global_registrations = getGlobalRegistrations(); if (it == global_registrations.end()) { throw sg_exception("unknown subsystem registration for: " + std::string(name)); } @@ -955,6 +962,7 @@ auto SGSubsystemMgr::defaultGroupFor(const char* name) -> GroupType double SGSubsystemMgr::defaultUpdateIntervalFor(const char* name) { auto it = findRegistration(name); + auto &global_registrations = getGlobalRegistrations(); if (it == global_registrations.end()) { throw sg_exception("unknown subsystem registration for: " + std::string(name)); } @@ -966,6 +974,7 @@ const SGSubsystemMgr::DependencyVec& SGSubsystemMgr::dependsFor(const char* name) { auto it = findRegistration(name); + auto &global_registrations = getGlobalRegistrations(); if (it == global_registrations.end()) { throw sg_exception("unknown subsystem registration for: " + std::string(name)); } @@ -977,6 +986,7 @@ SGSubsystemRef SGSubsystemMgr::create(const std::string& name) { auto it = findRegistration(name); + auto &global_registrations = getGlobalRegistrations(); if (it == global_registrations.end()) { return {}; // or should this throw with a 'not registered'? } @@ -998,6 +1008,7 @@ SGSubsystemRef SGSubsystemMgr::createInstance(const std::string& name, const std::string& instanceName) { auto it = findRegistration(name); + auto &global_registrations = getGlobalRegistrations(); if (it == global_registrations.end()) { return {}; // or should this throw with a 'not registered'? } From f5ff969cd497355dcf2e3b58d98ab053fea7cb39 Mon Sep 17 00:00:00 2001 From: James Turner Date: Tue, 8 May 2018 06:50:15 +0100 Subject: [PATCH 10/16] Warning improvements when requesting bad URLs Found while debugging some issues with add-default-catalog flow in the launcher. --- simgear/io/HTTPClient.cxx | 7 ++++++- simgear/package/Root.cxx | 5 +++++ 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/simgear/io/HTTPClient.cxx b/simgear/io/HTTPClient.cxx index eab0258c..fe6fa737 100644 --- a/simgear/io/HTTPClient.cxx +++ b/simgear/io/HTTPClient.cxx @@ -242,8 +242,13 @@ void Client::makeRequest(const Request_ptr& r) if( r->isComplete() ) return; + if (r->url().empty()) { + r->setFailure(EINVAL, "no URL specified on request"); + return; + } + if( r->url().find("://") == std::string::npos ) { - r->setFailure(EINVAL, "malformed URL"); + r->setFailure(EINVAL, "malformed URL: '" + r->url() + "'"); return; } diff --git a/simgear/package/Root.cxx b/simgear/package/Root.cxx index 226e632e..d7e06b4f 100644 --- a/simgear/package/Root.cxx +++ b/simgear/package/Root.cxx @@ -778,6 +778,11 @@ bool Root::removeCatalogById(const std::string& aId) void Root::requestThumbnailData(const std::string& aUrl) { + if (aUrl.empty()) { + SG_LOG(SG_GENERAL, SG_DEV_WARN, "requestThumbnailData: empty URL requested"); + return; + } + auto it = d->thumbnailCache.find(aUrl); if (it == d->thumbnailCache.end()) { bool cachedOnDisk = d->checkPersistentCache(aUrl); From 9755110ec7d5030ec2a63c4757eceacd9d32f7cb Mon Sep 17 00:00:00 2001 From: James Turner Date: Wed, 9 May 2018 10:15:07 +0100 Subject: [PATCH 11/16] Packages: Remove deprecation warnings for now Probably a bit over-zealous for these. --- simgear/package/Package.hxx | 11 +++-------- 1 file changed, 3 insertions(+), 8 deletions(-) diff --git a/simgear/package/Package.hxx b/simgear/package/Package.hxx index 5f696dcc..ac38f758 100644 --- a/simgear/package/Package.hxx +++ b/simgear/package/Package.hxx @@ -99,10 +99,8 @@ public: /** * human-readable name - note this is probably not localised, * although this is not ruled out for the future. - * - * Deprecated - please use nameForVariant */ - SG_DEPRECATED(std::string name() const); + std::string name() const; /** * Human readable name of a variant @@ -112,12 +110,9 @@ public: std::string nameForVariant(const unsigned int vIndex) const; /** - * syntactic sugar to get the localised description - * - * Deprecated - please use getLocalisedProp to get the variant-specific - * description. + * syntactic sugar to get the localised description of the main aircraft */ - SG_DEPRECATED(std::string description() const); + std::string description() const; /** * access the raw property data in the package From 66cfa800beae582c4d447eeeec5276be9f18edbf Mon Sep 17 00:00:00 2001 From: Edward d'Auvergne Date: Mon, 14 May 2018 14:05:04 +0200 Subject: [PATCH 12/16] SGEventMgr: Reset the shutdown flag on init as a reset does not call the ctor. This fixes the reset process that was broken by dfed2184f1e280281277030a8a94e3e0dd7dc326. --- simgear/structure/event_mgr.cxx | 3 +++ 1 file changed, 3 insertions(+) diff --git a/simgear/structure/event_mgr.cxx b/simgear/structure/event_mgr.cxx index d5ffd01e..12e56d5d 100644 --- a/simgear/structure/event_mgr.cxx +++ b/simgear/structure/event_mgr.cxx @@ -69,6 +69,9 @@ void SGEventMgr::init() return; } + // The event manager dtor and ctor are not called on reset, so reset the flag here. + _shutdown = false; + _inited = true; } From 2ba5676eb0e4a893e5c387c9898e4cec5a597e13 Mon Sep 17 00:00:00 2001 From: Edward d'Auvergne Date: Mon, 14 May 2018 21:36:54 +0200 Subject: [PATCH 13/16] SGTime: Stripped trailing '\n' from some debugging messages. --- simgear/timing/sg_time.cxx | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/simgear/timing/sg_time.cxx b/simgear/timing/sg_time.cxx index 2282db93..83b22aec 100644 --- a/simgear/timing/sg_time.cxx +++ b/simgear/timing/sg_time.cxx @@ -72,10 +72,14 @@ void SGTime::init( const SGGeod& location, const SGPath& root, time_t init_time cur_time = time(NULL); } + char* gmt = asctime(gmtime(&cur_time)); + char* local = asctime(localtime(&cur_time)); + gmt[strlen(gmt) - 1] = '\0'; + local[strlen(local) - 1] = '\0'; SG_LOG( SG_EVENT, SG_DEBUG, - "Current greenwich mean time = " << asctime(gmtime(&cur_time))); + "Current greenwich mean time = " << gmt); SG_LOG( SG_EVENT, SG_DEBUG, - "Current local time = " << asctime(localtime(&cur_time))); + "Current local time = " << local); if ( !root.isNull()) { if (!static_tzContainer.get()) { From d92a289c2534ede31998f1c4b55ee1286cf981da Mon Sep 17 00:00:00 2001 From: xDraconian Date: Thu, 17 May 2018 01:30:32 -0500 Subject: [PATCH 14/16] Bug fix: svg dirty flag --- simgear/canvas/elements/CanvasPath.cxx | 2 ++ 1 file changed, 2 insertions(+) diff --git a/simgear/canvas/elements/CanvasPath.cxx b/simgear/canvas/elements/CanvasPath.cxx index c23f1e49..5fd8b775 100644 --- a/simgear/canvas/elements/CanvasPath.cxx +++ b/simgear/canvas/elements/CanvasPath.cxx @@ -900,8 +900,10 @@ namespace canvas else if( name == "coord" ) _attributes_dirty |= COORDS; else if ( name == "svg") + { _hasSVG = true; _attributes_dirty |= SVG; + } } //---------------------------------------------------------------------------- From 5ed4fbd4a3ac8feca447a84ec973c0491a0d9545 Mon Sep 17 00:00:00 2001 From: Torsten Dreyer Date: Sat, 19 May 2018 21:02:35 +0200 Subject: [PATCH 15/16] new version: 2018.2.1 --- version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version b/version index 26b1d26a..2a72d53c 100644 --- a/version +++ b/version @@ -1 +1 @@ -2018.2.0 +2018.2.1 From 94a1156a6bef17ec0ba7071c26ce8b28e0792ca9 Mon Sep 17 00:00:00 2001 From: Torsten Dreyer Date: Sat, 19 May 2018 21:02:35 +0200 Subject: [PATCH 16/16] new version: 2018.3.0 --- version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version b/version index 2a72d53c..ddab0701 100644 --- a/version +++ b/version @@ -1 +1 @@ -2018.2.1 +2018.3.0