00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032 #include <glib.h>
00033 #include <glib/gstdio.h>
00034 #include <gconf/gconf-client.h>
00035 #include <sys/utsname.h>
00036 #include <unistd.h>
00037 #include <sys/stat.h>
00038
00039
00040
00041
00042 #include "log.h"
00043 #include "erconftool.h"
00044 #include "export.h"
00045 #include "show.h"
00046
00047 #define UNUSED(x) (void)(x)
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059 #define PATH_SYSSET "/sys/devices/system/sysset/sysset0/"
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071 static gboolean create_registry (const char *filename);
00072 static void export_device_info (GKeyFile *key_file);
00073 static void export_gconf (GConfClient *client, GKeyFile *key_file, const char *path, gboolean force_defaults);
00074 static void export_gconf_entries(GConfClient *client, GKeyFile *key_file, const char *path, gboolean force_defaults);
00075 static void export_gconf_entry (GConfClient *client, GKeyFile *key_file, GConfEntry* entry, gboolean force_defaults);
00076
00077 static gchar *get_file_content (const gchar* file_path);
00078 static char *get_kernel_version (void);
00079 static char *get_micro_bootloader_version (void);
00080 static char *get_micro_app_version (void);
00081 static char *get_sub_dir (const char* parent, const char* sub_dir);
00082
00083
00084
00085
00086
00087
00088 gboolean export_registry(GConfClient *client, const char *filename, const char **paths, gboolean force_defaults)
00089 {
00090 GKeyFile *key_file = NULL;
00091 FILE *inifile = NULL;
00092 GError *error = NULL;
00093
00094
00095
00096 key_file = g_key_file_new();
00097 if (!g_key_file_load_from_file(key_file, filename, G_KEY_FILE_KEEP_COMMENTS | G_KEY_FILE_KEEP_TRANSLATIONS, &error))
00098 {
00099 if (error->code == G_KEY_FILE_ERROR_PARSE)
00100 {
00101 g_error_free(error);
00102 error = NULL;
00103
00104 g_print("Error parsing file, backup as: %s.old\n", filename);
00105
00106 gchar *filename_old = g_strconcat(filename, ".old", NULL);
00107 unlink(filename_old);
00108 rename(filename, filename_old);
00109 g_free(filename_old);
00110 }
00111
00112 g_print("File does not exist, create new: %s\n", filename);
00113 if (!create_registry(filename))
00114 {
00115 g_print("Error creating new file: %s\n", filename);
00116 return FALSE;
00117 }
00118 }
00119
00120
00121
00122 export_device_info(key_file);
00123
00124
00125
00126 gint i;
00127 for (i = 0; paths[i]; i++)
00128 {
00129 export_gconf(client, key_file, paths[i], force_defaults);
00130 }
00131
00132
00133 #if 0 // disabled see PR3439
00134 export_pointercal(key_file);
00135 #endif
00136
00137
00138
00139 inifile = fopen(filename, "w");
00140 if (inifile == NULL)
00141 {
00142 g_print("Error writing file: %s\n", filename);
00143 g_key_file_free(key_file);
00144 return FALSE;
00145 }
00146 else
00147 {
00148 fprintf(inifile, "%s", g_key_file_to_data(key_file, NULL, NULL));
00149 fclose(inifile);
00150 }
00151
00152 g_key_file_free(key_file);
00153
00154 return TRUE;
00155 }
00156
00157
00158 static gboolean create_registry(const char *filename)
00159 {
00160
00161 gchar *path = g_path_get_dirname(filename);
00162 if (path)
00163 {
00164 gint rc = g_mkdir(path, 0755);
00165 g_free(path);
00166 if (rc < 0 && errno != EEXIST)
00167 {
00168
00169 g_printf("Error creating dir [%s]: %s\n", path, strerror(errno));
00170 return FALSE;
00171 }
00172 }
00173 else
00174 {
00175
00176 return FALSE;
00177 }
00178
00179
00180 if (!g_file_set_contents (filename, "", -1, NULL))
00181 {
00182
00183 return FALSE;
00184 }
00185
00186 return TRUE;
00187 }
00188
00189
00190 static void export_gconf_entry(GConfClient* client, GKeyFile *key_file, GConfEntry* entry, gboolean force_defaults)
00191 {
00192 UNUSED(client);
00193 const char* key = gconf_entry_get_key(entry);
00194 GConfValue* value = gconf_entry_get_value(entry);
00195 gboolean is_default = gconf_entry_get_is_default(entry);
00196
00197 #if (LOGGING_ON)
00198 show_entry(client, entry);
00199 #endif
00200
00201
00202 if ( is_default
00203 && !(force_defaults && g_key_file_has_key(key_file, INI_GROUP_REGISTRY, key, NULL)) )
00204 {
00205 LOGPRINTF("default key not exported: %s", key);
00206 return;
00207 }
00208
00209 LOGPRINTF("is_default [%d] force [%d] has_key [%d]", is_default, force_defaults, g_key_file_has_key(key_file, INI_GROUP_REGISTRY, key, NULL));
00210
00211 if (value)
00212 {
00213 switch (value->type)
00214 {
00215 case GCONF_VALUE_STRING:
00216 g_key_file_set_string(key_file, INI_GROUP_REGISTRY, key, gconf_value_get_string(value));
00217 break;
00218
00219 case GCONF_VALUE_INT:
00220 g_key_file_set_integer(key_file, INI_GROUP_REGISTRY, key, gconf_value_get_int(value));
00221 break;
00222
00223 case GCONF_VALUE_FLOAT:
00224 g_key_file_set_double(key_file, INI_GROUP_REGISTRY, key, gconf_value_get_float(value));
00225 break;
00226
00227 case GCONF_VALUE_BOOL:
00228 g_key_file_set_boolean(key_file, INI_GROUP_REGISTRY, key, gconf_value_get_bool(value));
00229 break;
00230
00231 case GCONF_VALUE_LIST:
00232 {
00233 GSList *valuelist = gconf_value_get_list(value);
00234 gsize len = g_slist_length(valuelist);
00235
00236 switch (gconf_value_get_list_type(value))
00237 {
00238 case GCONF_VALUE_STRING:
00239 {
00240
00241
00242 gchar **list = g_malloc0((len+1)*sizeof(gchar *));
00243 gchar **ptr=list;
00244 while (valuelist!=NULL)
00245 {
00246 const char *str = gconf_value_get_string(valuelist->data);
00247 if (str)
00248 {
00249 *ptr = g_strdup(str);
00250 ptr = ptr + 1;
00251 }
00252 valuelist=valuelist->next;
00253 }
00254
00255
00256 g_key_file_set_string_list(key_file, INI_GROUP_REGISTRY, key, (const gchar * const *)list, len);
00257
00258
00259 g_strfreev(list);
00260 }
00261 break;
00262
00263 case GCONF_VALUE_INT:
00264 {
00265
00266
00267 gint *list = g_malloc0((len+1)*sizeof(gint));
00268 gint *ptr=list;
00269 while (valuelist!=NULL)
00270 {
00271 gint val = gconf_value_get_int(valuelist->data);
00272 if (val)
00273 {
00274 *ptr++ = val;
00275 }
00276 valuelist=valuelist->next;
00277 }
00278
00279
00280 g_key_file_set_integer_list(key_file, INI_GROUP_REGISTRY, key, list, len);
00281
00282
00283 g_free(list);
00284 }
00285 break;
00286
00287 case GCONF_VALUE_FLOAT:
00288 {
00289
00290
00291 double *list = g_malloc0((len+1)*sizeof(double));
00292 double *ptr=list;
00293 while (valuelist!=NULL)
00294 {
00295 double val = gconf_value_get_float(valuelist->data);
00296 if (val)
00297 {
00298 *ptr++ = val;
00299 }
00300 valuelist=valuelist->next;
00301 }
00302
00303
00304 g_key_file_set_double_list(key_file, INI_GROUP_REGISTRY, key, list, len);
00305
00306
00307 g_free(list);
00308 }
00309 break;
00310
00311 case GCONF_VALUE_BOOL:
00312 {
00313
00314
00315 gboolean *list = g_malloc0((len+1)*sizeof(gboolean));
00316 gboolean *ptr=list;
00317 while (valuelist!=NULL)
00318 {
00319 gboolean val = gconf_value_get_bool(valuelist->data);
00320 if (val)
00321 {
00322 *ptr++ = val;
00323 }
00324 valuelist=valuelist->next;
00325 }
00326
00327
00328 g_key_file_set_boolean_list(key_file, INI_GROUP_REGISTRY, key, list, len);
00329
00330
00331 g_free(list);
00332 }
00333 break;
00334
00335 default:
00336 g_print("Unsupported data type of list for key: %s\n", key);
00337 break;
00338 }
00339
00340 g_slist_free(valuelist);
00341 }
00342 break;
00343
00344 case GCONF_VALUE_INVALID:
00345 default:
00346
00347 g_print("Invalid or unsupported data type for key: %s\n", key);
00348 break;
00349 }
00350 }
00351 else
00352 {
00353
00354 g_print("Invalid value for key: %s\n", key);
00355 }
00356 }
00357
00358
00359 static void export_gconf_entries(GConfClient *client, GKeyFile *key_file, const char *path, gboolean force_defaults)
00360 {
00361 GSList *entries = gconf_client_all_entries(client, (char*) path, NULL);
00362 while (entries!=NULL)
00363 {
00364 export_gconf_entry(client, key_file, (GConfEntry*) entries->data, force_defaults);
00365 entries=entries->next;
00366 }
00367 }
00368
00369
00370 static void export_gconf(GConfClient *client, GKeyFile *key_file, const char *path, gboolean force_defaults)
00371 {
00372 GSList *tmp = gconf_client_all_dirs(client, path, NULL);
00373
00374 export_gconf_entries(client, key_file, path, force_defaults);
00375
00376
00377 while (tmp!=NULL)
00378 {
00379 export_gconf(client, key_file, (char*) tmp->data, force_defaults);
00380 tmp=tmp->next;
00381 }
00382 }
00383
00384
00385 #if 0 // disabled See PR3439
00386 static void export_pointercal(GKeyFile *key_file)
00387 {
00388 FILE *calfile = NULL;
00389 gint a_cur[7];
00390
00391 calfile = fopen(CAL_FILE, "r");
00392 if (calfile == NULL)
00393 {
00394 g_print("Error opening file: %s\n", CAL_FILE);
00395 return;
00396 }
00397 else
00398 {
00399 fscanf(calfile, "%d %d %d %d %d %d %d",
00400 a_cur + 0,
00401 a_cur + 1,
00402 a_cur + 2,
00403 a_cur + 3,
00404 a_cur + 4,
00405 a_cur + 5,
00406 a_cur + 6);
00407
00408 fclose(calfile);
00409 }
00410
00411 g_key_file_set_integer_list(key_file, INI_GROUP_XTSCAL, "pointercal", a_cur, 7);
00412
00413 return;
00414 }
00415 #endif
00416
00417
00418 static gchar *get_file_content(const gchar* file_path)
00419 {
00420 gchar* contents = NULL;
00421 gsize len = 0;
00422
00423 if (g_file_get_contents(file_path, &contents, &len, NULL) == FALSE)
00424 {
00425 return NULL;
00426 }
00427
00428
00429 while (len > 0 && (contents[len - 1] == '\n' || contents[len - 1] == '\0'))
00430 {
00431 contents[len - 1] = '\0';
00432 len--;
00433 }
00434 return contents;
00435 }
00436
00437
00438 static char *get_kernel_version()
00439 {
00440 struct utsname utsbuf;
00441 unsigned int build_no;
00442
00443 if (-1 == uname(&utsbuf))
00444 {
00445
00446 return NULL;
00447 }
00448
00449
00450 sscanf(utsbuf.version, "#%d", &build_no);
00451 return g_strdup_printf("%d", build_no);
00452 }
00453
00454
00455 static char *get_micro_bootloader_version()
00456 {
00457 char* serio = get_sub_dir("/sys/devices", "serio");
00458 char* bootloader_ver_path = NULL;
00459 char* content = NULL;
00460
00461 if (serio == NULL)
00462 {
00463 LOGPRINTF("Can't find the micro device name!");
00464 return NULL;
00465 }
00466
00467 bootloader_ver_path = g_strdup_printf("%s/boot_ver", serio);
00468 content = get_file_content(bootloader_ver_path);
00469
00470 g_free(bootloader_ver_path);
00471 g_free(serio);
00472 return content;
00473 }
00474
00475
00476 static char *get_micro_app_version()
00477 {
00478 char* serio = get_sub_dir("/sys/devices", "serio");
00479 char* app_ver_path = NULL;
00480 char* content = NULL;
00481
00482 if (serio == NULL)
00483 {
00484 LOGPRINTF("Can't find the micro device name!");
00485 return NULL;
00486 }
00487
00488 app_ver_path = g_strdup_printf("%s/micro_ver", serio);
00489 content = get_file_content(app_ver_path);
00490
00491 g_free(app_ver_path);
00492 g_free(serio);
00493 return content;
00494 }
00495
00496
00497 static char *get_sub_dir(const char* parent, const char* sub_dir)
00498 {
00499 GDir* dir = g_dir_open(parent, 0, NULL);
00500 const char* file = NULL;
00501 char full_path[256];
00502
00503 if (dir == NULL)
00504 {
00505 return NULL;
00506 }
00507
00508 while ((file = g_dir_read_name(dir)) != NULL)
00509 {
00510
00511 snprintf(full_path, sizeof(full_path), "%s/%s", parent, file);
00512
00513 if (g_file_test(full_path, G_FILE_TEST_IS_DIR) == TRUE &&
00514 g_str_has_prefix(file, sub_dir) == TRUE)
00515 {
00516
00517 return g_strdup_printf("%s/%s", parent, file);
00518 }
00519 }
00520
00521 g_dir_close(dir);
00522 return NULL;
00523 }
00524
00525
00526 static void export_device_info(GKeyFile *key_file)
00527 {
00528 gchar *data = NULL;
00529 gchar *cat = NULL;
00530 gchar *mod = NULL;
00531 gchar *reg = NULL;
00532
00533
00534 cat = get_file_content(PATH_SYSSET "fasm/category");
00535 mod = get_file_content(PATH_SYSSET "fasm/model");
00536 if (mod) g_strchomp(mod);
00537 reg = get_file_content(PATH_SYSSET "fasm/region");
00538 if (cat && mod && reg) data = g_strconcat(cat, mod, "-", reg, NULL);
00539 if (data) g_key_file_set_string(key_file, INI_GROUP_DEVICEINFO, "product_type", data);
00540
00541 data = get_file_content(PATH_SYSSET "fasm/serial");
00542 if (data) g_key_file_set_string(key_file, INI_GROUP_DEVICEINFO, "serial_number", data);
00543
00544 data = get_file_content("/etc/version");
00545 if (data) g_key_file_set_string(key_file, INI_GROUP_DEVICEINFO, "software_version", data);
00546
00547 data = get_kernel_version();
00548 if (data) g_key_file_set_string(key_file, INI_GROUP_DEVICEINFO, "kernel_version", data);
00549
00550 data = get_micro_bootloader_version();
00551 if (data) g_key_file_set_string(key_file, INI_GROUP_DEVICEINFO, "micro_bootloader", data);
00552
00553 data = get_micro_app_version();
00554 if (data) g_key_file_set_string(key_file, INI_GROUP_DEVICEINFO, "micro_application", data);
00555
00556 if (data) g_free(data);
00557 if (cat) g_free(cat);
00558 if (mod) g_free(mod);
00559 if (reg) g_free(reg);
00560 }