category.c 6.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234
  1. /*
  2. * This file is part of the zlog Library.
  3. *
  4. * Copyright (C) 2011 by Hardy Simpson <HardySimpson1984@gmail.com>
  5. *
  6. * Licensed under the LGPL v2.1, see the file COPYING in base directory.
  7. */
  8. #include "fmacros.h"
  9. #include <string.h>
  10. #include <stdlib.h>
  11. #include <errno.h>
  12. #include "category.h"
  13. #include "rule.h"
  14. #include "zc_defs.h"
  15. void zlog_category_profile(zlog_category_t *a_category, int flag)
  16. {
  17. int i;
  18. zlog_rule_t *a_rule;
  19. zc_assert(a_category,);
  20. zc_profile(flag, "--category[%p][%s][%p]--",
  21. a_category,
  22. a_category->name,
  23. a_category->fit_rules);
  24. if (a_category->fit_rules) {
  25. zc_arraylist_foreach(a_category->fit_rules, i, a_rule) {
  26. zlog_rule_profile(a_rule, flag);
  27. }
  28. }
  29. return;
  30. }
  31. /*******************************************************************************/
  32. void zlog_category_del(zlog_category_t * a_category)
  33. {
  34. zc_assert(a_category,);
  35. if (a_category->fit_rules) zc_arraylist_del(a_category->fit_rules);
  36. zc_debug("zlog_category_del[%p]", a_category);
  37. free(a_category);
  38. return;
  39. }
  40. /* overlap one rule's level bitmap to cateogry,
  41. * so category can judge whether a log level will be output by itself
  42. * It is safe when configure is reloaded, when rule will be released an recreated
  43. */
  44. static void zlog_cateogry_overlap_bitmap(zlog_category_t * a_category, zlog_rule_t *a_rule)
  45. {
  46. int i;
  47. for(i = 0; i < sizeof(a_rule->level_bitmap); i++) {
  48. a_category->level_bitmap[i] |= a_rule->level_bitmap[i];
  49. }
  50. }
  51. static int zlog_category_obtain_rules(zlog_category_t * a_category, zc_arraylist_t * rules)
  52. {
  53. int i;
  54. int count = 0;
  55. int fit = 0;
  56. zlog_rule_t *a_rule;
  57. zlog_rule_t *wastebin_rule = NULL;
  58. /* before set, clean last fit rules first */
  59. if (a_category->fit_rules) zc_arraylist_del(a_category->fit_rules);
  60. memset(a_category->level_bitmap, 0x00, sizeof(a_category->level_bitmap));
  61. a_category->fit_rules = zc_arraylist_new(NULL);
  62. if (!(a_category->fit_rules)) {
  63. zc_error("zc_arraylist_new fail");
  64. return -1;
  65. }
  66. /* get match rules from all rules */
  67. zc_arraylist_foreach(rules, i, a_rule) {
  68. fit = zlog_rule_match_category(a_rule, a_category->name);
  69. if (fit) {
  70. if (zc_arraylist_add(a_category->fit_rules, a_rule)) {
  71. zc_error("zc_arrylist_add fail");
  72. goto err;
  73. }
  74. zlog_cateogry_overlap_bitmap(a_category, a_rule);
  75. count++;
  76. }
  77. if (zlog_rule_is_wastebin(a_rule)) {
  78. wastebin_rule = a_rule;
  79. }
  80. }
  81. if (count == 0) {
  82. if (wastebin_rule) {
  83. zc_debug("category[%s], no match rules, use wastebin_rule", a_category->name);
  84. if (zc_arraylist_add(a_category->fit_rules, wastebin_rule)) {
  85. zc_error("zc_arrylist_add fail");
  86. goto err;
  87. }
  88. zlog_cateogry_overlap_bitmap(a_category, wastebin_rule);
  89. count++;
  90. } else {
  91. zc_debug("category[%s], no match rules & no wastebin_rule", a_category->name);
  92. }
  93. }
  94. return 0;
  95. err:
  96. zc_arraylist_del(a_category->fit_rules);
  97. a_category->fit_rules = NULL;
  98. return -1;
  99. }
  100. zlog_category_t *zlog_category_new(const char *name, zc_arraylist_t * rules)
  101. {
  102. size_t len;
  103. zlog_category_t *a_category;
  104. zc_assert(name, NULL);
  105. zc_assert(rules, NULL);
  106. len = strlen(name);
  107. if (len > sizeof(a_category->name) - 1) {
  108. zc_error("name[%s] too long", name);
  109. return NULL;
  110. }
  111. a_category = calloc(1, sizeof(zlog_category_t));
  112. if (!a_category) {
  113. zc_error("calloc fail, errno[%d]", errno);
  114. return NULL;
  115. }
  116. strcpy(a_category->name, name);
  117. a_category->name_len = len;
  118. if (zlog_category_obtain_rules(a_category, rules)) {
  119. zc_error("zlog_category_fit_rules fail");
  120. goto err;
  121. }
  122. zlog_category_profile(a_category, ZC_DEBUG);
  123. return a_category;
  124. err:
  125. zlog_category_del(a_category);
  126. return NULL;
  127. }
  128. /*******************************************************************************/
  129. /* update success: fit_rules 1, fit_rules_backup 1 */
  130. /* update fail: fit_rules 0, fit_rules_backup 1 */
  131. int zlog_category_update_rules(zlog_category_t * a_category, zc_arraylist_t * new_rules)
  132. {
  133. zc_assert(a_category, -1);
  134. zc_assert(new_rules, -1);
  135. /* 1st, mv fit_rules fit_rules_backup */
  136. if (a_category->fit_rules_backup) zc_arraylist_del(a_category->fit_rules_backup);
  137. a_category->fit_rules_backup = a_category->fit_rules;
  138. a_category->fit_rules = NULL;
  139. memcpy(a_category->level_bitmap_backup, a_category->level_bitmap,
  140. sizeof(a_category->level_bitmap));
  141. /* 2nd, obtain new_rules to fit_rules */
  142. if (zlog_category_obtain_rules(a_category, new_rules)) {
  143. zc_error("zlog_category_obtain_rules fail");
  144. a_category->fit_rules = NULL;
  145. return -1;
  146. }
  147. /* keep the fit_rules_backup not change, return */
  148. return 0;
  149. }
  150. /* commit fail: fit_rules_backup != 0 */
  151. /* commit success: fit_rules 1, fit_rules_backup 0 */
  152. void zlog_category_commit_rules(zlog_category_t * a_category)
  153. {
  154. zc_assert(a_category,);
  155. if (!a_category->fit_rules_backup) {
  156. zc_warn("a_category->fit_rules_backup is NULL, never update before");
  157. return;
  158. }
  159. zc_arraylist_del(a_category->fit_rules_backup);
  160. a_category->fit_rules_backup = NULL;
  161. memset(a_category->level_bitmap_backup, 0x00,
  162. sizeof(a_category->level_bitmap_backup));
  163. return;
  164. }
  165. /* rollback fail: fit_rules_backup != 0 */
  166. /* rollback success: fit_rules 1, fit_rules_backup 0 */
  167. /* so whether update succes or not, make things back to old */
  168. void zlog_category_rollback_rules(zlog_category_t * a_category)
  169. {
  170. zc_assert(a_category,);
  171. if (!a_category->fit_rules_backup) {
  172. zc_warn("a_category->fit_rules_backup in NULL, never update before");
  173. return;
  174. }
  175. if (a_category->fit_rules) {
  176. /* update success, rm new and backup */
  177. zc_arraylist_del(a_category->fit_rules);
  178. a_category->fit_rules = a_category->fit_rules_backup;
  179. a_category->fit_rules_backup = NULL;
  180. } else {
  181. /* update fail, just backup */
  182. a_category->fit_rules = a_category->fit_rules_backup;
  183. a_category->fit_rules_backup = NULL;
  184. }
  185. memcpy(a_category->level_bitmap, a_category->level_bitmap_backup,
  186. sizeof(a_category->level_bitmap));
  187. memset(a_category->level_bitmap_backup, 0x00,
  188. sizeof(a_category->level_bitmap_backup));
  189. return; /* always success */
  190. }
  191. /*******************************************************************************/
  192. int zlog_category_output(zlog_category_t * a_category, zlog_thread_t * a_thread)
  193. {
  194. int i;
  195. int rc = 0;
  196. zlog_rule_t *a_rule;
  197. /* go through all match rules to output */
  198. zc_arraylist_foreach(a_category->fit_rules, i, a_rule) {
  199. rc = zlog_rule_output(a_rule, a_thread);
  200. }
  201. return rc;
  202. }