bool builder::reserialize(boost::filesystem::path const& input_file, uint16_t start_stage) const { std::cout << std::endl; std::cout << "--------------------------------" << std::endl; std::cout << "serialize to file" << std::endl; std::cout << "--------------------------------" << std::endl; lamure::pre::bvh bvh(memory_limit_, desc_.buffer_size, desc_.rep_radius_algo); if (!bvh.load_tree(input_file.string())) { return false; } if (bvh.state() != bvh::state_type::after_upsweep) { LOGGER_ERROR("Wrong processing state!"); return false; } CPU_TIMER; auto lod_file = add_to_path(base_path_, ".lod"); auto kdn_file = add_to_path(base_path_, ".bvh"); std::cout << "serialize surfels to file" << std::endl; bvh.serialize_surfels_to_file(lod_file.string(), desc_.buffer_size); std::cout << "serialize bvh to file" << std::endl << std::endl; bvh.serialize_tree_to_file(kdn_file.string(), false); if ((!desc_.keep_intermediate_files) && (start_stage < 3)) { std::remove(input_file.string().c_str()); bvh.reset_nodes(); } // LOGGER_DEBUG("Used memory: " << GetProcessUsedMemory() / 1024 / 1024 << " MiB"); return true; }
void test_create_xdg_dirs_when_xdg_directories_are_arbitrary_and_missing(void **param) { //create temporary base directory char temp_base[] = "/tmp/flybyXXXXXXXX"; mkdtemp(temp_base); assert_true(directory_exists(temp_base)); //specify XDG directories to something arbitrary in the base directory char *expected_data_home = add_to_path(temp_base, "arbitrarydata/data/directory"); char *expected_config_home = add_to_path(temp_base, "arbitraryconf/config/directory"); setenv("XDG_DATA_HOME", expected_data_home, 1); setenv("XDG_CONFIG_HOME", expected_config_home, 1); assert_false(directory_exists(expected_data_home)); assert_false(directory_exists(expected_config_home)); //test directory creation test_create_xdg_dirs(); assert_true(directory_exists(expected_data_home)); assert_true(directory_exists(expected_config_home)); free(expected_data_home); free(expected_config_home); //cleanup char *dir; dir = add_to_path(temp_base, "arbitrarydata/data/directory"); rmdir(dir); free(dir); dir = add_to_path(temp_base, "arbitrarydata/data"); rmdir(dir); free(dir); dir = add_to_path(temp_base, "arbitrarydata"); rmdir(dir); free(dir); dir = add_to_path(temp_base, "arbitraryconf/config/directory"); rmdir(dir); free(dir); dir = add_to_path(temp_base, "arbitraryconf/config"); rmdir(dir); free(dir); dir = add_to_path(temp_base, "arbitraryconf"); rmdir(dir); free(dir); rmdir(temp_base); assert_false(directory_exists(temp_base)); }
bool builder::resample_surfels(boost::filesystem::path const& input_file) const { std::cout << std::endl; std::cout << "--------------------------------" << std::endl; std::cout << "resample" << std::endl; std::cout << "--------------------------------" << std::endl; LOGGER_TRACE("resample stage"); lamure::pre::bvh bvh(memory_limit_, desc_.buffer_size, desc_.rep_radius_algo); if (!bvh.load_tree(input_file.string())) { return false; } if (bvh.state() != bvh::state_type::after_downsweep) { LOGGER_ERROR("Wrong processing state!"); return false; } CPU_TIMER; // perform resample bvh.resample(); //write resampled leaf level out format_xyz format_out; std::unique_ptr<format_xyz> dummy_format_in{new format_xyz()}; auto xyz_res_file = add_to_path(base_path_, "_res.xyz"); converter conv(*dummy_format_in, format_out, desc_.buffer_size); surfel_vector resampled_ll = bvh.get_resampled_leaf_lv_surfels(); conv.write_in_core_surfels_out(resampled_ll, xyz_res_file.string()); std::remove(input_file.string().c_str()); // LOGGER_DEBUG("Used memory: " << GetProcessUsedMemory() / 1024 / 1024 << " MiB"); return true; }
void test_create_xdg_dirs_when_dotlocal_and_dotconfig_have_not_been_created(void **param) { //set temporary directory as HOME in order to ensure that .local and .config do not exist char *previous_home_dir = strdup(getenv("HOME")); char temp_home_dir[] = "/tmp/flybyXXXXXXXX"; mkdtemp(temp_home_dir); setenv("HOME", temp_home_dir, 1); assert_true(directory_exists(temp_home_dir)); //ensure XDG_*_HOME are empty setenv("XDG_DATA_HOME", "", 1); setenv("XDG_CONFIG_HOME", "", 1); char *data_home_path = xdg_data_home(); char *config_home_path = xdg_config_home(); assert_false(directory_exists(data_home_path)); assert_false(directory_exists(config_home_path)); //ensure that XDG_DATA_HOME and XDG_CONFIG_HOME are as expected char *expected_data_home_path = add_to_path(temp_home_dir, DEFAULT_XDG_DATA_HOME); char *expected_config_home_path = add_to_path(temp_home_dir, DEFAULT_XDG_CONFIG_HOME); assert_string_equal(data_home_path, expected_data_home_path); assert_string_equal(config_home_path, expected_config_home_path); free(expected_data_home_path); free(expected_config_home_path); //test directory creation test_create_xdg_dirs(); //revert HOME variable setenv("HOME", previous_home_dir, 1); free(previous_home_dir); //clean up directories char *data_home_base_path = add_to_path(temp_home_dir, DEFAULT_XDG_DATA_HOME_BASE); //corresponds to (...)/.local rmdir(data_home_path); rmdir(data_home_base_path); rmdir(config_home_path); rmdir(temp_home_dir); assert_false(directory_exists(temp_home_dir)); free(data_home_base_path); free(data_home_path); free(config_home_path); }
/** * Check that full flyby config/data directories (XDG_DATA_HOME/flyby/tles, * XDG_CONFIG_HOME/flyby) can be created given the current definitions of * XDG_DATA_HOME and XDG_CONFIG_HOME and remove the directories again. Called * from the test_create_xdg_dirs_when_*-functions. **/ void test_create_xdg_dirs() { //construct expected paths char *xdg_data_home_basepath = xdg_data_home(); char *xdg_config_home_basepath = xdg_config_home(); char *flyby_config_dir = add_to_path(xdg_config_home_basepath, FLYBY_RELATIVE_ROOT_PATH); char *flyby_data_dir = add_to_path(xdg_data_home_basepath, FLYBY_RELATIVE_ROOT_PATH); char *flyby_tle_dir = add_to_path(xdg_data_home_basepath, TLE_RELATIVE_DIR_PATH); //check that paths do not exist yet assert_false(directory_exists(flyby_config_dir)); assert_false(directory_exists(flyby_data_dir)); assert_false(directory_exists(flyby_tle_dir)); create_xdg_dirs(); //check that paths have been created assert_true(directory_exists(flyby_config_dir)); assert_true(directory_exists(flyby_data_dir)); assert_true(directory_exists(flyby_tle_dir)); //cleanup rmdir(flyby_tle_dir); rmdir(flyby_data_dir); rmdir(flyby_config_dir); assert_false(directory_exists(flyby_config_dir)); assert_false(directory_exists(flyby_data_dir)); assert_false(directory_exists(flyby_tle_dir)); free(flyby_config_dir); free(flyby_data_dir); free(flyby_tle_dir); free(xdg_data_home_basepath); free(xdg_config_home_basepath); }
boost::filesystem::path builder::upsweep(boost::filesystem::path input_file, uint16_t start_stage, reduction_strategy const* reduction_strategy, normal_computation_strategy const* normal_comp_strategy, radius_computation_strategy const* radius_comp_strategy) const { std::cout << std::endl; std::cout << "--------------------------------" << std::endl; std::cout << "upsweep" << std::endl; std::cout << "--------------------------------" << std::endl; LOGGER_TRACE("upsweep stage"); lamure::pre::bvh bvh(memory_limit_, desc_.buffer_size, desc_.rep_radius_algo); if (!bvh.load_tree(input_file.string())) { return boost::filesystem::path{}; } if (bvh.state() != bvh::state_type::after_downsweep) { LOGGER_ERROR("Wrong processing state!"); return boost::filesystem::path{}; } CPU_TIMER; // perform upsweep bvh.upsweep(*reduction_strategy, *normal_comp_strategy, *radius_comp_strategy, desc_.compute_normals_and_radii, desc_.resample); auto bvhu_file = add_to_path(base_path_, ".bvhu"); bvh.serialize_tree_to_file(bvhu_file.string(), true); if ((!desc_.keep_intermediate_files) && (start_stage < 2)) { std::remove(input_file.string().c_str()); } input_file = bvhu_file; // LOGGER_DEBUG("Used memory: " << GetProcessUsedMemory() / 1024 / 1024 << " MiB"); return input_file; }
/* Traverses passed directory recursively and adds it and all found * subdirectories to PATH environment variable. */ static void add_dirs_to_path(const char *path) { DIR *dir; struct dirent *dentry; const char *slash = ""; dir = os_opendir(path); if(dir == NULL) return; slash = ends_with_slash(path) ? "" : "/"; add_to_path(path); while((dentry = os_readdir(dir)) != NULL) { char buf[PATH_MAX]; if(is_builtin_dir(dentry->d_name)) { continue; } snprintf(buf, sizeof(buf), "%s%s%s", path, slash, dentry->d_name); #ifndef _WIN32 if(dentry->d_type == DT_DIR) #else if(is_dir(buf)) #endif { add_dirs_to_path(buf); } } os_closedir(dir); }
boost::filesystem::path builder::downsweep(boost::filesystem::path input_file, uint16_t start_stage) const{ bool performed_outlier_removal = false; do { std::string status_suffix = ""; if ( true == performed_outlier_removal ) { status_suffix = " (after outlier removal)"; } std::cout << std::endl; std::cout << "--------------------------------" << std::endl; std::cout << "bvh properties" << status_suffix << std::endl; std::cout << "--------------------------------" << std::endl; lamure::pre::bvh bvh(memory_limit_, desc_.buffer_size, desc_.rep_radius_algo); bvh.init_tree(input_file.string(), desc_.max_fan_factor, desc_.surfels_per_node, base_path_); bvh.print_tree_properties(); std::cout << std::endl; std::cout << "--------------------------------" << std::endl; std::cout << "downsweep" << status_suffix << std::endl; std::cout << "--------------------------------" << std::endl; LOGGER_TRACE("downsweep stage"); CPU_TIMER; bvh.downsweep(desc_.translate_to_origin, input_file.string()); auto bvhd_file = add_to_path(base_path_, ".bvhd"); bvh.serialize_tree_to_file(bvhd_file.string(), true); if ((!desc_.keep_intermediate_files) && (start_stage < 1)) { // do not remove input file std::remove(input_file.string().c_str()); } input_file = bvhd_file; // LOGGER_DEBUG("Used memory: " << GetProcessUsedMemory() / 1024 / 1024 << " MiB"); if ( 3 <= start_stage ) { break; } if ( performed_outlier_removal ) { break; } if(start_stage <= 2 ) { if(desc_.outlier_ratio != 0.0) { size_t num_outliers = desc_.outlier_ratio * (bvh.nodes().size() - bvh.first_leaf()) * bvh.max_surfels_per_node(); size_t ten_percent_of_surfels = std::max( size_t(0.1 * (bvh.nodes().size() - bvh.first_leaf()) * bvh.max_surfels_per_node()), size_t(1) ); num_outliers = std::min(std::max(num_outliers, size_t(1) ), ten_percent_of_surfels); // remove at least 1 surfel, for any given ratio != 0.0 std::cout << std::endl; std::cout << "--------------------------------" << std::endl; std::cout << "outlier removal ( " << int(desc_.outlier_ratio * 100) << " percent = " << num_outliers << " surfels)" << std::endl; std::cout << "--------------------------------" << std::endl; LOGGER_TRACE("outlier removal stage"); surfel_vector kept_surfels = bvh.remove_outliers_statistically(num_outliers, desc_.number_of_outlier_neighbours); format_bin format_out; std::unique_ptr<format_abstract> dummy_format_in{new format_xyz()}; converter conv(*dummy_format_in, format_out, desc_.buffer_size); conv.set_surfel_callback([](surfel &s, bool& keep) { if (s.pos() == vec3r(0.0,0.0,0.0)) keep = false; }); auto binary_outlier_removed_file = add_to_path(base_path_, ".bin_wo_outlier"); conv.write_in_core_surfels_out(kept_surfels, binary_outlier_removed_file.string()); bvh.reset_nodes(); input_file = fs::canonical(binary_outlier_removed_file); performed_outlier_removal = true; } else { break; } } } while( true ); return input_file; }
// Call only once! int start_cl() { const char *compiler = getenv("CL_LOCATION"); #ifdef _WIN32 const char *vs_path = getenv("VS_PATH"); if(!vs_path) vs_path = getenv("VSINSTALLDIR"); if(vs_path) { size_t len = strlen(vs_path); if(vs_path[len - 1] == '/' || vs_path[len - 1] == '\\') len--; char buffer[len + 8]; memcpy(buffer, vs_path, len); strcpy(buffer + len, "/VC/bin"); add_to_path(buffer); } char command_line[PATH_MAX * 2 + 1]; argv_to_command_line(cl_argv, command_line, sizeof command_line); STARTUPINFOA si = { .cb = sizeof(STARTUPINFOA) }; if(target.type == PREPROCESSED_SOURCE && target.name) { SECURITY_ATTRIBUTES security_attr = { .nLength = sizeof(SECURITY_ATTRIBUTES), .lpSecurityDescriptor = NULL, .bInheritHandle = 1 }; void *fh = CreateFileA(target.name, GENERIC_WRITE, FILE_SHARE_READ, &security_attr, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL); if(fh == INVALID_HANDLE_VALUE) { fprintf(stderr, "error: opening output file %s: CreateFileA failed, error %lu\n", target.name, GetLastError()); return 1; } si.hStdOutput = fh; si.hStdInput = GetStdHandle(STD_INPUT_HANDLE); si.hStdError = GetStdHandle(STD_ERROR_HANDLE); si.dwFlags |= STARTF_USESTDHANDLES; } PROCESS_INFORMATION pi; while(!CreateProcessA(compiler, command_line, NULL, NULL, 1, 0, NULL, NULL, &si, &pi)) { if(compiler) { compiler = NULL; continue; } fprintf(stderr, "CreateProcessA failed, error %lu\n", GetLastError()); return 127; } unsigned long int r; WaitForSingleObject(pi.hProcess, INFINITE); GetExitCodeProcess(pi.hProcess, &r); #else pid_t pid = fork(); if(pid == -1) { perror("fork"); abort(); } if(pid == 0) { if(target.type == PREPROCESSED_SOURCE && target.name) { int fd = creat(target.name, 0666); if(fd == -1) { fprintf(stderr, "error: opening output file %s: %s\n", target.name, strerror(errno)); exit(1); } close(1); dup2(fd, 1); } if(compiler) execvp(compiler, cl_argv); execvp("cl", cl_argv); perror("cl"); exit(127); } free_argv(); int status; if(waitpid(pid, &status, 0) < 0) { perror("waitpid"); abort(); } if(WIFSIGNALED(status)) { fprintf(stderr, "cl terminated with signal %d\n", WTERMSIG(status)); return WTERMSIG(status) + 126; } int r = WEXITSTATUS(status); #endif if(r || !target.name || target.type == PREPROCESSED_SOURCE) return r; if(access(target.name, F_OK) == 0) return r; size_t len = strlen(target.name); int n = get_last_dot(target.name, len); if(n >= 0) len = n; char out[len + 4 + 1]; memcpy(out, target.name, len); assert(target.type == EXE || target.type == OBJ); strcpy(out + len, target.type == EXE ? ".exe" : ".obj"); if(access(out, F_OK) < 0) { perror(NULL); return 1; } /* if(target.type == EXE) { char manifest[len + 4 + 9 + 1]; memcpy(manifest, out, len + 4); strcpy(manifest + len + 4, ".manifest"); unlink(manifest); }*/ return -rename(out, target.name); } static int no_static_link = 1; struct option { const char *opt; char arg; void (*act)(); }; void define(const char *d) { char buffer[2 + strlen(d) + 1]; strcpy(buffer, "-D"); strcpy(buffer + 2, d); add_to_argv(buffer); }