void Run() { while (active) { boost::interprocess::scoped_lock<storage::SharedBarrier::mutex_type> current_region_lock(barrier.GetMutex()); while (active && timestamp == barrier.GetTimestamp()) { barrier.Wait(current_region_lock); } if (timestamp != barrier.GetTimestamp()) { facade = std::make_shared<datafacade::ContiguousInternalMemoryDataFacade>( std::make_unique<datafacade::SharedMemoryAllocator>(barrier.GetRegion())); timestamp = barrier.GetTimestamp(); util::Log() << "updated facade to region " << storage::regionToString(barrier.GetRegion()) << " with timestamp " << timestamp; } } util::Log() << "DataWatchdog thread stopped"; }
bool Engine<routing_algorithms::corech::Algorithm>::CheckCompability(const EngineConfig &config) { if (!Engine<routing_algorithms::ch::Algorithm>::CheckCompability(config)) { return false; } if (config.use_shared_memory) { storage::SharedMonitor<storage::SharedDataTimestamp> barrier; using mutex_type = typename decltype(barrier)::mutex_type; boost::interprocess::scoped_lock<mutex_type> current_region_lock(barrier.get_mutex()); auto mem = storage::makeSharedMemory(barrier.data().region); auto layout = reinterpret_cast<storage::DataLayout *>(mem->Ptr()); return layout->GetBlockSize(storage::DataLayout::CH_CORE_MARKER_0) > sizeof(std::uint64_t) + sizeof(util::FingerPrint); } else { if (!boost::filesystem::exists(config.storage_config.GetPath(".osrm.core"))) return false; storage::io::FileReader in(config.storage_config.GetPath(".osrm.core"), storage::io::FileReader::VerifyFingerprint); in.ReadElementCount64(); // number of core markers const auto number_of_core_markers = in.ReadElementCount64(); return number_of_core_markers > 0; } }
DataWatchdog() : barrier(boost::interprocess::open_only), active(true), timestamp(0) { // create the initial facade before launching the watchdog thread { boost::interprocess::scoped_lock<storage::SharedBarrier::mutex_type> current_region_lock(barrier.GetMutex()); facade = std::make_shared<datafacade::ContiguousInternalMemoryDataFacade>( std::make_unique<datafacade::SharedMemoryAllocator>(barrier.GetRegion())); timestamp = barrier.GetTimestamp(); } watcher = std::thread(&DataWatchdog::Run, this); }
bool Engine<routing_algorithms::mld::Algorithm>::CheckCompability(const EngineConfig &config) { if (config.use_shared_memory) { storage::SharedMonitor<storage::SharedDataTimestamp> barrier; using mutex_type = typename decltype(barrier)::mutex_type; boost::interprocess::scoped_lock<mutex_type> current_region_lock(barrier.get_mutex()); auto mem = storage::makeSharedMemory(barrier.data().region); auto layout = reinterpret_cast<storage::DataLayout *>(mem->Ptr()); return layout->GetBlockSize(storage::DataLayout::MLD_PARTITION) > 0; } else { if (!boost::filesystem::exists(config.storage_config.GetPath(".osrm.partition"))) return false; storage::io::FileReader in(config.storage_config.GetPath(".osrm.partition"), storage::io::FileReader::VerifyFingerprint); auto size = in.GetSize(); return size > 0; } }
OSRM::OSRM(engine::EngineConfig &config) { using CH = engine::routing_algorithms::ch::Algorithm; using MLD = engine::routing_algorithms::mld::Algorithm; // First, check that necessary core data is available if (!config.use_shared_memory && !config.storage_config.IsValid()) { throw util::exception("Required files are missing, cannot continue. Have all the " "pre-processing steps been run?"); } else if (config.use_shared_memory) { storage::SharedMonitor<storage::SharedDataTimestamp> barrier; using mutex_type = typename decltype(barrier)::mutex_type; boost::interprocess::scoped_lock<mutex_type> current_region_lock(barrier.get_mutex()); auto mem = storage::makeSharedMemory(barrier.data().region); auto layout = reinterpret_cast<storage::DataLayout *>(mem->Ptr()); if (layout->GetBlockSize(storage::DataLayout::NAME_CHAR_DATA) == 0) throw util::exception( "No name data loaded, cannot continue. Have you run osrm-datastore to load data?"); } // Now, check that the algorithm requested can be used with the data // that's available. if (config.algorithm == EngineConfig::Algorithm::CH || config.algorithm == EngineConfig::Algorithm::CoreCH) { if (config.algorithm == EngineConfig::Algorithm::CoreCH) { util::Log(logWARNING) << "Using CoreCH is deprecated. Falling back to CH"; config.algorithm = EngineConfig::Algorithm::CH; } bool ch_compatible = engine::Engine<CH>::CheckCompatibility(config); // throw error if dataset is not usable with CH if (config.algorithm == EngineConfig::Algorithm::CH && !ch_compatible) { throw util::exception("Dataset is not compatible with CH"); } } else if (config.algorithm == EngineConfig::Algorithm::MLD) { bool mld_compatible = engine::Engine<MLD>::CheckCompatibility(config); // throw error if dataset is not usable with MLD if (!mld_compatible) { throw util::exception("Dataset is not compatible with MLD."); } } switch (config.algorithm) { case EngineConfig::Algorithm::CH: engine_ = std::make_unique<engine::Engine<CH>>(config); break; case EngineConfig::Algorithm::MLD: engine_ = std::make_unique<engine::Engine<MLD>>(config); break; default: util::exception("Algorithm not implemented!"); } }