parse_api.c 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214
  1. /*
  2. * Copyright (c) 2010 Philippe Pepiot <phil@philpep.org>
  3. * Copyright (c) 2011 Martin Duquesnoy <xorg62@gmail.com>
  4. *
  5. * Permission to use, copy, modify, and distribute this software for any
  6. * purpose with or without fee is hereby granted, provided that the above
  7. * copyright notice and this permission notice appear in all copies.
  8. *
  9. * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
  10. * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
  11. * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
  12. * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
  13. * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
  14. * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
  15. * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
  16. */
  17. #ifndef _BSD_SOURCE
  18. #define _BSD_SOURCE
  19. #endif
  20. #include <string.h>
  21. #include <stdlib.h>
  22. #include <err.h>
  23. #include "wmfs.h"
  24. #include "parse.h"
  25. #include "util.h"
  26. extern TAILQ_HEAD(, conf_sec) config;
  27. static const struct opt_type opt_type_null = { 0, 0, false, NULL };
  28. static struct opt_type
  29. string_to_opt(char *s)
  30. {
  31. struct opt_type ret = opt_type_null;
  32. if(!s || !strlen(s))
  33. return ret;
  34. ret.num = strtol(s, (char**)NULL, 10);
  35. ret.fnum = strtod(s, NULL);
  36. ret.boolean = (!strcmp(s, "true")
  37. || !strcmp(s, "true")
  38. || !strcmp(s, "TRUE")
  39. || !strcmp(s, "1"));
  40. ret.str = s;
  41. return ret;
  42. }
  43. void
  44. print_unused(struct conf_sec *sec)
  45. {
  46. struct conf_sec *s;
  47. struct conf_opt *o;
  48. if(!sec)
  49. {
  50. TAILQ_FOREACH(s, &config, entry)
  51. print_unused(s);
  52. return;
  53. }
  54. SLIST_FOREACH(o, &sec->optlist, entry)
  55. if(!o->used)
  56. warnx("%s:%d, unused param %s", o->filename, o->line, o->name);
  57. TAILQ_FOREACH(s, &sec->sub, entry)
  58. if(!TAILQ_EMPTY(&s->sub))
  59. print_unused(s);
  60. }
  61. struct conf_sec **
  62. fetch_section(struct conf_sec *s, char *name)
  63. {
  64. struct conf_sec **ret;
  65. struct conf_sec *sec;
  66. size_t i = 0;
  67. if(!name)
  68. return NULL;
  69. if(!s)
  70. {
  71. ret = xcalloc(2, sizeof(struct conf_sec *));
  72. TAILQ_FOREACH(sec, &config, entry)
  73. if(!strcmp(sec->name, name))
  74. {
  75. ret[0] = sec;
  76. ret[1] = NULL;
  77. break;
  78. }
  79. }
  80. else
  81. {
  82. ret = xcalloc(s->nsub + 1, sizeof(struct conf_sec *));
  83. TAILQ_FOREACH(sec, &s->sub, entry)
  84. if(!strcmp(sec->name, name) && i < s->nsub)
  85. ret[i++] = sec;
  86. ret[i] = NULL;
  87. }
  88. return ret;
  89. }
  90. struct conf_sec *
  91. fetch_section_first(struct conf_sec *s, char *name)
  92. {
  93. struct conf_sec *sec, *ret = NULL;
  94. TAILQ_HEAD(cshead, conf_sec) *head =
  95. (s
  96. ? (struct cshead*)&s->sub
  97. : (struct cshead*)&config);
  98. if(!name)
  99. return NULL;
  100. TAILQ_FOREACH(sec, head, entry)
  101. if(sec->name && !strcmp(sec->name, name))
  102. {
  103. ret = sec;
  104. break;
  105. }
  106. return ret;
  107. }
  108. size_t
  109. fetch_section_count(struct conf_sec **s)
  110. {
  111. size_t ret = 0;
  112. while(s[ret])
  113. ++ret;
  114. return ret;
  115. }
  116. struct opt_type *
  117. fetch_opt(struct conf_sec *s, char *dfl, char *name)
  118. {
  119. struct conf_opt *o;
  120. struct opt_type *ret;
  121. size_t i = 0;
  122. if(!name)
  123. return NULL;
  124. ret = xcalloc(10, sizeof(struct opt_type));
  125. if(s)
  126. {
  127. SLIST_FOREACH(o, &s->optlist, entry)
  128. if(!strcmp(o->name, name))
  129. {
  130. while(o->val[i])
  131. {
  132. o->used = true;
  133. ret[i] = string_to_opt(o->val[i]);
  134. ++i;
  135. }
  136. ret[i] = opt_type_null;
  137. return ret;
  138. }
  139. }
  140. ret[0] = string_to_opt(dfl);
  141. ret[1] = opt_type_null;
  142. return ret;
  143. }
  144. struct opt_type
  145. fetch_opt_first(struct conf_sec *s, char *dfl, char *name)
  146. {
  147. struct conf_opt *o;
  148. if(!name)
  149. return opt_type_null;
  150. else if(s)
  151. {
  152. SLIST_FOREACH(o, &s->optlist, entry)
  153. if(!strcmp(o->name, name))
  154. {
  155. o->used = true;
  156. return string_to_opt(o->val[0]);
  157. }
  158. }
  159. return string_to_opt(dfl);
  160. }
  161. size_t
  162. fetch_opt_count(struct opt_type *o)
  163. {
  164. size_t ret = 0;
  165. while(o[ret].str)
  166. ++ret;
  167. return ret;
  168. }