rt_names.c 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257
  1. /* vi: set sw=4 ts=4: */
  2. /*
  3. * This program is free software; you can redistribute it and/or
  4. * modify it under the terms of the GNU General Public License
  5. * as published by the Free Software Foundation; either version
  6. * 2 of the License, or (at your option) any later version.
  7. *
  8. * Authors: Alexey Kuznetsov, <kuznet@ms2.inr.ac.ru>
  9. */
  10. #include "libbb.h"
  11. #include "rt_names.h"
  12. #define CONFDIR CONFIG_FEATURE_IP_ROUTE_DIR
  13. typedef struct rtnl_tab_t {
  14. const char *cached_str;
  15. unsigned cached_result;
  16. /* upstream version switched to a hash table and removed
  17. * id < 256 limit. For now bbox bumps this array size from 256
  18. * to 1024. If you plan to change this to a hash table,
  19. * consider merging several hash tables we have (for example,
  20. * awk has resizable one!
  21. */
  22. #define RT_TABLE_MAX 1023
  23. const char *tab[RT_TABLE_MAX+1];
  24. } rtnl_tab_t;
  25. static void rtnl_tab_initialize(const char *file, const char **tab)
  26. {
  27. char *token[2];
  28. char fullname[sizeof(CONFDIR"/rt_dsfield") + 8];
  29. parser_t *parser;
  30. sprintf(fullname, CONFDIR"/rt_%s", file);
  31. parser = config_open2(fullname, fopen_for_read);
  32. while (config_read(parser, token, 2, 2, "# \t", PARSE_NORMAL)) {
  33. unsigned id = bb_strtou(token[0], NULL, 0);
  34. if (id > RT_TABLE_MAX) {
  35. bb_error_msg("database %s is corrupted at line %d",
  36. file, parser->lineno);
  37. break;
  38. }
  39. tab[id] = xstrdup(token[1]);
  40. }
  41. config_close(parser);
  42. }
  43. static int rtnl_a2n(rtnl_tab_t *tab, uint32_t *id, const char *arg, int base)
  44. {
  45. unsigned i;
  46. if (tab->cached_str && strcmp(tab->cached_str, arg) == 0) {
  47. *id = tab->cached_result;
  48. return 0;
  49. }
  50. for (i = 0; i <= RT_TABLE_MAX; i++) {
  51. if (tab->tab[i]
  52. && strcmp(tab->tab[i], arg) == 0
  53. ) {
  54. tab->cached_str = tab->tab[i];
  55. tab->cached_result = i;
  56. *id = i;
  57. return 0;
  58. }
  59. }
  60. i = bb_strtou(arg, NULL, base);
  61. if (i > RT_TABLE_MAX)
  62. return -1;
  63. *id = i;
  64. return 0;
  65. }
  66. static rtnl_tab_t *rtnl_rtprot_tab;
  67. static void rtnl_rtprot_initialize(void)
  68. {
  69. static const char *const init_tab[] = {
  70. "none",
  71. "redirect",
  72. "kernel",
  73. "boot",
  74. "static",
  75. NULL,
  76. NULL,
  77. NULL,
  78. "gated",
  79. "ra",
  80. "mrt",
  81. "zebra",
  82. "bird",
  83. };
  84. if (rtnl_rtprot_tab)
  85. return;
  86. rtnl_rtprot_tab = xzalloc(sizeof(*rtnl_rtprot_tab));
  87. memcpy(rtnl_rtprot_tab->tab, init_tab, sizeof(init_tab));
  88. rtnl_tab_initialize("protos", rtnl_rtprot_tab->tab);
  89. }
  90. #if 0 /* UNUSED */
  91. const char* FAST_FUNC rtnl_rtprot_n2a(int id)
  92. {
  93. if (id < 0 || id > RT_TABLE_MAX) {
  94. return itoa(id);
  95. }
  96. rtnl_rtprot_initialize();
  97. if (rtnl_rtprot_tab->tab[id])
  98. return rtnl_rtprot_tab->tab[id];
  99. return itoa(id);
  100. }
  101. #endif
  102. int FAST_FUNC rtnl_rtprot_a2n(uint32_t *id, char *arg)
  103. {
  104. rtnl_rtprot_initialize();
  105. return rtnl_a2n(rtnl_rtprot_tab, id, arg, 0);
  106. }
  107. static rtnl_tab_t *rtnl_rtscope_tab;
  108. static void rtnl_rtscope_initialize(void)
  109. {
  110. if (rtnl_rtscope_tab)
  111. return;
  112. rtnl_rtscope_tab = xzalloc(sizeof(*rtnl_rtscope_tab));
  113. rtnl_rtscope_tab->tab[0] = "global";
  114. rtnl_rtscope_tab->tab[255] = "nowhere";
  115. rtnl_rtscope_tab->tab[254] = "host";
  116. rtnl_rtscope_tab->tab[253] = "link";
  117. rtnl_rtscope_tab->tab[200] = "site";
  118. rtnl_tab_initialize("scopes", rtnl_rtscope_tab->tab);
  119. }
  120. const char* FAST_FUNC rtnl_rtscope_n2a(int id)
  121. {
  122. if (id < 0 || id > RT_TABLE_MAX) {
  123. return itoa(id);
  124. }
  125. rtnl_rtscope_initialize();
  126. if (rtnl_rtscope_tab->tab[id])
  127. return rtnl_rtscope_tab->tab[id];
  128. return itoa(id);
  129. }
  130. int FAST_FUNC rtnl_rtscope_a2n(uint32_t *id, char *arg)
  131. {
  132. rtnl_rtscope_initialize();
  133. return rtnl_a2n(rtnl_rtscope_tab, id, arg, 0);
  134. }
  135. static rtnl_tab_t *rtnl_rtrealm_tab;
  136. static void rtnl_rtrealm_initialize(void)
  137. {
  138. if (rtnl_rtrealm_tab) return;
  139. rtnl_rtrealm_tab = xzalloc(sizeof(*rtnl_rtrealm_tab));
  140. rtnl_rtrealm_tab->tab[0] = "unknown";
  141. rtnl_tab_initialize("realms", rtnl_rtrealm_tab->tab);
  142. }
  143. int FAST_FUNC rtnl_rtrealm_a2n(uint32_t *id, char *arg)
  144. {
  145. rtnl_rtrealm_initialize();
  146. return rtnl_a2n(rtnl_rtrealm_tab, id, arg, 0);
  147. }
  148. #if ENABLE_FEATURE_IP_RULE
  149. const char* FAST_FUNC rtnl_rtrealm_n2a(int id)
  150. {
  151. if (id < 0 || id > RT_TABLE_MAX) {
  152. return itoa(id);
  153. }
  154. rtnl_rtrealm_initialize();
  155. if (rtnl_rtrealm_tab->tab[id])
  156. return rtnl_rtrealm_tab->tab[id];
  157. return itoa(id);
  158. }
  159. #endif
  160. static rtnl_tab_t *rtnl_rtdsfield_tab;
  161. static void rtnl_rtdsfield_initialize(void)
  162. {
  163. if (rtnl_rtdsfield_tab) return;
  164. rtnl_rtdsfield_tab = xzalloc(sizeof(*rtnl_rtdsfield_tab));
  165. rtnl_rtdsfield_tab->tab[0] = "0";
  166. rtnl_tab_initialize("dsfield", rtnl_rtdsfield_tab->tab);
  167. }
  168. const char* FAST_FUNC rtnl_dsfield_n2a(int id)
  169. {
  170. if (id < 0 || id > RT_TABLE_MAX) {
  171. return itoa(id);
  172. }
  173. rtnl_rtdsfield_initialize();
  174. if (rtnl_rtdsfield_tab->tab[id])
  175. return rtnl_rtdsfield_tab->tab[id];
  176. return itoa(id);
  177. }
  178. int FAST_FUNC rtnl_dsfield_a2n(uint32_t *id, char *arg)
  179. {
  180. rtnl_rtdsfield_initialize();
  181. return rtnl_a2n(rtnl_rtdsfield_tab, id, arg, 16);
  182. }
  183. #if ENABLE_FEATURE_IP_RULE
  184. static rtnl_tab_t *rtnl_rttable_tab;
  185. static void rtnl_rttable_initialize(void)
  186. {
  187. if (rtnl_rttable_tab)
  188. return;
  189. rtnl_rttable_tab = xzalloc(sizeof(*rtnl_rttable_tab));
  190. rtnl_rttable_tab->tab[0] = "unspec";
  191. rtnl_rttable_tab->tab[255] = "local";
  192. rtnl_rttable_tab->tab[254] = "main";
  193. rtnl_rttable_tab->tab[253] = "default";
  194. rtnl_tab_initialize("tables", rtnl_rttable_tab->tab);
  195. }
  196. const char* FAST_FUNC rtnl_rttable_n2a(int id)
  197. {
  198. if (id < 0 || id > RT_TABLE_MAX) {
  199. return itoa(id);
  200. }
  201. rtnl_rttable_initialize();
  202. if (rtnl_rttable_tab->tab[id])
  203. return rtnl_rttable_tab->tab[id];
  204. return itoa(id);
  205. }
  206. int FAST_FUNC rtnl_rttable_a2n(uint32_t *id, char *arg)
  207. {
  208. rtnl_rttable_initialize();
  209. return rtnl_a2n(rtnl_rttable_tab, id, arg, 0);
  210. }
  211. #endif