Skip to content
This repository was archived by the owner on Mar 8, 2023. It is now read-only.

Commit d567a88

Browse files
adrparAdrian Partl
authored andcommitted
capture bad_alloc if it ever happens, however usually the OOM killer steps in before that...
Signed-off-by: Adrian Partl <[email protected]>
1 parent 3e8078b commit d567a88

File tree

1 file changed

+111
-62
lines changed

1 file changed

+111
-62
lines changed

src/cmd.cpp

Lines changed: 111 additions & 62 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,21 @@ namespace tntn {
3030

3131
//forward decl for use in preset commands
3232
int tin_terrain_commandline_action(std::vector<std::string> args);
33+
static int main_loop_dem2tintiles(const std::string input_file,
34+
const std::string meshing_method,
35+
const int min_zoom,
36+
const int max_zoom,
37+
double max_error,
38+
bool max_error_given,
39+
const std::string output_basedir,
40+
std::unique_ptr<MeshWriter> w);
41+
static int main_loop_dem2tin(const std::string input_file,
42+
const std::string method,
43+
double max_error,
44+
bool max_error_given,
45+
int step,
46+
const std::string output_file,
47+
const FileFormat output_file_format);
3348

3449
typedef int (*subcommand_function_t)(bool need_help,
3550
const po::variables_map&,
@@ -140,40 +155,52 @@ static int subcommand_dem2tintiles(bool need_help,
140155

141156
const std::string meshing_method = local_varmap["method"].as<std::string>();
142157

143-
auto input_raster = std::make_unique<RasterDouble>();
144-
145-
if(!load_raster_file(input_file.c_str(), *input_raster))
158+
if("zemlya" != meshing_method && "terra" != meshing_method)
146159
{
147-
return false;
160+
throw po::error(std::string("unknown method ") + meshing_method);
148161
}
149162

150-
if("zemlya" == meshing_method || "terra" == meshing_method)
163+
std::unique_ptr<char[]> emergency_memory(new char[16384]);
164+
165+
try
151166
{
152-
max_error = input_raster->get_cell_size();
153-
if(local_varmap.count("max-error"))
154-
{
155-
max_error_given = true;
156-
max_error = local_varmap["max-error"].as<double>();
157-
}
167+
return main_loop_dem2tintiles(input_file,
168+
meshing_method,
169+
min_zoom,
170+
max_zoom,
171+
max_error,
172+
max_error_given,
173+
output_basedir,
174+
std::move(w));
175+
}
176+
catch(std::bad_alloc& exception)
177+
{
178+
emergency_memory.reset();
158179

159-
if(max_error < 0.0)
160-
{
161-
throw po::error("max-error must be positive");
162-
}
180+
TNTN_LOG_ERROR("tin-terrain has run out of memory.");
181+
exit(1);
163182
}
164-
#if defined(TNTN_USE_ADDONS) && TNTN_USE_ADDONS
165-
else if("curvature")
183+
}
184+
185+
static int main_loop_dem2tintiles(const std::string input_file,
186+
const std::string meshing_method,
187+
const int min_zoom,
188+
const int max_zoom,
189+
double max_error,
190+
bool max_error_given,
191+
const std::string output_basedir,
192+
std::unique_ptr<MeshWriter> w)
193+
{
194+
auto input_raster = std::make_unique<RasterDouble>();
195+
196+
if(!load_raster_file(input_file.c_str(), *input_raster))
166197
{
167-
double threshold = 1;
168-
if(local_varmap.count("threshold"))
169-
{
170-
threshold = local_varmap["threshold"].as<double>();
171-
}
198+
return false;
172199
}
173-
#endif
174-
else
200+
201+
if(!max_error_given && ("zemlya" == meshing_method || "terra" == meshing_method))
175202
{
176-
throw po::error(std::string("unknown method ") + meshing_method);
203+
max_error = input_raster->get_cell_size();
177204
}
178205

179206
RasterOverviews overviews(std::move(input_raster), min_zoom, max_zoom);
@@ -278,17 +305,20 @@ static int subcommand_dem2tin(bool need_help,
278305

279306
// clang-format off
280307
subdesc.add_options()
281-
("input", po::value<std::string>(), "input filename")
282-
("input-format",po::value<std::string>()->default_value("auto"), "input file format, can be any of: auto, asc, xyz, tiff")
283-
("output", po::value<std::string>(), "output filename")
284-
("output-format", po::value<std::string>()->default_value("auto"), "output file format, can be any of: auto, obj, off, terrain (quantized mesh), json/geojson")
285-
("max-error", po::value<double>(), "max error parameter when using terra or zemlya method")
286-
("step", po::value<int>(), "grid spacing in pixels when using dense method")
308+
("input", po::value<std::string>(), "input filename")
309+
("input-format", po::value<std::string>()->default_value("auto"),
310+
"input file format, can be any of: auto, asc, xyz, tiff")
311+
("output", po::value<std::string>(), "output filename")
312+
("output-format", po::value<std::string>()->default_value("auto"),
313+
"output file format, can be any of: auto, obj, off, terrain (quantized mesh), json/geojson")
314+
("max-error", po::value<double>(), "max error parameter when using terra or zemlya method")
315+
("step", po::value<int>(), "grid spacing in pixels when using dense method")
287316
#if defined(TNTN_USE_ADDONS) && TNTN_USE_ADDONS
288-
("threshold", po::value<double>(), "threshold when using curvature method")
289-
("method", po::value<std::string>()->default_value("terra"), "meshing method, valid values are: dense, terra, zemlya, curvature");
317+
("threshold", po::value<double>(), "threshold when using curvature method")
318+
("method", po::value<std::string>()->default_value("terra"), "meshing method, valid values are: dense, terra, zemlya, curvature");
290319
#else
291-
("method", po::value<std::string>()->default_value("terra"), "meshing method, valid values are: dense, terra, zemlya");
320+
("method", po::value<std::string>()->default_value("terra"),
321+
"meshing method, valid values are: dense, terra, zemlya");
292322
#endif
293323
// clang-format on
294324

@@ -344,6 +374,51 @@ static int subcommand_dem2tin(bool need_help,
344374

345375
const std::string method = local_varmap["method"].as<std::string>();
346376

377+
bool max_error_given = false;
378+
double max_error = 0.0;
379+
380+
if(local_varmap.count("max-error"))
381+
{
382+
max_error_given = true;
383+
max_error = local_varmap["max-error"].as<double>();
384+
}
385+
386+
int step = 1;
387+
if(local_varmap.count("step"))
388+
{
389+
step = local_varmap["step"].as<int>();
390+
}
391+
392+
std::unique_ptr<char[]> emergency_memory(new char[16384]);
393+
394+
try
395+
{
396+
return main_loop_dem2tin(input_file,
397+
method,
398+
max_error,
399+
max_error_given,
400+
step,
401+
output_file,
402+
output_file_format);
403+
}
404+
catch(std::bad_alloc& exception)
405+
{
406+
emergency_memory.reset();
407+
408+
TNTN_LOG_ERROR("tin-terrain has run out of memory.");
409+
exit(1);
410+
}
411+
412+
}
413+
414+
static int main_loop_dem2tin(const std::string input_file,
415+
const std::string method,
416+
double max_error,
417+
bool max_error_given,
418+
int step,
419+
const std::string output_file,
420+
const FileFormat output_file_format)
421+
{
347422
auto raster = std::make_unique<RasterDouble>();
348423

349424
// Import raster file without projection validation
@@ -361,10 +436,9 @@ static int subcommand_dem2tin(bool need_help,
361436

362437
if(method == "terra" || method == "zemlya")
363438
{
364-
double max_error = raster->get_cell_size();
365-
if(local_varmap.count("max-error"))
439+
if(!max_error_given)
366440
{
367-
max_error = local_varmap["max-error"].as<double>();
441+
max_error = raster->get_cell_size();
368442
}
369443

370444
if("terra" == method)
@@ -380,34 +454,9 @@ static int subcommand_dem2tin(bool need_help,
380454
}
381455
else if(method == "dense")
382456
{
383-
int step = 1;
384-
if(local_varmap.count("step"))
385-
{
386-
step = local_varmap["step"].as<int>();
387-
}
388-
389457
TNTN_LOG_INFO("generating dense mesh grid ...");
390458
mesh = generate_tin_dense_quadwalk(*raster, step);
391459
}
392-
#if defined(TNTN_USE_ADDONS) && TNTN_USE_ADDONS
393-
else if(method == "curvature")
394-
{
395-
if(!local_varmap.count("threshold"))
396-
{
397-
throw po::error("no --threshold given, required for this method");
398-
}
399-
400-
double gradient_threshold = local_varmap["threshold"].as<double>();
401-
402-
if(gradient_threshold <= 0.0)
403-
{
404-
throw po::error("threshold must be larger than zero");
405-
}
406-
407-
TNTN_LOG_INFO("performing curverture integral meshing...");
408-
mesh = generate_tin_curvature(*raster, gradient_threshold);
409-
}
410-
#endif
411460
else
412461
{
413462
throw po::error(std::string("unknown method ") + method);

0 commit comments

Comments
 (0)