[lm-sensors] [PATCH] Parse the configuration file in C locale
Jean Delvare
khali at linux-fr.org
Mon Apr 7 22:03:55 CEST 2008
Hi Aurélien,
On Sun, 6 Apr 2008 22:58:39 +0200, Aurelien Jarno wrote:
> The configuration file is currently parsed in the locale set by the main
> program using the library. This means that if the decimal separator
> (defined in LC_NUMERIC) is not '.' the values in the compute lines are
> truncated. This happens for example with sensors-applet and a French
> locale.
Good catch.
>
> The patch below is an attempt to fix that. There may be more clever ways
> to do that, but currently I fail to find them.
>
>
> Index: lib/init.c
> ===================================================================
> --- lib/init.c (révision 5168)
> +++ lib/init.c (copie de travail)
> @@ -19,6 +19,7 @@
> MA 02110-1301 USA.
> */
>
> +#include <locale.h>
> #include <stdlib.h>
> #include <stdio.h>
> #include <errno.h>
> @@ -37,6 +38,7 @@
> int sensors_init(FILE *input)
> {
> int res;
> + char *locale = NULL;
>
> if (!sensors_init_sysfs())
> return -SENSORS_ERR_KERNEL;
> @@ -44,6 +46,13 @@
> (res = sensors_read_sysfs_chips()))
> goto exit_cleanup;
>
> + /* Read the current locale */
> + locale = setlocale(LC_NUMERIC, NULL);
> + if (locale)
> + locale = strdup(locale);
> + /* Set the locale to C */
> + setlocale(LC_NUMERIC, "C");
> +
> res = -SENSORS_ERR_PARSE;
> if (input) {
> if (sensors_scanner_init(input) ||
> @@ -64,11 +73,21 @@
> }
> }
>
> + /* Restore the old locale */
> + if (locale) {
> + setlocale(LC_NUMERIC, locale);
> + free(locale);
> + }
> if ((res = sensors_substitute_busses()))
> goto exit_cleanup;
> return 0;
>
> exit_cleanup:
> + /* Restore the old locale */
> + if (locale) {
> + setlocale(LC_NUMERIC, locale);
> + free(locale);
> + }
> sensors_cleanup();
> return res;
> }
>
I've come up with a variant where we don't need to duplicate the
clear-up step in the error path:
---
lib/init.c | 31 +++++++++++++++++++++++++++++--
1 file changed, 29 insertions(+), 2 deletions(-)
--- lib/init.c.orig 2008-04-07 21:32:53.000000000 +0200
+++ lib/init.c 2008-04-07 21:48:18.000000000 +0200
@@ -19,8 +19,10 @@
MA 02110-1301 USA.
*/
+#include <locale.h>
#include <stdlib.h>
#include <stdio.h>
+#include <string.h>
#include <errno.h>
#include "sensors.h"
#include "data.h"
@@ -34,6 +36,31 @@
#define DEFAULT_CONFIG_FILE ETCDIR "/sensors3.conf"
#define ALT_CONFIG_FILE ETCDIR "/sensors.conf"
+/* Wrapper around sensors_yyparse(), which clears the locale so that
+ the decimal numbers are always parsed properly. */
+static int sensors_parse(void)
+{
+ int res;
+ char *locale;
+
+ /* Remember the current locale and clear it */
+ locale = setlocale(LC_ALL, NULL);
+ if (locale) {
+ locale = strdup(locale);
+ setlocale(LC_ALL, "C");
+ }
+
+ res = sensors_yyparse();
+
+ /* Restore the old locale */
+ if (locale) {
+ setlocale(LC_ALL, locale);
+ free(locale);
+ }
+
+ return res;
+}
+
int sensors_init(FILE *input)
{
int res;
@@ -47,7 +74,7 @@ int sensors_init(FILE *input)
res = -SENSORS_ERR_PARSE;
if (input) {
if (sensors_scanner_init(input) ||
- sensors_yyparse())
+ sensors_parse())
goto exit_cleanup;
} else {
/* No configuration provided, use default */
@@ -56,7 +83,7 @@ int sensors_init(FILE *input)
input = fopen(ALT_CONFIG_FILE, "r");
if (input) {
if (sensors_scanner_init(input) ||
- sensors_yyparse()) {
+ sensors_parse()) {
fclose(input);
goto exit_cleanup;
}
I've also changed LC_NUMERIC for LC_ALL, as discussed on IRC. Otherwise
it's the same as your original patch.
I'll apply this patch tomorrow if nobody objects.
Thanks,
--
Jean Delvare
More information about the lm-sensors
mailing list