diff --git a/ipmitool/doc/ipmitool.1.in b/ipmitool/doc/ipmitool.1.in index 682d815..9af477d 100644 --- a/ipmitool/doc/ipmitool.1.in +++ b/ipmitool/doc/ipmitool.1.in @@ -302,10 +302,10 @@ This command will read the SDR and extract sensor information, then query each s This command will list sensors and thresholds in a wide table format. .TP \fIget\fP <\fBid\fR> -This command will print info for a single sensor specified by numeric ID or name. +This command will print info for a single sensor specified by or name. .TP \fIthresh\fP <\fBid\fR> <\fBthreshold\fR> <\fBsetting\fR> -This allows you to set a particular sensor threshold value. The sensor can be specified by numeric ID or name. +This allows you to set a particular sensor threshold value. The sensor is specified by name. .RS .TP Valid thresholds are: diff --git a/ipmitool/include/ipmitool/ipmi_sdr.h b/ipmitool/include/ipmitool/ipmi_sdr.h index e0a424e..1fc1efa 100644 --- a/ipmitool/include/ipmitool/ipmi_sdr.h +++ b/ipmitool/include/ipmitool/ipmi_sdr.h @@ -576,6 +576,19 @@ struct ipmi_sdr_iterator int next; }; +struct sdr_record_list { + unsigned short id; + unsigned char type; + struct sdr_record_list * next; + union { + struct sdr_record_full_sensor * full; + struct sdr_record_compact_sensor * compact; + struct sdr_record_eventonly_sensor * eventonly; + struct sdr_record_fru_locator * fruloc; + struct sdr_record_mc_locator * mcloc; + } record; +}; + /* unit description codes (IPMI v1.5 section 37.16) */ #define UNIT_MAX 0x90 static const char * unit_desc[] __attribute__((unused)) = { @@ -630,8 +643,13 @@ unsigned char sdr_convert_sensor_value_to_raw(struct sdr_record_full_sensor * se struct ipmi_rs * ipmi_sdr_get_sensor_reading(struct ipmi_intf * intf, unsigned char sensor); const char * ipmi_sdr_get_sensor_type_desc(const unsigned char type); -struct sdr_record_full_sensor *ipmi_sdr_find_sdr_byid(struct ipmi_intf * intf, char * id); -struct sdr_record_full_sensor *ipmi_sdr_find_sdr_bynum(struct ipmi_intf * intf, unsigned char num); +void ipmi_sdr_print_sensor_full(struct ipmi_intf * intf, struct sdr_record_full_sensor * sensor); +void ipmi_sdr_print_sensor_compact(struct ipmi_intf * intf, struct sdr_record_compact_sensor * sensor); +void ipmi_sdr_print_sensor_eventonly(struct ipmi_intf * intf, struct sdr_record_eventonly_sensor * sensor); +void ipmi_sdr_print_fru_locator(struct ipmi_intf * intf, struct sdr_record_fru_locator * fru); +void ipmi_sdr_print_mc_locator(struct ipmi_intf * intf, struct sdr_record_mc_locator * mc); + +struct sdr_record_list * ipmi_sdr_find_sdr_byid(struct ipmi_intf * intf, char * id); void ipmi_sdr_list_empty(void); #endif /* IPMI_SDR_H */ diff --git a/ipmitool/lib/ipmi_sdr.c b/ipmitool/lib/ipmi_sdr.c index 1de57c4..1bd8a7c 100644 --- a/ipmitool/lib/ipmi_sdr.c +++ b/ipmitool/lib/ipmi_sdr.c @@ -49,11 +49,7 @@ extern int verbose; static int sdr_max_read_len = GET_SDR_ENTIRE_RECORD; -struct sdr_records_full { - struct sdr_record_full_sensor * record; - struct sdr_records_full * next; -}; -static struct sdr_records_full * sdr_list_head = NULL; +static struct sdr_record_list * sdr_list_head = NULL; /* convert unsigned value to 2's complement signed */ int utos(unsigned val, unsigned bits) @@ -241,9 +237,8 @@ static inline int get_offset(unsigned char x) return 0; } -static void -ipmi_sdr_print_sensor_full(struct ipmi_intf * intf, - struct sdr_record_full_sensor * sensor) +void ipmi_sdr_print_sensor_full(struct ipmi_intf * intf, + struct sdr_record_full_sensor * sensor) { char sval[16], unitstr[16], desc[17]; int i=0, validread=1, do_unit=1; @@ -513,9 +508,8 @@ ipmi_sdr_print_sensor_full(struct ipmi_intf * intf, } } -static void -ipmi_sdr_print_sensor_compact(struct ipmi_intf * intf, - struct sdr_record_compact_sensor * sensor) +void ipmi_sdr_print_sensor_compact(struct ipmi_intf * intf, + struct sdr_record_compact_sensor * sensor) { struct ipmi_rs * rsp; char desc[17]; @@ -633,9 +627,8 @@ ipmi_sdr_print_sensor_compact(struct ipmi_intf * intf, } } -static void -ipmi_sdr_print_sensor_eventonly(struct ipmi_intf * intf, - struct sdr_record_eventonly_sensor * sensor) +void ipmi_sdr_print_sensor_eventonly(struct ipmi_intf * intf, + struct sdr_record_eventonly_sensor * sensor) { char desc[17]; @@ -669,9 +662,8 @@ ipmi_sdr_print_sensor_eventonly(struct ipmi_intf * intf, } } -static void -ipmi_sdr_print_mc_locator(struct ipmi_intf * intf, - struct sdr_record_mc_locator * mc) +void ipmi_sdr_print_mc_locator(struct ipmi_intf * intf, + struct sdr_record_mc_locator * mc) { char desc[17]; @@ -744,9 +736,8 @@ ipmi_sdr_print_mc_locator(struct ipmi_intf * intf, printf("\n"); } -static void -ipmi_sdr_print_fru_locator(struct ipmi_intf * intf, - struct sdr_record_fru_locator * fru) +void ipmi_sdr_print_fru_locator(struct ipmi_intf * intf, + struct sdr_record_fru_locator * fru) { char desc[17]; @@ -790,8 +781,7 @@ ipmi_sdr_print_fru_locator(struct ipmi_intf * intf, printf("\n"); } -void -ipmi_sdr_print_sdr(struct ipmi_intf * intf, unsigned char type) +void ipmi_sdr_print_sdr(struct ipmi_intf * intf, unsigned char type) { struct sdr_get_rs * header; struct ipmi_sdr_iterator * itr; @@ -1012,7 +1002,7 @@ int ipmi_sdr_list_fill(struct ipmi_intf * intf) { struct sdr_get_rs * header; struct ipmi_sdr_iterator * itr; - static struct sdr_records_full * sdr_list_tail; + static struct sdr_record_list * sdr_list_tail; itr = ipmi_sdr_start(intf); if (!itr) { @@ -1021,29 +1011,46 @@ int ipmi_sdr_list_fill(struct ipmi_intf * intf) } while (header = ipmi_sdr_get_next_header(intf, itr)) { - struct sdr_record_full_sensor * sdr; - struct sdr_records_full * sdrr; + unsigned char * rec; + struct sdr_record_full_sensor * full; + struct sdr_record_compact_sensor * compact; + struct sdr_record_list * sdrr; - if (header->type != SDR_RECORD_TYPE_FULL_SENSOR) + sdrr = malloc(sizeof(struct sdr_record_list)); + memset(sdrr, 0, sizeof(struct sdr_record_list)); + sdrr->id = header->id; + sdrr->type = header->type; + + rec = ipmi_sdr_get_record(intf, header, itr); + if (!rec) continue; - sdr = (struct sdr_record_full_sensor *)ipmi_sdr_get_record(intf, header, itr); - if (!sdr) + switch (header->type) { + case SDR_RECORD_TYPE_FULL_SENSOR: + sdrr->record.full = (struct sdr_record_full_sensor *)rec; + break; + case SDR_RECORD_TYPE_COMPACT_SENSOR: + sdrr->record.compact = (struct sdr_record_compact_sensor *)rec; + break; + case SDR_RECORD_TYPE_EVENTONLY_SENSOR: + sdrr->record.eventonly = (struct sdr_record_eventonly_sensor *)rec; + break; + case SDR_RECORD_TYPE_FRU_DEVICE_LOCATOR: + sdrr->record.fruloc = (struct sdr_record_fru_locator *)rec; + break; + case SDR_RECORD_TYPE_MC_DEVICE_LOCATOR: + sdrr->record.mcloc = (struct sdr_record_mc_locator *)rec; + break; + default: + free(rec); continue; - - sdrr = malloc(sizeof(struct sdr_records_full)); - memset(sdrr, 0, sizeof(struct sdr_records_full)); - - sdrr->record = sdr; + } if (!sdr_list_head) sdr_list_head = sdrr; else sdr_list_tail->next = sdrr; sdr_list_tail = sdrr; - - if (verbose > 3) - printf("added list entry %x\n", sdrr->record->keys.sensor_num); } ipmi_sdr_end(intf, itr); @@ -1051,37 +1058,43 @@ int ipmi_sdr_list_fill(struct ipmi_intf * intf) return 0; } -struct sdr_record_full_sensor * +struct sdr_record_list * ipmi_sdr_find_sdr_byid(struct ipmi_intf * intf, char * id) { - static struct sdr_records_full * e; + static struct sdr_record_list * e; if (!sdr_list_head) ipmi_sdr_list_fill(intf); e = sdr_list_head; while (e) { - if (!strncmp(e->record->id_string, id, e->record->id_code & 0x3f)) - return e->record; - e = e->next; - } - - return NULL; -} - -struct sdr_record_full_sensor * -ipmi_sdr_find_sdr_bynum(struct ipmi_intf * intf, unsigned char num) -{ - static struct sdr_records_full * e; - - if (!sdr_list_head) - ipmi_sdr_list_fill(intf); - - e = sdr_list_head; - - while (e) { - if (e->record->keys.sensor_num == num) - return e->record; + switch (e->type) { + case SDR_RECORD_TYPE_FULL_SENSOR: + if (!strncmp(e->record.full->id_string, id, + e->record.full->id_code & 0x1f)) + return e; + break; + case SDR_RECORD_TYPE_COMPACT_SENSOR: + if (!strncmp(e->record.compact->id_string, id, + e->record.compact->id_code & 0x1f)) + return e; + break; + case SDR_RECORD_TYPE_EVENTONLY_SENSOR: + if (!strncmp(e->record.eventonly->id_string, id, + e->record.eventonly->id_code & 0x1f)) + return e; + break; + case SDR_RECORD_TYPE_FRU_DEVICE_LOCATOR: + if (!strncmp(e->record.fruloc->id_string, id, + e->record.fruloc->id_code & 0x1f)) + return e; + break; + case SDR_RECORD_TYPE_MC_DEVICE_LOCATOR: + if (!strncmp(e->record.mcloc->id_string, id, + e->record.mcloc->id_code & 0x1f)) + return e; + break; + } e = e->next; } @@ -1090,14 +1103,32 @@ ipmi_sdr_find_sdr_bynum(struct ipmi_intf * intf, unsigned char num) void ipmi_sdr_list_empty(void) { - struct sdr_records_full *list, *next; + struct sdr_record_list *list, *next; list = sdr_list_head; while (list) { - if (verbose > 3) - printf("cleared sdr entry %x\n", list->record->keys.sensor_num); - if (list->record) - free(list->record); + switch (list->type) { + case SDR_RECORD_TYPE_FULL_SENSOR: + if (list->record.full) + free(list->record.full); + break; + case SDR_RECORD_TYPE_COMPACT_SENSOR: + if (list->record.compact) + free(list->record.compact); + break; + case SDR_RECORD_TYPE_EVENTONLY_SENSOR: + if (list->record.eventonly) + free(list->record.eventonly); + break; + case SDR_RECORD_TYPE_FRU_DEVICE_LOCATOR: + if (list->record.fruloc) + free(list->record.fruloc); + break; + case SDR_RECORD_TYPE_MC_DEVICE_LOCATOR: + if (list->record.mcloc) + free(list->record.mcloc); + break; + } next = list->next; free(list); list = next; diff --git a/ipmitool/lib/ipmi_sensor.c b/ipmitool/lib/ipmi_sensor.c index 36c0895..b87f384 100644 --- a/ipmitool/lib/ipmi_sensor.c +++ b/ipmitool/lib/ipmi_sensor.c @@ -617,13 +617,13 @@ ipmi_sensor_set_threshold(struct ipmi_intf * intf, int argc, char ** argv) * thresh; unsigned char settingMask; float setting; - struct sdr_record_full_sensor * sdr; + struct sdr_record_list * sdr; struct ipmi_rs * rsp; if (argc < 3 || !strncmp(argv[0], "help", 4)) { printf("sensor thresh \n"); - printf(" id : name or number of the sensor for which threshold is to be set\n"); + printf(" id : name of the sensor for which threshold is to be set\n"); printf(" threshold : which threshold to set\n"); printf(" unr = upper non-recoverable\n"); printf(" ucr = upper critical\n"); @@ -669,24 +669,25 @@ ipmi_sensor_set_threshold(struct ipmi_intf * intf, int argc, char ** argv) } printf("Locating sensor record...\n"); + /* lookup by sensor name */ sdr = ipmi_sdr_find_sdr_byid(intf, id); - if (!sdr) - { - /* lookup by sensor number */ - unsigned char num = (unsigned char)strtol(id, NULL, 0); - sdr = ipmi_sdr_find_sdr_bynum(intf, num); - } if (sdr) { - printf("Setting sensor \"%s\" %s threshold to %.3f\n", - sdr->id_string, val2str(settingMask, threshold_vals), setting); - rsp = ipmi_sensor_set_sensor_thresholds(intf, - sdr->keys.sensor_num, - settingMask, - sdr_convert_sensor_value_to_raw(sdr, setting)); - if (rsp && rsp->ccode) - printf("Error setting threshold: 0x%x\n", rsp->ccode); + if (sdr->type != SDR_RECORD_TYPE_FULL_SENSOR) + { + printf("Invalid sensor type %02x\n", sdr->type); + } + else + { + printf("Setting sensor \"%s\" %s threshold to %.3f\n", + sdr->record.full->id_string, val2str(settingMask, threshold_vals), setting); + rsp = ipmi_sensor_set_sensor_thresholds(intf, + sdr->record.full->keys.sensor_num, settingMask, + sdr_convert_sensor_value_to_raw(sdr->record.full, setting)); + if (rsp && rsp->ccode) + printf("Error setting threshold: 0x%x\n", rsp->ccode); + } } else { @@ -698,26 +699,36 @@ ipmi_sensor_set_threshold(struct ipmi_intf * intf, int argc, char ** argv) static void ipmi_sensor_get(struct ipmi_intf * intf, char * id) { - struct sdr_record_full_sensor * sdr; + struct sdr_record_list * sdr; if (!id || !strncmp(id, "help", 4)) { printf("sensor get \n"); - printf(" id : name or number desired sensor\n"); + printf(" id : name of desired sensor\n"); return; } printf("Locating sensor record...\n"); /* lookup by sensor name */ sdr = ipmi_sdr_find_sdr_byid(intf, id); - if (!sdr) { - /* lookup by sensor number */ - unsigned char num = (unsigned char)strtol(id, NULL, 0); - sdr = ipmi_sdr_find_sdr_bynum(intf, num); - } - if (sdr) { verbose = verbose ? : 1; - ipmi_sensor_print_full(intf, sdr); + switch (sdr->type) { + case SDR_RECORD_TYPE_FULL_SENSOR: + ipmi_sensor_print_full(intf, sdr->record.full); + break; + case SDR_RECORD_TYPE_COMPACT_SENSOR: + ipmi_sensor_print_compact(intf, sdr->record.compact); + break; + case SDR_RECORD_TYPE_EVENTONLY_SENSOR: + ipmi_sdr_print_sensor_eventonly(intf, sdr->record.eventonly); + break; + case SDR_RECORD_TYPE_FRU_DEVICE_LOCATOR: + ipmi_sdr_print_fru_locator(intf, sdr->record.fruloc); + break; + case SDR_RECORD_TYPE_MC_DEVICE_LOCATOR: + ipmi_sdr_print_mc_locator(intf, sdr->record.mcloc); + break; + } } else { printf("Sensor data record not found!\n"); }