Support for elements of config.xml
[src/app-framework-main.git] / wgt-locales.c
1
2 #define _GNU_SOURCE
3 #include <string.h>
4 #include <errno.h>
5 #include <unistd.h>
6 #include <ctype.h>
7
8 #include "wgt.h"
9
10 struct locarr {
11         int count;
12         char **arr;
13 };
14
15 static struct locarr locarr = { 0, NULL };
16
17 static int add(const char *locstr, int length)
18 {
19         int i;
20         char *item, **ptr;
21
22         item = strndup(locstr, length);
23         if (item != NULL) {
24                 for (i = 0 ; item[i] ; i++)
25                         item[i] = tolower(item[i]);
26                 for (i = 0 ; i < locarr.count ; i++)
27                         if (!strcmp(item, locarr.arr[i])) {
28                                 free(item);
29                                 return 0;
30                         }
31
32                 ptr = realloc(locarr.arr, (1 + locarr.count) * sizeof(locarr.arr[0]));
33                 if (ptr) {
34                         locarr.arr = ptr;
35                         locarr.arr[locarr.count++] = item;
36                         return 0;
37                 }
38                 free(item);
39         }
40         errno = ENOMEM;
41         return -1;
42 }
43
44 void locales_reset()
45 {
46         while (locarr.count)
47                 free(locarr.arr[--locarr.count]);
48 }
49
50 int locales_add(const char *locstr)
51 {
52         const char *stop, *next;
53         while (*locstr) {
54                 stop = strchrnul(locstr, ',');
55                 next = stop + !!*stop;
56                 while (locstr != stop) {
57                         if (add(locstr, stop - locstr))
58                                 return -1;
59                         do { stop--; } while(stop > locstr && *stop != '-');
60                 }
61                 locstr = next;
62         }
63         return 0;
64 }
65
66 int locales_score(const char *lang)
67 {
68         int i;
69
70         if (lang)
71                 for (i = 0 ; i < locarr.count ; i++)
72                         if (!strcasecmp(lang, locarr.arr[i]))
73                                 return i;
74
75         return INT_MAX;
76 }
77
78 char *locales_locate_file(const char *filename)
79 {
80         int i;
81         char path[PATH_MAX];
82         char * result;
83
84         for (i = 0 ; i < locarr.count ; i++) {
85                 if (snprintf(path, sizeof path, "locales/%s/%s", locarr.arr[i], filename) >= (int)(sizeof path)) {
86                         errno = EINVAL;
87                         return NULL;
88                 }
89                 if (!access(path, F_OK)) {
90                         result = strdup(path);
91                         if (!result)
92                                 errno = ENOMEM;
93                         return result;
94                 }
95         }
96         if (access(filename, F_OK)) {
97                 result = strdup(filename);
98                 if (!result)
99                         errno = ENOMEM;
100                 return result;
101         }
102         errno = ENOENT;
103         return NULL;
104 }
105