/*___INFO__MARK_BEGIN__*/ /************************************************************************* * * The Contents of this file are made available subject to the terms of * the Sun Industry Standards Source License Version 1.2 * * Sun Microsystems Inc., March, 2001 * * * Sun Industry Standards Source License Version 1.2 * ================================================= * The contents of this file are subject to the Sun Industry Standards * Source License Version 1.2 (the "License"); You may not use this file * except in compliance with the License. You may obtain a copy of the * License at http://gridengine.sunsource.net/Gridengine_SISSL_license.html * * Software provided under this License is provided on an "AS IS" basis, * WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, * WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS, * MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING. * See the License for the specific provisions governing your rights and * obligations concerning the Software. * * The Initial Developer of the Original Code is: Sun Microsystems, Inc. * * Copyright: 2001 by Sun Microsystems, Inc. * * All Rights Reserved. * ************************************************************************/ /*___INFO__MARK_END__*/ #include #include #include #include #include #include "basis_types.h" #include "sge_time.h" #include "cl_commlib.h" #include "cl_util.h" #include "sge_arch.h" #include "version.h" #include "sge_profiling.h" #include "sge_uidgid.h" #include "sge_signal.h" #include "setup_path.h" #include "sge_bootstrap.h" #include "sge_feature.h" #include "sge_prog.h" #include "sge_security.h" #include "sge_all_listsL.h" #include "msg_utilbin.h" #include "gdi/sge_gdi.h" #include "gdi/sge_gdi_ctx.h" #include "gdi/sge_gdi_packet.h" #include "gdi/sge_gdi_packet_pb_cull.h" #include "uti/sge_string.h" #include "msg_clients_common.h" #define ARGUMENT_COUNT 15 static char* cl_values[ARGUMENT_COUNT+2]; static int cl_short_host_name_option = 0; static int cl_show[] = {1,1 ,1,1 ,1,1,1 ,1,1,1,1,0 ,0,1,1}; static int cl_alignment[] = {1,0 ,1,0 ,1,1,1 ,1,1,1,1,0 ,0,1,1}; static int cl_column_width[] = {0,0 ,0,30,0,0,22,0,0,0,0,20,5,0,0}; static char* cl_description[] = { /* 00 */ "time of debug output creation", /* 01 */ "endpoint service name where debug client is connected", /* 02 */ "message direction", /* 03 */ "name of participating communication endpoint", /* 04 */ "message data format", /* 05 */ "message acknowledge type", /* 06 */ "message tag information", /* 07 */ "message id", /* 08 */ "message response id", /* 09 */ "message length", /* 10 */ "time when message was sent/received", /* 11 */ "message content dump (xml/bin/cull)", /* 12 */ "additional information", /* 13 */ "commlib linger time", /* 14 */ "nr. of connections" }; static char* cl_names[] = { "time", "local", "d.", "remote", "format", "ack type", "msg tag", "msg id", "msg rid", "msg len", "msg time", "msg dump", "info", "msg ltime", "con count" }; static void sighandler_ping(int sig); #if 0 static int pipe_signal = 0; static int hup_signal = 0; #endif static int do_shutdown = 0; static void sighandler_ping(int sig) { if (sig == SIGPIPE) { #if 0 pipe_signal = 1; #endif return; } if (sig == SIGHUP) { #if 0 hup_signal = 1; #endif return; } cl_com_ignore_timeouts(CL_TRUE); do_shutdown = 1; } static void qping_set_output_option(char* option_string) { char* option = NULL; char* value1 = NULL; char* value2 = NULL; int opt = 0; option = strstr(option_string, ":"); if (option) { option[0]=0; if (strcmp(option_string,"h") == 0) { opt = 1; option++; value1=option; } if (strcmp(option_string,"hn") == 0) { opt = 2; option++; value1=option; } if (strcmp(option_string,"w") == 0) { opt = 3; option++; value2=strstr(option,":"); value2[0] = 0; value1=option; value2++; } if (strcmp(option_string,"s") == 0) { opt = 4; option++; value1=option; } switch(opt) { case 1: { /* h */ int column = -1; if (value1) { column = atoi(value1); } column--; if (column>=0 && column =0 && column =0 && column 0) { cl_column_width[column] = width; } } break; } } } } static void qping_convert_time(char* buffer, char* dest, cl_bool_t show_hour) { time_t i; char* help; char* help2; #ifdef HAS_LOCALTIME_R struct tm tm_buffer; #endif struct tm *tm; struct saved_vars_s *context = NULL; help=sge_strtok_r(buffer, ".", &context); if (help == NULL) { help = "-"; } help2=sge_strtok_r(NULL,".", &context); if (help2 == NULL) { help2 = "NULL"; } if (strcmp(help,"-") == 0) { sprintf(dest, "N.A."); } else { i = atoi(help); #ifndef HAS_LOCALTIME_R tm = localtime(&i); #else tm = (struct tm *)localtime_r(&i, &tm_buffer); #endif if (show_hour == CL_TRUE) { sprintf(dest, "%02d:%02d:%02d.%s", tm->tm_hour, tm->tm_min, tm->tm_sec, help2); } else { sprintf(dest, "%02d:%02d.%s", tm->tm_min, tm->tm_sec, help2); } } sge_free_saved_vars(context); } static void qping_general_communication_error(const cl_application_error_list_elem_t* commlib_error) { if (commlib_error != NULL) { if (commlib_error->cl_already_logged == CL_FALSE) { if (commlib_error->cl_info != NULL) { fprintf(stderr,"%s: %s\n", cl_get_error_text(commlib_error->cl_error), commlib_error->cl_info); } else { fprintf(stderr,"error: %s\n", cl_get_error_text(commlib_error->cl_error)); } if (commlib_error->cl_error == CL_RETVAL_ACCESS_DENIED) { do_shutdown = 1; } } } } static void qping_parse_environment(void) { char* env_opt = NULL; char opt_buffer[1024]; char* opt_str = NULL; env_opt = getenv("SGE_QPING_OUTPUT_FORMAT"); if (env_opt != NULL) { snprintf(opt_buffer, 1024, "%s", env_opt); opt_str=strtok(opt_buffer, " "); if (opt_str) { qping_set_output_option(opt_str); } while( (opt_str=strtok(NULL, " "))) { qping_set_output_option(opt_str); } } } static void qping_printf_fill_up(FILE* fd, char* name, int length, char c, int before) { int n = strlen(name); int i; if (before == 0) { fprintf(fd,"%s",name); } for (i=0;i<(length-n);i++) { fprintf(fd,"%c",c); } if (before != 0) { fprintf(fd,"%s",name); } } static void qping_print_line(const char* buffer, int nonewline, int dump_tag, const char *sender_comp_name) { int i=0; int max_name_length = 0; int full_width = 0; cl_com_debug_message_tag_t debug_tag = CL_DMT_MESSAGE; static int show_header = 1; char* message_debug_data = NULL; char time[512]; char msg_time[512]; char com_time[512]; struct saved_vars_s *context = NULL; for (i=0;i= CL_DMT_MESSAGE &&i < CL_DMT_MAX_TYPE) { debug_tag = (cl_com_debug_message_tag_t)i; for (i=0;iid) { printf("id : "sge_U32CFormat"\n", sge_u32c(packet->id)); } else { printf("id : %s\n", "NULL"); } if (packet->host) { printf("host : %s\n", packet->host); } else { printf("host : %s\n", "NULL"); } if (packet->commproc) { printf("commproc : %s\n", packet->commproc); } else { printf("commproc : %s\n", "NULL"); } if (packet->version) { printf("version : "sge_U32CFormat"\n", sge_u32c(packet->version)); } else { printf("version : %s\n", "NULL"); } if (packet->auth_info) { printf("auth_info : %s\n", packet->auth_info); } else { printf("auth_info : %s\n", "NULL"); } task = packet->first_task; while (task != NULL) { printf(" task:\n"); if (task->command) { printf("op : "sge_U32CFormat"\n", sge_u32c(task->command)); } else { printf("op : %s\n", "NULL"); } if (task->target) { printf("target : "sge_U32CFormat"\n", sge_u32c(task->target)); } else { printf("target : %s\n", "NULL"); } if (task->data_list) { lWriteListTo(task->data_list,stdout); } else { printf("lp : %s\n", "NULL"); } if (task->answer_list) { lWriteListTo(task->answer_list,stdout); } else { printf("alp : %s\n", "NULL"); } if (task->condition) { lWriteWhereTo(task->condition,stdout); } else { printf("cp : %s\n", "NULL"); } if (task->enumeration) { lWriteWhatTo(task->enumeration,stdout); } else { printf("enp : %s\n", "NULL"); } if (task->id) { printf("id : "sge_U32CFormat"\n", sge_u32c(task->id)); } else { printf("id : %s\n", "NULL"); } task = task->next; } } sge_gdi_packet_free(&packet); clear_packbuffer(&buf); } } } if (strstr(cl_values[6], "TAG_REPORT_REQUEST") != NULL) { unsigned long buffer_length = 0; if ( cl_util_get_binary_buffer(message_debug_data, &binary_buffer , &buffer_length) == CL_RETVAL_OK) { sge_pack_buffer buf; if (init_packbuffer_from_buffer(&buf, (char*)binary_buffer, buffer_length) == PACK_SUCCESS) { lList *rep = NULL; if (cull_unpack_list(&buf, &rep) == 0) { printf(" unpacked report request (binary buffer length %lu):\n", buffer_length ); if (rep) { lWriteListTo(rep, stdout); } else { printf("rep: NULL\n"); } } lFreeList(&rep); rep = NULL; clear_packbuffer(&buf); } } } if ( strstr( cl_values[6] , "TAG_EVENT_CLIENT_EXIT") != NULL ) { unsigned long buffer_length = 0; if ( cl_util_get_binary_buffer(message_debug_data, &binary_buffer , &buffer_length) == CL_RETVAL_OK) { sge_pack_buffer buf; if (init_packbuffer_from_buffer(&buf, (char*)binary_buffer, buffer_length) == PACK_SUCCESS) { u_long32 client_id = 0; if (unpackint(&buf, &client_id) == PACK_SUCCESS) { printf(" unpacked event client exit (binary buffer length %lu):\n", buffer_length ); printf("event client "sge_U32CFormat" exit\n", sge_u32c(client_id)); } clear_packbuffer(&buf); } } } if (strstr( cl_values[6] , "TAG_ACK_REQUEST") != NULL ) { unsigned long buffer_length = 0; if (cl_util_get_binary_buffer(message_debug_data, &binary_buffer, &buffer_length) == CL_RETVAL_OK) { sge_pack_buffer buf; if (init_packbuffer_from_buffer(&buf, (char*)binary_buffer, buffer_length) == PACK_SUCCESS) { lListElem *ack = NULL; while (pb_unused(&buf) > 0) { if (cull_unpack_elem(&buf, &ack, NULL)) { printf("TAG_ACK_REQUEST: unpack error\n"); } else { lWriteElemTo(ack, stdout); /* ack */ lFreeElem(&ack); } } clear_packbuffer(&buf); } } } if (strstr(cl_values[6] , "TAG_JOB_EXECUTION") != NULL || strstr(cl_values[6] , "TAG_SLAVE_ALLOW") != NULL) { unsigned long buffer_length = 0; if (cl_util_get_binary_buffer(message_debug_data, &binary_buffer, &buffer_length) == CL_RETVAL_OK) { sge_pack_buffer buf; if (init_packbuffer_from_buffer(&buf, (char*)binary_buffer, buffer_length) == PACK_SUCCESS) { if (strcmp(sender_comp_name, "qmaster") == 0) { u_long32 feature_set; lListElem *job = NULL; if (unpackint(&buf, &feature_set) == PACK_SUCCESS) { printf(" unpacked %s (binary buffer length %lu):\n", cl_values[6], buffer_length); printf("feature_set: "sge_U32CFormat"\n", sge_u32c(feature_set)); } if (cull_unpack_elem(&buf, &job, NULL) == PACK_SUCCESS) { lWriteElemTo(job, stdout); /* job */ } else { printf("could not unpack job\n"); } lFreeElem(&job); } else { u_long32 feature_set; lListElem *petr = NULL; if (unpackint(&buf, &feature_set) == PACK_SUCCESS) { printf(" unpacked %s - PE TASK REQUEST (binary buffer length %lu):\n", cl_values[6], buffer_length); printf("feature_set: "sge_U32CFormat"\n", sge_u32c(feature_set)); } if (cull_unpack_elem(&buf, &petr, NULL) == PACK_SUCCESS) { lWriteElemTo(petr, stdout); } else { printf("could not unpack pe task request\n"); } lFreeElem(&petr); } clear_packbuffer(&buf); } } } if (strstr(cl_values[6] , "TAG_SIGJOB") != NULL) { unsigned long buffer_length = 0; if (cl_util_get_binary_buffer(message_debug_data, &binary_buffer , &buffer_length) == CL_RETVAL_OK) { sge_pack_buffer buf; if (init_packbuffer_from_buffer(&buf, (char*)binary_buffer, buffer_length) == PACK_SUCCESS) { u_long32 jobid = 0; u_long32 job_signal = 0; u_long32 jataskid = 0; char *qname = NULL; if (unpackint(&buf, &jobid) == PACK_SUCCESS) { printf("jobid (JB_job_number): "sge_U32CFormat"\n", sge_u32c(jobid)); } if (unpackint(&buf, &jataskid) == PACK_SUCCESS) { printf("jataskid (JAT_task_number): "sge_U32CFormat"\n", sge_u32c(jataskid)); } if (unpackstr(&buf, &qname) == PACK_SUCCESS) { if (qname != NULL) { printf("qname(QU_full_name): \"%s\"\n", qname); } else { printf("qping: qname(QU_full_name) is NULL !!!!\n"); } } if (unpackint(&buf, &job_signal) == PACK_SUCCESS) { printf("signal: "sge_U32CFormat" (%s)\n", sge_u32c(job_signal), sge_sig2str(job_signal)); } if (qname) { free(qname); } clear_packbuffer(&buf); } } } if (strstr(cl_values[6], "TAG_SIGQUEUE") != NULL) { unsigned long buffer_length = 0; if ( cl_util_get_binary_buffer(message_debug_data, &binary_buffer , &buffer_length) == CL_RETVAL_OK) { sge_pack_buffer buf; printf("binary buffer length is %lu\n",buffer_length); if (init_packbuffer_from_buffer(&buf, (char*)binary_buffer, buffer_length) == PACK_SUCCESS) { u_long32 jobid = 0; u_long32 queue_signal = 0; u_long32 jataskid = 0; char *qname = NULL; if (unpackint(&buf, &jobid) == PACK_SUCCESS) { printf("jobid (0 - unused): "sge_U32CFormat"\n", sge_u32c(jobid)); } if (unpackint(&buf, &jataskid) == PACK_SUCCESS) { printf("jataskid (0 - unused): "sge_U32CFormat"\n", sge_u32c(jataskid)); } if (unpackstr(&buf, &qname) == PACK_SUCCESS) { if (qname != NULL) { printf("qname(QU_full_name): \"%s\"\n", qname); } else { printf("qping: qname(QU_full_name) is NULL !!!!\n"); } } if (unpackint(&buf, &queue_signal) == PACK_SUCCESS) { printf("signal: "sge_U32CFormat" (%s)\n", sge_u32c(queue_signal), sge_sig2str(queue_signal)); } if (qname) { free(qname); } clear_packbuffer(&buf); } } } #if 0 CR: qping TODO: a) Add a option do ignore hosts/components b) Following Tags are not unpacked case TAG_SLAVE_ALLOW case TAG_CHANGE_TICKET case TAG_SIGJOB case TAG_SIGQUEUE case TAG_KILL_EXECD case TAG_NEW_FEATURES case TAG_GET_NEW_CONF case TAG_FULL_LOAD_REPORT ... are missing !!! #endif printf("%s", bin_end); for(i=strlen(bin_end);i] [-info] [-f] ] | [ [-dump_tag tag [param] ] [-dump] [-nonewline] ] ] \n",MSG_UTILBIN_USAGE); fprintf(out, " -i : set ping interval time\n"); fprintf(out, " -info : show full status information and exit\n"); fprintf(out, " -f : show full status information on each ping interval\n"); fprintf(out, " -noalias : ignore $SGE_ROOT/SGE_CELL/common/host_aliases file\n"); fprintf(out, " -ssl : use SSL framework\n"); fprintf(out, " -tcp : use TCP framework\n"); fprintf(out, " -dump : dump communication traffic (see \"communication traffic output options\" for additional information)\n"); fprintf(out, " (provides the same output like -dump_tag MSG)\n"); fprintf(out, " -dump_tag : dump communication traffic (see \"communication traffic output options\" for additional information)\n"); fprintf(out, " tag=ALL - show all\n"); fprintf(out, " tag=APP - show application messages\n"); fprintf(out, " tag=MSG - show commlib protocol messages\n"); fprintf(out, " - ERROR, WARNING, INFO, DEBUG or DPRINTF\n"); fprintf(out, " -nonewline : dump output will not have a linebreak within a message\n"); fprintf(out, " -help : show this info\n"); fprintf(out, " host : host name of running component\n"); fprintf(out, " port : port number of running component\n"); fprintf(out, " name : name of running component (e.g.: \"qmaster\" or \"execd\")\n"); fprintf(out, " id : id of running component (e.g.: 1 for daemons)\n\n"); fprintf(out, "example:\n"); fprintf(out, " qping -info clustermaster 5000 qmaster 1\n\n"); fprintf(out, "communication traffic output options:\n"); fprintf(out, " The environment variable SGE_QPING_OUTPUT_FORMAT can be used to hide columns and\n"); fprintf(out, " to set default column width. For hostname output the parameter hn is used.\n"); fprintf(out, " SGE_QPING_OUTPUT_FORMAT=\"h:1 h:4 w:1:20\"\n"); fprintf(out, " will hide the columns 1 and 4 and set the width of column 1 to 20 characters.\n"); fprintf(out, " h:X -> hide column X\n"); fprintf(out, " s:X -> show column X\n"); fprintf(out, " w:X:Y -> set width of column X to Y\n"); fprintf(out, " hn:X -> set hostname output parameter X. X values are \"long\" or \"short\"\n\n"); fprintf(out, " available columns are:\n\n"); qping_parse_environment(); for (i=0;iruntime); } else { time_t starttime; starttime = (time_t)status->starttime; printf(":\nSIRM version: %s\n", status->version ); printf("SIRM message id: "sge_U32CFormat"\n", sge_u32c(status->mid) ); printf("start time: %s ("sge_U32CFormat")\n", sge_ctime(starttime, &ds),sge_u32c(status->starttime)); printf("run time [s]: "sge_U32CFormat"\n", sge_u32c(status->runtime) ); printf("messages in read buffer: "sge_U32CFormat"\n", sge_u32c(status->application_messages_brm) ); printf("messages in write buffer: "sge_U32CFormat"\n", sge_u32c(status->application_messages_bwm) ); printf("nr. of connected clients: "sge_U32CFormat"\n", sge_u32c(status->application_connections_noc) ); printf("status: "sge_U32CFormat"\n", sge_u32c(status->application_status) ); printf("info: %s\n", status->info ); printf("\n"); } } else { printf("unexpected error\n"); } } cl_com_free_sirm_message(&status); if (option_info != 0) { break; } sleep(interval); } } else { dstring line_buffer = DSTRING_INIT; qping_parse_environment(); while (do_shutdown == 0 ) { int retval = 0; #if 0 static int stop_running = 15; #endif cl_com_message_t* message = NULL; cl_com_endpoint_t* sender = NULL; #if 0 if (stop_running-- == 0) { do_shutdown = 1; } #endif cl_commlib_trigger(handle, 1); retval = cl_commlib_receive_message(handle, NULL, NULL, 0, /* handle, comp_host, comp_name , comp_id, */ CL_FALSE, 0, /* syncron, response_mid */ &message, &sender ); if ( retval != CL_RETVAL_OK) { if ( retval == CL_RETVAL_CONNECTION_NOT_FOUND ) { char command_buffer[256]; cl_byte_t *reference = (cl_byte_t *)command_buffer; printf("open connection to \"%s/%s/"sge_U32CFormat"\" ... " ,resolved_comp_host , comp_name, sge_u32c(comp_id) ); retval = cl_commlib_open_connection(handle, resolved_comp_host , comp_name, comp_id); printf("%s\n", cl_get_error_text(retval)); if (retval == CL_RETVAL_CREATE_RESERVED_PORT_SOCKET) { printf("please start qping as root\n"); break; } /* * set message tag we want to receive from endpoint */ switch(dump_tag) { case 1: { snprintf(command_buffer,256,"set tag ALL"); break; } case 2: { snprintf(command_buffer,256,"set tag APP"); break; } case 3: { snprintf(command_buffer,256,"set tag MSG"); break; } } cl_commlib_send_message(handle, resolved_comp_host, comp_name, comp_id, CL_MIH_MAT_NAK, &reference, strlen(command_buffer)+1, NULL, 0, 0, CL_TRUE, CL_FALSE); /* * set if we want the message dump */ if (cl_show[11] != 0) { snprintf(command_buffer,256,"set dump ON"); } else { snprintf(command_buffer,256,"set dump OFF"); } cl_commlib_send_message(handle, resolved_comp_host, comp_name, comp_id, CL_MIH_MAT_NAK, &reference, strlen(command_buffer)+1, NULL, 0, 0, CL_TRUE, CL_FALSE); /* * set debug level */ switch(option_debuglevel) { case 1: { snprintf(command_buffer,256,"set debug ERROR"); break; } case 2: { snprintf(command_buffer,256,"set debug WARNING"); break; } case 3: { snprintf(command_buffer,256,"set debug INFO"); break; } case 4: { snprintf(command_buffer,256,"set debug DEBUG"); break; } case 5: { snprintf(command_buffer,256,"set debug DPRINTF"); break; } default: { snprintf(command_buffer,256,"set debug OFF"); break; } } cl_commlib_send_message(handle, resolved_comp_host, comp_name, comp_id, CL_MIH_MAT_NAK, &reference, strlen(command_buffer)+1, NULL, 0, 0, CL_TRUE, CL_FALSE); } } else { int i; for (i=0; i < message->message_length; i++) { sge_dstring_append_char(&line_buffer, message->message[i]); if (message->message[i] == '\n') { qping_print_line(sge_dstring_get_string(&line_buffer), option_nonewline, dump_tag, sender->comp_name); sge_dstring_free(&line_buffer); } } fflush(stdout); cl_com_free_message(&message); cl_com_free_endpoint(&sender); } } sge_dstring_free(&line_buffer); } retval = cl_commlib_shutdown_handle(handle,CL_FALSE); if (retval != CL_RETVAL_OK) { fprintf(stderr,"%s\n",cl_get_error_text(retval)); free(resolved_comp_host); resolved_comp_host = NULL; cl_com_cleanup_commlib(); exit(1); } retval = cl_com_cleanup_commlib(); if (retval != CL_RETVAL_OK) { fprintf(stderr,"%s\n",cl_get_error_text(retval)); free(resolved_comp_host); resolved_comp_host = NULL; exit(1); } free(resolved_comp_host); resolved_comp_host = NULL; sge_prof_cleanup(); return exit_value; }