Changeset 4834

Show
Ignore:
Timestamp:
09/23/07 14:05:16 (6 years ago)
Author:
khali
Message:

Define a separate structure to represent main features. This allows
for faster main features lookup. One side effect of this change is
that subfeatures can no longer have labels nor be ignored. I do not
think that this is a problem in practice, and actually this makes a
lot of sense.

Location:
lm-sensors/branches/lm-sensors-3.0.0
Files:
11 modified

Legend:

Unmodified
Added
Removed
  • lm-sensors/branches/lm-sensors-3.0.0/lib/access.c

    r4832 r4834  
    142142   yourself). On failure, NULL is returned. 
    143143   If no label exists for this feature, its name is returned itself. */ 
    144 char *sensors_get_label(const sensors_chip_name *name, int feature) 
     144char *sensors_get_label(const sensors_chip_name *name, 
     145                        const sensors_feature *feature) 
    145146{ 
    146147        char *label; 
    147148        const sensors_chip *chip; 
    148         const sensors_subfeature *featureptr; 
    149149        char buf[128], path[PATH_MAX]; 
    150150        FILE *f; 
     
    153153        if (sensors_chip_name_has_wildcards(name)) 
    154154                return NULL; 
    155         if (!(featureptr = sensors_lookup_feature_nr(name, feature))) 
    156                 return NULL; 
    157155 
    158156        for (chip = NULL; (chip = sensors_for_all_config_chips(name, chip));) 
    159157                for (i = 0; i < chip->labels_count; i++) 
    160                         if (!strcmp(featureptr->name, chip->labels[i].name)) { 
     158                        if (!strcmp(feature->name, chip->labels[i].name)) { 
    161159                                label = strdup(chip->labels[i].value); 
    162160                                goto sensors_get_label_exit; 
     
    164162 
    165163        /* No user specified label, check for a _label sysfs file */ 
    166         snprintf(path, PATH_MAX, "%s/%s_label", name->path, 
    167                 featureptr->name); 
     164        snprintf(path, PATH_MAX, "%s/%s_label", name->path, feature->name); 
    168165         
    169166        if ((f = fopen(path, "r"))) { 
     
    179176 
    180177        /* No label, return the feature name instead */ 
    181         label = strdup(featureptr->name); 
     178        label = strdup(feature->name); 
    182179         
    183180sensors_get_label_exit: 
     
    189186 
    190187/* Looks up whether a feature should be ignored. Returns 
    191    1 if it should be ignored, 0 if not. This function takes 
    192    mappings into account. */ 
     188   1 if it should be ignored, 0 if not. */ 
    193189static int sensors_get_ignored(const sensors_chip_name *name, 
    194                                const sensors_subfeature *feature) 
     190                               const sensors_feature *feature) 
    195191{ 
    196192        const sensors_chip *chip; 
    197         const char *main_feature_name; 
    198193        int i; 
    199  
    200         if (feature->mapping == SENSORS_NO_MAPPING) 
    201                 main_feature_name = NULL; 
    202         else 
    203                 main_feature_name = sensors_lookup_feature_nr(name, 
    204                                         feature->mapping)->name; 
    205194 
    206195        for (chip = NULL; (chip = sensors_for_all_config_chips(name, chip));) 
    207196                for (i = 0; i < chip->ignores_count; i++) 
    208                         if (!strcmp(feature->name, chip->ignores[i].name) || 
    209                             (main_feature_name && 
    210                              !strcmp(main_feature_name, chip->ignores[i].name))) 
     197                        if (!strcmp(feature->name, chip->ignores[i].name)) 
    211198                                return 1; 
    212199        return 0; 
     
    353340                if (sensors_match_chip(&sensors_proc_chips[i].chip, name)) { 
    354341                        subfeature_list = sensors_proc_chips[i].subfeature; 
    355                         while (*nr < sensors_proc_chips[i].subfeature_count 
    356                             && sensors_get_ignored(name, &subfeature_list[*nr])) 
    357                                 (*nr)++; 
    358                         if (*nr == sensors_proc_chips[i].subfeature_count) 
     342                        if (*nr >= sensors_proc_chips[i].subfeature_count) 
    359343                                return NULL; 
    360344                        return &subfeature_list[(*nr)++]; 
     
    363347} 
    364348 
     349const sensors_feature * 
     350sensors_get_features(const sensors_chip_name *name, int *nr) 
     351{ 
     352        const sensors_feature *feature_list; 
     353        int i; 
     354 
     355        for (i = 0; i < sensors_proc_chips_count; i++) 
     356                if (sensors_match_chip(&sensors_proc_chips[i].chip, name)) { 
     357                        feature_list = sensors_proc_chips[i].feature; 
     358                        while (*nr < sensors_proc_chips[i].feature_count 
     359                            && sensors_get_ignored(name, &feature_list[*nr])) 
     360                                (*nr)++; 
     361                        if (*nr >= sensors_proc_chips[i].feature_count) 
     362                                return NULL; 
     363                        return &feature_list[(*nr)++]; 
     364                } 
     365        return NULL;    /* end of list */ 
     366} 
     367 
    365368const sensors_subfeature * 
    366 sensors_get_features(const sensors_chip_name *name, int *nr) 
    367 { 
    368         const sensors_subfeature *feature; 
    369  
    370         while ((feature = sensors_get_all_features(name, nr))) { 
    371                 if (feature->mapping == SENSORS_NO_MAPPING) 
    372                         return feature; 
    373         } 
    374         return NULL;    /* end of list */ 
    375 } 
    376  
    377 const sensors_subfeature * 
    378 sensors_get_all_subfeatures(const sensors_chip_name *name, int feature, int *nr) 
     369sensors_get_all_subfeatures(const sensors_chip_name *name, 
     370                        const sensors_feature *feature, int *nr) 
    379371{ 
    380372        const sensors_subfeature *subfeature; 
    381373 
    382374        /* Seek directly to the first subfeature */ 
    383         if (*nr < feature) 
    384                 *nr = feature; 
     375        if (*nr < feature->first_subfeature) 
     376                *nr = feature->first_subfeature; 
    385377 
    386378        subfeature = sensors_get_all_features(name, nr); 
    387379        if (!subfeature) 
    388380                return NULL;    /* end of list */ 
    389         if (subfeature->number == feature || 
    390             subfeature->mapping == feature) 
     381        if (subfeature->number == feature->first_subfeature || 
     382            subfeature->mapping == feature->first_subfeature) 
    391383                return subfeature; 
    392384        return NULL;            /* end of subfeature list */ 
  • lm-sensors/branches/lm-sensors-3.0.0/lib/data.h

    r4832 r4834  
    124124typedef struct sensors_chip_features { 
    125125        struct sensors_chip_name chip; 
     126        struct sensors_feature *feature; 
    126127        struct sensors_subfeature *subfeature; 
     128        int feature_count; 
    127129        int subfeature_count; 
    128130} sensors_chip_features; 
  • lm-sensors/branches/lm-sensors-3.0.0/lib/init.c

    r4832 r4834  
    6060                free(features->subfeature[i].name); 
    6161        free(features->subfeature); 
     62        for (i = 0; i < features->feature_count; i++) 
     63                free(features->feature[i].name); 
     64        free(features->feature); 
    6265} 
    6366 
  • lm-sensors/branches/lm-sensors-3.0.0/lib/libsensors.3

    r4832 r4834  
    3737                            \fBsensors_chip_name *res);\fP 
    3838.B const char *sensors_get_adapter_name(int bus_nr); 
    39 .B char *sensors_get_label(const sensors_chip_name *name, int feature);\fP 
     39.B char *sensors_get_label(const sensors_chip_name *name, const sensors_feature *feature);\fP 
    4040.B int sensors_get_value(const sensors_chip_name *name, int feature, 
    4141                      \fBdouble *value);\fP 
     
    4545.B const sensors_chip_name *sensors_get_detected_chips(const sensors_chip_name 
    4646                                                    \fB*match, int *nr);\fP 
    47 .B const sensors_feature_data *sensors_get_features 
    48              \fB(const sensors_chip_name *name, int *nr);\fP 
    49 .B const sensors_feature_data *sensors_get_all_subfeatures 
    50              \fB(const sensors_chip_name *name, int feature, int *nr);\fP 
     47.B const sensors_feature *sensors_get_features(const sensors_chip_name *name, int *nr);\fP 
     48.B const sensors_subfeature *sensors_get_all_subfeatures(const sensors_chip_name *name, const sensors_feature *feature, int *nr);\fP 
    5149.B const char *libsensors_version; 
    5250.fi 
     
    7472sensors_chip_name structure. If it could not be found, it returns NULL. 
    7573 
    76 \fBchar *sensors_get_label(const sensors_chip_name *name, int feature);\fP 
     74\fBchar *sensors_get_label(const sensors_chip_name *name, const sensors_feature *feature);\fP 
    7775.br 
    7876Look up the label which belongs to this chip. Note that chip should not 
     
    125123(affected by the computation rules of the main feature). 
    126124 
    127 \fBconst sensors_feature_data *sensors_get_features(const sensors_chip_name *name, int *nr);\fP 
     125\fBconst sensors_feature *sensors_get_features(const sensors_chip_name *name, int *nr);\fP 
    128126.br 
    129127This returns all main features of a specific chip. nr is an internally 
     
    133131data structures. 
    134132 
    135 \fBconst sensors_feature_data *sensors_get_all_subfeatures(const sensors_chip_name *name, int feature, int *nr);\fP 
     133\fBconst sensors_subfeature *sensors_get_all_subfeatures(const sensors_chip_name *name, const sensors_feature *feature, int *nr);\fP 
    136134.br 
    137135This returns all subfeatures of a given main feature (including that 
    138136main feature itself, in first position.) nr is an internally used 
    139137variable. Set it to zero to start at the begin of the list. If no more 
    140 features are found NULL is returned. 
     138subfeatures are found NULL is returned. 
    141139Do not try to change the returned structure; you will corrupt internal 
    142140data structures. 
  • lm-sensors/branches/lm-sensors-3.0.0/lib/sensors.h

    r4832 r4834  
    8383const char *sensors_get_adapter_name(const sensors_bus_id *bus); 
    8484 
     85typedef struct sensors_feature sensors_feature; 
     86 
    8587/* Look up the label which belongs to this chip. Note that chip should not 
    8688   contain wildcard values! The returned string is newly allocated (free it 
    8789   yourself). On failure, NULL is returned. 
    8890   If no label exists for this feature, its name is returned itself. */ 
    89 char *sensors_get_label(const sensors_chip_name *name, int feature); 
     91char *sensors_get_label(const sensors_chip_name *name, 
     92                        const sensors_feature *feature); 
    9093 
    9194/* Read the value of a feature of a certain chip. Note that chip should not 
     
    163166        SENSORS_FEATURE_UNKNOWN = INT_MAX, 
    164167} sensors_feature_type; 
     168 
     169/* Data about a single chip feature (or category leader) */ 
     170struct sensors_feature { 
     171        char *name; 
     172        int first_subfeature; 
     173        sensors_feature_type type; 
     174}; 
    165175 
    166176/* Data about a single chip subfeature: 
     
    189199   Do not try to change the returned structure; you will corrupt internal 
    190200   data structures. */ 
    191 const sensors_subfeature * 
     201const sensors_feature * 
    192202sensors_get_features(const sensors_chip_name *name, int *nr); 
    193203 
     
    199209   data structures. */ 
    200210const sensors_subfeature * 
    201 sensors_get_all_subfeatures(const sensors_chip_name *name, int feature, int *nr); 
     211sensors_get_all_subfeatures(const sensors_chip_name *name, 
     212                            const sensors_feature *feature, int *nr); 
    202213 
    203214#ifdef __cplusplus 
  • lm-sensors/branches/lm-sensors-3.0.0/lib/sysfs.c

    r4832 r4834  
    164164        sensors_subfeature *features; 
    165165        sensors_subfeature *dyn_subfeatures; 
     166        sensors_feature *dyn_features; 
    166167 
    167168        attrs = sysfs_get_device_attributes(sysdir); 
     
    290291        chip->subfeature_count = fnum; 
    291292 
     293        /* And now the main features */ 
     294        fnum = 0; 
     295        for (i = 0; i < chip->subfeature_count; i++) { 
     296                if (chip->subfeature[i].mapping == SENSORS_NO_MAPPING) 
     297                        fnum++; 
     298        } 
     299 
     300        dyn_features = calloc(fnum, sizeof(sensors_feature)); 
     301        if (dyn_features == NULL) { 
     302                sensors_fatal_error(__FUNCTION__, "Out of memory"); 
     303        } 
     304 
     305        fnum = 0; 
     306        for (i = 0; i < chip->subfeature_count; i++) { 
     307                if (chip->subfeature[i].mapping == SENSORS_NO_MAPPING) { 
     308                        dyn_features[fnum].name = strdup(chip->subfeature[i].name); 
     309                        dyn_features[fnum].first_subfeature = i; 
     310                        dyn_features[fnum].type = chip->subfeature[i].type; 
     311                        fnum++; 
     312                } 
     313        } 
     314 
     315        chip->feature = dyn_features; 
     316        chip->feature_count = fnum; 
     317 
    292318exit_free: 
    293319        free(features); 
  • lm-sensors/branches/lm-sensors-3.0.0/prog/sensord/chips.c

    r4833 r4834  
    142142 
    143143static void getAvailableFeatures (const sensors_chip_name *name, 
    144                                   const sensors_subfeature *feature, 
     144                                  const sensors_feature *feature, 
    145145                                  short *has_features, 
    146146                                  int *feature_nrs, int size, 
     
    150150  int i = 0; 
    151151 
    152   while ((iter = sensors_get_all_subfeatures(name, feature->number, &i))) { 
     152  while ((iter = sensors_get_all_subfeatures(name, feature, &i))) { 
    153153    int index0; 
    154154 
     
    167167static void fillChipVoltage (FeatureDescriptor *voltage, 
    168168                             const sensors_chip_name *name, 
    169                              const sensors_subfeature *feature) 
     169                             const sensors_feature *feature) 
    170170{ 
    171171  const int size = SENSORS_FEATURE_IN_BEEP - SENSORS_FEATURE_IN + 1; 
     
    216216static void fillChipTemperature (FeatureDescriptor *temperature, 
    217217                                 const sensors_chip_name *name, 
    218                                  const sensors_subfeature *feature) 
     218                                 const sensors_feature *feature) 
    219219{ 
    220220  const int size = SENSORS_FEATURE_TEMP_BEEP - SENSORS_FEATURE_TEMP + 1; 
     
    268268static void fillChipFan (FeatureDescriptor *fan, 
    269269                         const sensors_chip_name *name, 
    270                          const sensors_subfeature *feature) 
     270                         const sensors_feature *feature) 
    271271{ 
    272272  const int size = SENSORS_FEATURE_FAN_BEEP - SENSORS_FEATURE_FAN + 1; 
     
    313313 
    314314static void fillChipVid (FeatureDescriptor *vid, 
    315                          const sensors_subfeature *feature) 
    316 { 
     315                         const sensors_chip_name *name, 
     316                         const sensors_feature *feature) 
     317{ 
     318  int i = 0; 
     319  const sensors_subfeature *sub; 
     320 
     321  sub = sensors_get_all_subfeatures(name, feature, &i); 
     322  if (!sub) 
     323    return; 
     324 
    317325  vid->format = fmtVolt_3; 
    318326  vid->rrd = rrdF3; 
     
    320328  vid->alarmNumber = -1; 
    321329  vid->beepNumber = -1; 
    322   vid->dataNumbers[0] = feature->number; 
     330  vid->dataNumbers[0] = sub->number; 
    323331  vid->dataNumbers[1] = -1; 
    324332} 
    325333 
    326334static void fillChipBeepEnable (FeatureDescriptor *beepen, 
    327                                 const sensors_subfeature *feature) 
    328 { 
     335                                const sensors_chip_name *name, 
     336                                const sensors_feature *feature) 
     337{ 
     338  int i = 0; 
     339  const sensors_subfeature *sub; 
     340 
     341  sub = sensors_get_all_subfeatures(name, feature, &i); 
     342  if (!sub) 
     343    return; 
     344 
    329345  beepen->format = fmtSoundAlarm; 
    330346  beepen->rrd = rrdF0; 
     
    332348  beepen->alarmNumber = -1; 
    333349  beepen->beepNumber = -1; 
    334   beepen->dataNumbers[0] = feature->number; 
     350  beepen->dataNumbers[0] = sub->number; 
    335351  beepen->dataNumbers[1] = -1; 
    336352} 
     
    340356{ 
    341357        int nr, count = 1; 
    342         const sensors_subfeature *sensor; 
     358        const sensors_feature *sensor; 
    343359        FeatureDescriptor *features; 
    344360 
     
    368384                        break; 
    369385                case SENSORS_FEATURE_VID: 
    370                         fillChipVid(&features[count], sensor); 
     386                        fillChipVid(&features[count], chip, sensor); 
    371387                        break; 
    372388                case SENSORS_FEATURE_BEEP_ENABLE: 
    373                         fillChipBeepEnable(&features[count], sensor); 
     389                        fillChipBeepEnable(&features[count], chip, sensor); 
    374390                        break; 
    375391                default: 
     
    377393                } 
    378394 
     395                features[count].feature = sensor; 
    379396                count++; 
    380397        } 
  • lm-sensors/branches/lm-sensors-3.0.0/prog/sensord/rrd.c

    r4828 r4834  
    157157        for (index0 = 0; (ret == 0) && (num < MAX_RRD_SENSORS) && features[index0].format; ++ index0) { 
    158158          const FeatureDescriptor *feature = features + index0; 
    159           int labelNumber = feature->dataNumbers[0]; 
    160           const char *rawLabel = NULL; 
     159          const char *rawLabel = features->feature->name; 
    161160          char *label = NULL; 
    162161 
    163           if (getRawLabel (chip, labelNumber, &rawLabel)) { 
    164             sensorLog (LOG_ERR, "Error getting raw sensor label: %s/#%d", chip->prefix, labelNumber); 
    165             ret = -1; 
    166           } else if (!(label = sensors_get_label (chip, labelNumber))) { 
    167             sensorLog (LOG_ERR, "Error getting sensor label: %s/#%d", chip->prefix, labelNumber); 
     162          if (!(label = sensors_get_label (chip, features->feature))) { 
     163            sensorLog (LOG_ERR, "Error getting sensor label: %s/%s", chip->prefix, rawLabel); 
    168164            ret = -1; 
    169165          } else  { 
  • lm-sensors/branches/lm-sensors-3.0.0/prog/sensord/sense.c

    r4832 r4834  
    3333#define DO_SET 2 
    3434#define DO_RRD 3 
    35  
    36 int 
    37 getRawLabel 
    38 (const sensors_chip_name *name, int feature, const char **label) { 
    39   const sensors_subfeature *mainfeat, *sub; 
    40   int a, b; 
    41  
    42   a = 0; 
    43   while ((mainfeat = sensors_get_features(name, &a))) { 
    44     b = 0; 
    45     while ((sub = sensors_get_all_subfeatures(name, mainfeat->number, &b))) { 
    46       if (sub->number == feature) { 
    47         *label = sub->name; 
    48         return 0; 
    49       } 
    50     } 
    51   } 
    52   /* TODO: Ensure labels match RRD construct and are not repeated! */ 
    53   return -1; 
    54 } 
    5535 
    5636static const char * 
     
    8868  for (index0 = 0; (ret == 0) && features[index0].format; ++ index0) { 
    8969    const FeatureDescriptor *feature = features + index0; 
    90     int labelNumber = feature->dataNumbers[0]; 
    9170    int alarm, beep; 
    9271    char *label = NULL; 
    9372 
    94     if (!(label = sensors_get_label (chip, labelNumber))) { 
    95       sensorLog (LOG_ERR, "Error getting sensor label: %s/#%d", chip->prefix, labelNumber); 
     73    if (!(label = sensors_get_label (chip, feature->feature))) { 
     74      sensorLog (LOG_ERR, "Error getting sensor label: %s/%s", chip->prefix, feature->feature->name); 
    9675      ret = 22; 
    9776    } else { 
  • lm-sensors/branches/lm-sensors-3.0.0/prog/sensord/sensord.h

    r4828 r4834  
    5757/* from sense.c */ 
    5858 
    59 extern int getRawLabel (const sensors_chip_name *name, int feature, const char **label); 
    60  
    6159extern int readChips (void); 
    6260extern int scanChips (void); 
     
    9290  int alarmNumber; 
    9391  int beepNumber; 
    94   int dataNumbers[MAX_DATA + 1]; /* First entry is used for the label */ 
     92  const sensors_feature *feature; 
     93  int dataNumbers[MAX_DATA + 1]; 
    9594} FeatureDescriptor; 
    9695 
  • lm-sensors/branches/lm-sensors-3.0.0/prog/sensors/chips.c

    r4833 r4834  
    3232{ 
    3333        int a, b; 
    34         const sensors_subfeature *feature, *sub; 
     34        const sensors_feature *feature; 
     35        const sensors_subfeature *sub; 
    3536        char *label; 
    3637        double val; 
     
    3839        a = 0; 
    3940        while ((feature = sensors_get_features(name, &a))) { 
     41                if (!(label = sensors_get_label(name, feature))) { 
     42                        printf("ERROR: Can't get feature label!\n"); 
     43                        continue; 
     44                } 
     45                printf("%s:\n", label); 
     46                free(label); 
     47 
    4048                b = 0; 
    41                 while ((sub = sensors_get_all_subfeatures(name, feature->number, 
    42                                                       &b))) { 
    43                         if (!(label = sensors_get_label(name, sub->number))) { 
    44                                 printf("ERROR: Can't get feature `%s' label!\n", 
    45                                        sub->name); 
    46                                 continue; 
    47                         } 
     49                while ((sub = sensors_get_all_subfeatures(name, feature, &b))) { 
    4850                        if (sub->flags & SENSORS_MODE_R) { 
    4951                                if (sensors_get_value(name, sub->number, &val)) 
    5052                                        printf("ERROR: Can't get feature `%s' " 
    5153                                               "data!\n", sub->name); 
    52                                 else if (sub->mapping != SENSORS_NO_MAPPING) 
    53                                         printf("  %s: %.2f\n", label, val); 
    5454                                else 
    55                                         printf("%s: %.2f (%s)\n", label, val, 
    56                                                sub->name); 
     55                                        printf("  %s: %.2f\n", sub->name, val); 
    5756                        } else 
    5857                                printf("(%s)\n", label); 
    59                         free(label); 
    6058                } 
    6159        } 
     
    7472 
    7573static void sensors_get_available_features(const sensors_chip_name *name, 
    76                                            const sensors_subfeature *feature, 
     74                                           const sensors_feature *feature, 
    7775                                           short *has_features, 
    7876                                           double *feature_vals, int size, 
     
    8280        int i = 0; 
    8381 
    84         while ((iter = sensors_get_all_subfeatures(name, feature->number, &i))) { 
     82        while ((iter = sensors_get_all_subfeatures(name, feature, &i))) { 
    8583                int indx, err; 
    8684 
     
    104102{ 
    105103        int i; 
    106         const sensors_subfeature *iter; 
     104        const sensors_feature *iter; 
    107105        char *label; 
    108106        unsigned int max_size = 11;     /* 11 as minumum label width */ 
     
    110108        i = 0; 
    111109        while ((iter = sensors_get_features(name, &i))) { 
    112                 if ((label = sensors_get_label(name, iter->number)) && 
     110                if ((label = sensors_get_label(name, iter)) && 
    113111                    strlen(label) > max_size) 
    114112                        max_size = strlen(label); 
     
    144142#define TEMP_FEATURE_VAL(x)     feature_vals[x - SENSORS_FEATURE_TEMP] 
    145143static void print_chip_temp(const sensors_chip_name *name, 
    146                             const sensors_subfeature *feature, 
     144                            const sensors_feature *feature, 
    147145                            int label_size) 
    148146{ 
     
    155153        double feature_vals[SENSORS_FEATURE_TEMP_TYPE - SENSORS_FEATURE_TEMP + 1] = { 0.0, }; 
    156154 
    157         if (!(label = sensors_get_label(name, feature->number))) { 
     155        if (!(label = sensors_get_label(name, feature))) { 
    158156                printf("ERROR: Can't get temperature label!\n"); 
    159157                return; 
     
    277275#define IN_FEATURE_VAL(x)       feature_vals[x - SENSORS_FEATURE_IN] 
    278276static void print_chip_in(const sensors_chip_name *name, 
    279                           const sensors_subfeature *feature, 
     277                          const sensors_feature *feature, 
    280278                          int label_size) 
    281279{ 
     
    286284        char *label; 
    287285 
    288         if (!(label = sensors_get_label(name, feature->number))) { 
     286        if (!(label = sensors_get_label(name, feature))) { 
    289287                printf("ERROR: Can't get in label!\n"); 
    290288                return; 
     
    337335#define FAN_FEATURE_VAL(x)      feature_vals[x - SENSORS_FEATURE_FAN] 
    338336static void print_chip_fan(const sensors_chip_name *name, 
    339                            const sensors_subfeature *feature, 
     337                           const sensors_feature *feature, 
    340338                           int label_size) 
    341339{ 
     
    346344        double val; 
    347345 
    348         if (!(label = sensors_get_label(name, feature->number))) { 
     346        if (!(label = sensors_get_label(name, feature))) { 
    349347                printf("ERROR: Can't get fan label!\n"); 
    350348                return; 
     
    384382} 
    385383 
    386 static void print_chip_vid(const sensors_chip_name *name, int f_vid, 
     384static void print_chip_vid(const sensors_chip_name *name, 
     385                           const sensors_feature *feature, 
    387386                           int label_size) 
    388387{ 
    389388        char *label; 
     389        const sensors_subfeature *subfeature; 
    390390        double vid; 
    391  
    392         if ((label = sensors_get_label(name, f_vid)) 
    393          && !sensors_get_value(name, f_vid, &vid)) { 
     391        int i = 0; 
     392 
     393        subfeature = sensors_get_all_subfeatures(name, feature, &i); 
     394        if (!subfeature) 
     395                return; 
     396 
     397        if ((label = sensors_get_label(name, feature)) 
     398         && !sensors_get_value(name, subfeature->number, &vid)) { 
    394399                print_label(label, label_size); 
    395400                printf("%+6.3f V\n", vid); 
     
    398403} 
    399404 
    400 static void print_chip_beep_enable(const sensors_chip_name *name, int f_beep, 
     405static void print_chip_beep_enable(const sensors_chip_name *name, 
     406                                   const sensors_feature *feature, 
    401407                                   int label_size) 
    402408{ 
    403409        char *label; 
     410        const sensors_subfeature *subfeature; 
    404411        double beep_enable; 
    405  
    406         if ((label = sensors_get_label(name, f_beep)) 
    407          && !sensors_get_value(name, f_beep, &beep_enable)) { 
     412        int i = 0; 
     413 
     414        subfeature = sensors_get_all_subfeatures(name, feature, &i); 
     415        if (!subfeature) 
     416                return; 
     417 
     418        if ((label = sensors_get_label(name, feature)) 
     419         && !sensors_get_value(name, subfeature->number, &beep_enable)) { 
    408420                print_label(label, label_size); 
    409421                printf("%s\n", beep_enable ? "enabled" : "disabled"); 
     
    414426void print_chip(const sensors_chip_name *name) 
    415427{ 
    416         const sensors_subfeature *feature; 
     428        const sensors_feature *feature; 
    417429        int i, label_size; 
    418430 
     
    432444                        break; 
    433445                case SENSORS_FEATURE_VID: 
    434                         print_chip_vid(name, feature->number, label_size); 
     446                        print_chip_vid(name, feature, label_size); 
    435447                        break; 
    436448                case SENSORS_FEATURE_BEEP_ENABLE: 
    437                         print_chip_beep_enable(name, feature->number, 
    438                                                label_size); 
     449                        print_chip_beep_enable(name, feature, label_size); 
    439450                        break; 
    440451                default: