Merge pull request #1741 from Project-OSRM/oom_messages

Catch `std::bad_alloc` at the top and translate to human readable messages
This commit is contained in:
Patrick Niklaus 2015-10-19 19:29:53 +02:00
commit fca4aeb50b
4 changed files with 574 additions and 560 deletions

View File

@ -62,6 +62,7 @@ using QueryGraph = StaticGraph<QueryEdge::EdgeData>;
#include <fstream> #include <fstream>
#include <string> #include <string>
#include <new>
// delete a shared memory region. report warning if it could not be deleted // delete a shared memory region. report warning if it could not be deleted
void delete_region(const SharedDataType region) void delete_region(const SharedDataType region)
@ -93,22 +94,20 @@ void delete_region(const SharedDataType region)
} }
} }
int main(const int argc, const char *argv[]) int main(const int argc, const char *argv[]) try
{ {
LogPolicy::GetInstance().Unmute(); LogPolicy::GetInstance().Unmute();
SharedBarriers barrier; SharedBarriers barrier;
try
{
#ifdef __linux__ #ifdef __linux__
// try to disable swapping on Linux // try to disable swapping on Linux
const bool lock_flags = MCL_CURRENT | MCL_FUTURE; const bool lock_flags = MCL_CURRENT | MCL_FUTURE;
if (-1 == mlockall(lock_flags)) if (-1 == mlockall(lock_flags))
{ {
SimpleLogger().Write(logWARNING) << "Process " << argv[0] SimpleLogger().Write(logWARNING) << "Process " << argv[0] << " could not request RAM lock";
<< " could not request RAM lock";
} }
#endif #endif
try try
{ {
boost::interprocess::scoped_lock<boost::interprocess::named_mutex> pending_lock( boost::interprocess::scoped_lock<boost::interprocess::named_mutex> pending_lock(
@ -119,20 +118,13 @@ int main(const int argc, const char *argv[])
// hard unlock in case of any exception. // hard unlock in case of any exception.
barrier.pending_update_mutex.unlock(); barrier.pending_update_mutex.unlock();
} }
}
catch (const std::exception &e)
{
SimpleLogger().Write(logWARNING) << "[exception] " << e.what();
}
try
{
SimpleLogger().Write(logDEBUG) << "Checking input parameters"; SimpleLogger().Write(logDEBUG) << "Checking input parameters";
ServerPaths server_paths; ServerPaths server_paths;
if (!GenerateDataStoreOptions(argc, argv, server_paths)) if (!GenerateDataStoreOptions(argc, argv, server_paths))
{ {
return 0; return EXIT_SUCCESS;
} }
if (server_paths.find("hsgrdata") == server_paths.end()) if (server_paths.find("hsgrdata") == server_paths.end())
@ -227,8 +219,7 @@ int main(const int argc, const char *argv[])
}(); }();
// Allocate a memory layout in shared memory, deallocate previous // Allocate a memory layout in shared memory, deallocate previous
SharedMemory *layout_memory = SharedMemory *layout_memory = SharedMemoryFactory::Get(layout_region, sizeof(SharedDataLayout));
SharedMemoryFactory::Get(layout_region, sizeof(SharedDataLayout));
SharedDataLayout *shared_layout_ptr = new (layout_memory->Ptr()) SharedDataLayout(); SharedDataLayout *shared_layout_ptr = new (layout_memory->Ptr()) SharedDataLayout();
shared_layout_ptr->SetBlockSize<char>(SharedDataLayout::FILE_INDEX_PATH, shared_layout_ptr->SetBlockSize<char>(SharedDataLayout::FILE_INDEX_PATH,
@ -292,15 +283,15 @@ int main(const int argc, const char *argv[])
hsgr_input_stream.read((char *)&number_of_graph_nodes, sizeof(unsigned)); hsgr_input_stream.read((char *)&number_of_graph_nodes, sizeof(unsigned));
BOOST_ASSERT_MSG((0 != number_of_graph_nodes), "number of nodes is zero"); BOOST_ASSERT_MSG((0 != number_of_graph_nodes), "number of nodes is zero");
shared_layout_ptr->SetBlockSize<QueryGraph::NodeArrayEntry>( shared_layout_ptr->SetBlockSize<QueryGraph::NodeArrayEntry>(SharedDataLayout::GRAPH_NODE_LIST,
SharedDataLayout::GRAPH_NODE_LIST, number_of_graph_nodes); number_of_graph_nodes);
// load graph edge size // load graph edge size
unsigned number_of_graph_edges = 0; unsigned number_of_graph_edges = 0;
hsgr_input_stream.read((char *)&number_of_graph_edges, sizeof(unsigned)); hsgr_input_stream.read((char *)&number_of_graph_edges, sizeof(unsigned));
// BOOST_ASSERT_MSG(0 != number_of_graph_edges, "number of graph edges is zero"); // BOOST_ASSERT_MSG(0 != number_of_graph_edges, "number of graph edges is zero");
shared_layout_ptr->SetBlockSize<QueryGraph::EdgeArrayEntry>( shared_layout_ptr->SetBlockSize<QueryGraph::EdgeArrayEntry>(SharedDataLayout::GRAPH_EDGE_LIST,
SharedDataLayout::GRAPH_EDGE_LIST, number_of_graph_edges); number_of_graph_edges);
// load rsearch tree size // load rsearch tree size
boost::filesystem::ifstream tree_node_file(ram_index_path, std::ios::binary); boost::filesystem::ifstream tree_node_file(ram_index_path, std::ios::binary);
@ -316,8 +307,7 @@ int main(const int argc, const char *argv[])
boost::filesystem::ifstream timestamp_stream(timestamp_path); boost::filesystem::ifstream timestamp_stream(timestamp_path);
if (!timestamp_stream) if (!timestamp_stream)
{ {
SimpleLogger().Write(logWARNING) << timestamp_path SimpleLogger().Write(logWARNING) << timestamp_path << " not found. setting to default";
<< " not found. setting to default";
} }
else else
{ {
@ -340,7 +330,8 @@ int main(const int argc, const char *argv[])
uint32_t number_of_core_markers = 0; uint32_t number_of_core_markers = 0;
core_marker_file.read((char *)&number_of_core_markers, sizeof(uint32_t)); core_marker_file.read((char *)&number_of_core_markers, sizeof(uint32_t));
shared_layout_ptr->SetBlockSize<unsigned>(SharedDataLayout::CORE_MARKER, number_of_core_markers); shared_layout_ptr->SetBlockSize<unsigned>(SharedDataLayout::CORE_MARKER,
number_of_core_markers);
// load coordinate size // load coordinate size
boost::filesystem::ifstream nodes_input_stream(nodes_data_path, std::ios::binary); boost::filesystem::ifstream nodes_input_stream(nodes_data_path, std::ios::binary);
@ -350,22 +341,21 @@ int main(const int argc, const char *argv[])
coordinate_list_size); coordinate_list_size);
// load geometries sizes // load geometries sizes
std::ifstream geometry_input_stream(geometries_data_path.string().c_str(), std::ifstream geometry_input_stream(geometries_data_path.string().c_str(), std::ios::binary);
std::ios::binary);
unsigned number_of_geometries_indices = 0; unsigned number_of_geometries_indices = 0;
unsigned number_of_compressed_geometries = 0; unsigned number_of_compressed_geometries = 0;
geometry_input_stream.read((char *)&number_of_geometries_indices, sizeof(unsigned)); geometry_input_stream.read((char *)&number_of_geometries_indices, sizeof(unsigned));
shared_layout_ptr->SetBlockSize<unsigned>(SharedDataLayout::GEOMETRIES_INDEX, shared_layout_ptr->SetBlockSize<unsigned>(SharedDataLayout::GEOMETRIES_INDEX,
number_of_geometries_indices); number_of_geometries_indices);
boost::iostreams::seek(geometry_input_stream, boost::iostreams::seek(geometry_input_stream, number_of_geometries_indices * sizeof(unsigned),
number_of_geometries_indices * sizeof(unsigned), BOOST_IOS::cur); BOOST_IOS::cur);
geometry_input_stream.read((char *)&number_of_compressed_geometries, sizeof(unsigned)); geometry_input_stream.read((char *)&number_of_compressed_geometries, sizeof(unsigned));
shared_layout_ptr->SetBlockSize<unsigned>(SharedDataLayout::GEOMETRIES_LIST, shared_layout_ptr->SetBlockSize<unsigned>(SharedDataLayout::GEOMETRIES_LIST,
number_of_compressed_geometries); number_of_compressed_geometries);
// allocate shared memory block // allocate shared memory block
SimpleLogger().Write() << "allocating shared memory of " SimpleLogger().Write() << "allocating shared memory of " << shared_layout_ptr->GetSizeOfLayout()
<< shared_layout_ptr->GetSizeOfLayout() << " bytes"; << " bytes";
SharedMemory *shared_memory = SharedMemory *shared_memory =
SharedMemoryFactory::Get(data_region, shared_layout_ptr->GetSizeOfLayout()); SharedMemoryFactory::Get(data_region, shared_layout_ptr->GetSizeOfLayout());
char *shared_memory_ptr = static_cast<char *>(shared_memory->Ptr()); char *shared_memory_ptr = static_cast<char *>(shared_memory->Ptr());
@ -431,8 +421,7 @@ int main(const int argc, const char *argv[])
TravelMode *travel_mode_ptr = shared_layout_ptr->GetBlockPtr<TravelMode, true>( TravelMode *travel_mode_ptr = shared_layout_ptr->GetBlockPtr<TravelMode, true>(
shared_memory_ptr, SharedDataLayout::TRAVEL_MODE); shared_memory_ptr, SharedDataLayout::TRAVEL_MODE);
TurnInstruction *turn_instructions_ptr = TurnInstruction *turn_instructions_ptr = shared_layout_ptr->GetBlockPtr<TurnInstruction, true>(
shared_layout_ptr->GetBlockPtr<TurnInstruction, true>(
shared_memory_ptr, SharedDataLayout::TURN_INSTRUCTION); shared_memory_ptr, SharedDataLayout::TURN_INSTRUCTION);
unsigned *geometries_indicator_ptr = shared_layout_ptr->GetBlockPtr<unsigned, true>( unsigned *geometries_indicator_ptr = shared_layout_ptr->GetBlockPtr<unsigned, true>(
@ -508,13 +497,13 @@ int main(const int argc, const char *argv[])
nodes_input_stream.close(); nodes_input_stream.close();
// store timestamp // store timestamp
char *timestamp_ptr = shared_layout_ptr->GetBlockPtr<char, true>( char *timestamp_ptr =
shared_memory_ptr, SharedDataLayout::TIMESTAMP); shared_layout_ptr->GetBlockPtr<char, true>(shared_memory_ptr, SharedDataLayout::TIMESTAMP);
std::copy(m_timestamp.c_str(), m_timestamp.c_str() + m_timestamp.length(), timestamp_ptr); std::copy(m_timestamp.c_str(), m_timestamp.c_str() + m_timestamp.length(), timestamp_ptr);
// store search tree portion of rtree // store search tree portion of rtree
char *rtree_ptr = shared_layout_ptr->GetBlockPtr<char, true>( char *rtree_ptr = shared_layout_ptr->GetBlockPtr<char, true>(shared_memory_ptr,
shared_memory_ptr, SharedDataLayout::R_SEARCH_TREE); SharedDataLayout::R_SEARCH_TREE);
if (tree_size > 0) if (tree_size > 0)
{ {
@ -524,7 +513,8 @@ int main(const int argc, const char *argv[])
// load core markers // load core markers
std::vector<char> unpacked_core_markers(number_of_core_markers); std::vector<char> unpacked_core_markers(number_of_core_markers);
core_marker_file.read((char *)unpacked_core_markers.data(), sizeof(char)*number_of_core_markers); core_marker_file.read((char *)unpacked_core_markers.data(),
sizeof(char) * number_of_core_markers);
unsigned *core_marker_ptr = shared_layout_ptr->GetBlockPtr<unsigned, true>( unsigned *core_marker_ptr = shared_layout_ptr->GetBlockPtr<unsigned, true>(
shared_memory_ptr, SharedDataLayout::CORE_MARKER); shared_memory_ptr, SharedDataLayout::CORE_MARKER);
@ -557,8 +547,7 @@ int main(const int argc, const char *argv[])
shared_memory_ptr, SharedDataLayout::GRAPH_NODE_LIST); shared_memory_ptr, SharedDataLayout::GRAPH_NODE_LIST);
if (shared_layout_ptr->GetBlockSize(SharedDataLayout::GRAPH_NODE_LIST) > 0) if (shared_layout_ptr->GetBlockSize(SharedDataLayout::GRAPH_NODE_LIST) > 0)
{ {
hsgr_input_stream.read( hsgr_input_stream.read((char *)graph_node_list_ptr,
(char *)graph_node_list_ptr,
shared_layout_ptr->GetBlockSize(SharedDataLayout::GRAPH_NODE_LIST)); shared_layout_ptr->GetBlockSize(SharedDataLayout::GRAPH_NODE_LIST));
} }
@ -568,8 +557,7 @@ int main(const int argc, const char *argv[])
shared_memory_ptr, SharedDataLayout::GRAPH_EDGE_LIST); shared_memory_ptr, SharedDataLayout::GRAPH_EDGE_LIST);
if (shared_layout_ptr->GetBlockSize(SharedDataLayout::GRAPH_EDGE_LIST) > 0) if (shared_layout_ptr->GetBlockSize(SharedDataLayout::GRAPH_EDGE_LIST) > 0)
{ {
hsgr_input_stream.read( hsgr_input_stream.read((char *)graph_edge_list_ptr,
(char *)graph_edge_list_ptr,
shared_layout_ptr->GetBlockSize(SharedDataLayout::GRAPH_EDGE_LIST)); shared_layout_ptr->GetBlockSize(SharedDataLayout::GRAPH_EDGE_LIST));
} }
hsgr_input_stream.close(); hsgr_input_stream.close();
@ -597,11 +585,15 @@ int main(const int argc, const char *argv[])
SimpleLogger().Write() << "all data loaded"; SimpleLogger().Write() << "all data loaded";
shared_layout_ptr->PrintInformation(); shared_layout_ptr->PrintInformation();
} }
catch (const std::exception &e) catch (const std::bad_alloc &e)
{ {
SimpleLogger().Write(logWARNING) << "caught exception: " << e.what(); SimpleLogger().Write(logWARNING) << "[exception] " << e.what();
} SimpleLogger().Write(logWARNING) << "Please provide more memory or disable locking the virtual "
"address space (note: this makes OSRM swap, i.e. slow)";
return 0; return EXIT_FAILURE;
}
catch (const std::exception &e)
{
SimpleLogger().Write(logWARNING) << "caught exception: " << e.what();
} }

View File

@ -31,12 +31,12 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include <boost/filesystem.hpp> #include <boost/filesystem.hpp>
#include <cstdlib>
#include <exception> #include <exception>
#include <new>
int main(int argc, char *argv[]) int main(int argc, char *argv[]) try
{ {
try
{
LogPolicy::GetInstance().Unmute(); LogPolicy::GetInstance().Unmute();
ExtractorConfig extractor_config; ExtractorConfig extractor_config;
@ -44,12 +44,12 @@ int main(int argc, char *argv[])
if (return_code::fail == result) if (return_code::fail == result)
{ {
return 1; return EXIT_FAILURE;
} }
if (return_code::exit == result) if (return_code::exit == result)
{ {
return 0; return EXIT_SUCCESS;
} }
ExtractorOptions::GenerateOutputFilesNames(extractor_config); ExtractorOptions::GenerateOutputFilesNames(extractor_config);
@ -57,27 +57,33 @@ int main(int argc, char *argv[])
if (1 > extractor_config.requested_num_threads) if (1 > extractor_config.requested_num_threads)
{ {
SimpleLogger().Write(logWARNING) << "Number of threads must be 1 or larger"; SimpleLogger().Write(logWARNING) << "Number of threads must be 1 or larger";
return 1; return EXIT_FAILURE;
} }
if (!boost::filesystem::is_regular_file(extractor_config.input_path)) if (!boost::filesystem::is_regular_file(extractor_config.input_path))
{ {
SimpleLogger().Write(logWARNING) SimpleLogger().Write(logWARNING) << "Input file " << extractor_config.input_path.string()
<< "Input file " << extractor_config.input_path.string() << " not found!"; << " not found!";
return 1; return EXIT_FAILURE;
} }
if (!boost::filesystem::is_regular_file(extractor_config.profile_path)) if (!boost::filesystem::is_regular_file(extractor_config.profile_path))
{ {
SimpleLogger().Write(logWARNING) << "Profile " << extractor_config.profile_path.string() SimpleLogger().Write(logWARNING) << "Profile " << extractor_config.profile_path.string()
<< " not found!"; << " not found!";
return 1; return EXIT_FAILURE;
} }
return extractor(extractor_config).run(); return extractor(extractor_config).run();
} }
catch (const std::exception &e) catch (const std::bad_alloc &e)
{ {
SimpleLogger().Write(logWARNING) << "[exception] " << e.what(); SimpleLogger().Write(logWARNING) << "[exception] " << e.what();
return 1; SimpleLogger().Write(logWARNING)
} << "Please provide more memory or consider using a larger swapfile";
return EXIT_FAILURE;
}
catch (const std::exception &e)
{
SimpleLogger().Write(logWARNING) << "[exception] " << e.what();
return EXIT_FAILURE;
} }

View File

@ -33,13 +33,13 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include <tbb/task_scheduler_init.h> #include <tbb/task_scheduler_init.h>
#include <cstdlib>
#include <exception> #include <exception>
#include <ostream> #include <ostream>
#include <new>
int main(int argc, char *argv[]) int main(int argc, char *argv[]) try
{ {
try
{
LogPolicy::GetInstance().Unmute(); LogPolicy::GetInstance().Unmute();
ContractorConfig contractor_config; ContractorConfig contractor_config;
@ -47,12 +47,12 @@ int main(int argc, char *argv[])
if (return_code::fail == result) if (return_code::fail == result)
{ {
return 1; return EXIT_FAILURE;
} }
if (return_code::exit == result) if (return_code::exit == result)
{ {
return 0; return EXIT_SUCCESS;
} }
ContractorOptions::GenerateOutputFilesNames(contractor_config); ContractorOptions::GenerateOutputFilesNames(contractor_config);
@ -60,7 +60,7 @@ int main(int argc, char *argv[])
if (1 > contractor_config.requested_num_threads) if (1 > contractor_config.requested_num_threads)
{ {
SimpleLogger().Write(logWARNING) << "Number of threads must be 1 or larger"; SimpleLogger().Write(logWARNING) << "Number of threads must be 1 or larger";
return 1; return EXIT_FAILURE;
} }
const unsigned recommended_num_threads = tbb::task_scheduler_init::default_num_threads(); const unsigned recommended_num_threads = tbb::task_scheduler_init::default_num_threads();
@ -76,27 +76,34 @@ int main(int argc, char *argv[])
{ {
SimpleLogger().Write(logWARNING) SimpleLogger().Write(logWARNING)
<< "Input file " << contractor_config.osrm_input_path.string() << " not found!"; << "Input file " << contractor_config.osrm_input_path.string() << " not found!";
return 1; return EXIT_FAILURE;
} }
if (!boost::filesystem::is_regular_file(contractor_config.profile_path)) if (!boost::filesystem::is_regular_file(contractor_config.profile_path))
{ {
SimpleLogger().Write(logWARNING) << "Profile " << contractor_config.profile_path.string() SimpleLogger().Write(logWARNING) << "Profile " << contractor_config.profile_path.string()
<< " not found!"; << " not found!";
return 1; return EXIT_FAILURE;
} }
SimpleLogger().Write() << "Input file: " << contractor_config.osrm_input_path.filename().string(); SimpleLogger().Write() << "Input file: "
<< contractor_config.osrm_input_path.filename().string();
SimpleLogger().Write() << "Profile: " << contractor_config.profile_path.filename().string(); SimpleLogger().Write() << "Profile: " << contractor_config.profile_path.filename().string();
SimpleLogger().Write() << "Threads: " << contractor_config.requested_num_threads; SimpleLogger().Write() << "Threads: " << contractor_config.requested_num_threads;
tbb::task_scheduler_init init(contractor_config.requested_num_threads); tbb::task_scheduler_init init(contractor_config.requested_num_threads);
return Prepare(contractor_config).Run(); return Prepare(contractor_config).Run();
} }
catch (const std::exception &e) catch (const std::bad_alloc &e)
{ {
SimpleLogger().Write(logWARNING) << "[exception] " << e.what(); SimpleLogger().Write(logWARNING) << "[exception] " << e.what();
return 1; SimpleLogger().Write(logWARNING)
} << "Please provide more memory or consider using a larger swapfile";
return EXIT_FAILURE;
}
catch (const std::exception &e)
{
SimpleLogger().Write(logWARNING) << "[exception] " << e.what();
return EXIT_FAILURE;
} }

View File

@ -43,6 +43,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include <future> #include <future>
#include <iostream> #include <iostream>
#include <thread> #include <thread>
#include <new>
#ifdef _WIN32 #ifdef _WIN32
boost::function0<void> console_ctrl_function; boost::function0<void> console_ctrl_function;
@ -81,11 +82,11 @@ int main(int argc, const char *argv[]) try
lib_config.max_locations_map_matching); lib_config.max_locations_map_matching);
if (init_result == INIT_OK_DO_NOT_START_ENGINE) if (init_result == INIT_OK_DO_NOT_START_ENGINE)
{ {
return 0; return EXIT_SUCCESS;
} }
if (init_result == INIT_FAILED) if (init_result == INIT_FAILED)
{ {
return 1; return EXIT_FAILURE;
} }
#ifdef __linux__ #ifdef __linux__
@ -117,6 +118,7 @@ int main(int argc, const char *argv[]) try
SimpleLogger().Write(logDEBUG) << "Threads:\t" << requested_thread_num; SimpleLogger().Write(logDEBUG) << "Threads:\t" << requested_thread_num;
SimpleLogger().Write(logDEBUG) << "IP address:\t" << ip_address; SimpleLogger().Write(logDEBUG) << "IP address:\t" << ip_address;
SimpleLogger().Write(logDEBUG) << "IP port:\t" << ip_port; SimpleLogger().Write(logDEBUG) << "IP port:\t" << ip_port;
#ifndef _WIN32 #ifndef _WIN32
int sig = 0; int sig = 0;
sigset_t new_mask; sigset_t new_mask;
@ -182,8 +184,15 @@ int main(int argc, const char *argv[]) try
routing_server.reset(); routing_server.reset();
SimpleLogger().Write() << "shutdown completed"; SimpleLogger().Write() << "shutdown completed";
} }
catch (const std::bad_alloc &e)
{
SimpleLogger().Write(logWARNING) << "[exception] " << e.what();
SimpleLogger().Write(logWARNING)
<< "Please provide more memory or consider using a larger swapfile";
return EXIT_FAILURE;
}
catch (const std::exception &e) catch (const std::exception &e)
{ {
SimpleLogger().Write(logWARNING) << "exception: " << e.what(); SimpleLogger().Write(logWARNING) << "[exception] " << e.what();
return 1; return EXIT_FAILURE;
} }