static bool util_addr2line_lookup__(const void * bt_addr , char ** func_name , char ** file_name , int * line_nr, bool subtract_base_adress) { *func_name = NULL; // If dladdr() succeeds, but addr2line fails the func_name pointer will be set, but the function will return false anyway. *file_name = NULL; *line_nr = 0; { bool address_found = false; Dl_info dl_info; #if defined(__APPLE__) return false; #else if (dladdr(bt_addr , &dl_info)) { const char * executable = dl_info.dli_fname; *func_name = util_alloc_string_copy( dl_info.dli_sname ); if (util_file_exists( executable )) { char *stdout_file = util_alloc_tmp_file("/tmp" , "addr2line" , true); /* 1: Run addr2line application */ { char ** argv = util_calloc(3 , sizeof * argv ); argv[0] = util_alloc_string_copy("--functions"); argv[1] = util_alloc_sprintf("--exe=%s" , executable ); { char * rel_address = (char *) bt_addr; if (subtract_base_adress) rel_address -= (size_t) dl_info.dli_fbase; argv[2] = util_alloc_sprintf("%p" , (void *) rel_address); } util_spawn_blocking("addr2line", 3, (const char **) argv, stdout_file, NULL); util_free_stringlist(argv , 3); } /* 2: Parse stdout output */ { bool at_eof; FILE * stream = util_fopen(stdout_file , "r"); char * tmp_fname = util_fscanf_alloc_line(stream , &at_eof); if (strcmp(tmp_fname , UNDEFINED_FUNCTION) != 0) { char * stdout_file_name = util_fscanf_alloc_line(stream , &at_eof); char * line_string = NULL; util_binary_split_string( stdout_file_name , ":" , false , file_name , &line_string); if (line_string && util_sscanf_int( line_string , line_nr)) address_found = true; free( stdout_file_name ); util_safe_free( line_string ); } free( tmp_fname ); fclose(stream); } util_unlink_existing(stdout_file); free( stdout_file ); } } return address_found; #endif } }
bool hash_add_option( hash_type * hash, const char * key_value) { bool addOK = false; { char * value; char * key; util_binary_split_string( key_value , ":" , true , &key , &value); if (value != NULL) { hash_insert_hash_owned_ref( hash , key , value , free ); addOK = true; } util_safe_free( key ); } return addOK; }
hash_type * hash_alloc_from_options(const stringlist_type * options) { int num_options = stringlist_get_size( options ); hash_type * opt_hash = hash_alloc(); int iopt; for (iopt = 0; iopt < num_options; iopt++) { char * option; char * value; util_binary_split_string( stringlist_iget(options , iopt) , ":" , true , &option , &value); if ((option != NULL) && (value != NULL)) hash_insert_hash_owned_ref( opt_hash , option , util_alloc_string_copy(value) , free); // Warning: could not interpret string as KEY:VALUE - ignored util_safe_free(option); util_safe_free(value); } return opt_hash; }
int main( int argc, char ** argv) { if (argc == 1) util_exit("block_node node1 node2 node3:2 \n"); /* Initialize lsf environment */ util_setenv( "LSF_BINDIR" , "/prog/LSF/9.1/linux2.6-glibc2.3-x86_64/bin" ); util_setenv( "LSF_LINDIR" , "/prog/LSF/9.1/linux2.6-glibc2.3-x86_64/lib" ); util_setenv( "XLSF_UIDDIR" , "/prog/LSF/9.1/linux2.6-glibc2.3-x86_64/lib/uid" ); util_setenv( "LSF_SERVERDIR" , "/prog/LSF/9.1/linux2.6-glibc2.3-x86_64/etc"); util_setenv( "LSF_ENVDIR" , "/prog/LSF/conf"); util_update_path_var( "PATH" , "/prog/LSF/9.1/linux2.6-glibc2.3-x86_64/bin" , false); util_update_path_var( "LD_LIBRARY_PATH" , "/prog/LSF/9.1/linux2.6-glibc2.3-x86_64/lib" , false); lsf_driver = lsf_driver_alloc(); if (lsf_driver_get_submit_method( lsf_driver ) != LSF_SUBMIT_INTERNAL) util_exit("Sorry - the block_node program must be invoked on a proper LSF node \n"); { int iarg; int total_blocked_target = 0; nodes = hash_alloc(); for (iarg = 1; iarg < argc; iarg++) { char *node_name; int num_slots; { char * num_slots_string; util_binary_split_string( argv[iarg] , ":" , true , &node_name , &num_slots_string); if (num_slots_string) util_sscanf_int( num_slots_string , &num_slots); else num_slots = 1; } if (!hash_has_key( nodes , node_name)) hash_insert_hash_owned_ref( nodes , node_name , count_pair_alloc() , free); { count_pair_type * pair = hash_get( nodes , node_name); pair->target += num_slots; } total_blocked_target += num_slots; } signal(SIGINT , block_node_exit ); { const int sleep_time = 5; const int chunk_size = 10; /* We submit this many at a time. */ const int max_pool_size = 1000; /* The absolute total maximum of jobs we will submit. */ bool cont = true; int pending = 0; bool all_blocked; job_pool = vector_alloc_new(); while (cont) { printf("[Ctrl-C to give up] "); fflush( stdout ); if (cont) sleep( sleep_time ); if (pending == 0) { if (vector_get_size( job_pool ) < max_pool_size) add_jobs( chunk_size ); } update_pool_status( &all_blocked , &pending); print_status(); if (all_blocked) cont = false; } if (!all_blocked) printf("Sorry - failed to block all the nodes \n"); block_node_exit( 0 ); hash_free( nodes ); } } }