1 /*
2 INTEL CONFIDENTIAL
3 Copyright 2009 Intel Corporation All Rights Reserved.
4 The source code contained or described herein and all documents related to the source code ("Material") are owned by Intel Corporation or its suppliers or licensors. Title to the Material remains with Intel Corporation or its suppliers and licensors. The Material contains trade secrets and proprietary and confidential information of Intel or its suppliers and licensors. The Material is protected by worldwide copyright and trade secret laws and treaty provisions. No part of the Material may be used, copied, reproduced, modified, published, uploaded, posted, transmitted, distributed, or disclosed in any way without Intel’s prior express written permission.
5
6 No license under any patent, copyright, trade secret or other intellectual property right is granted to or conferred upon you by disclosure or delivery of the Materials, either expressly, by implication, inducement, estoppel or otherwise. Any license under such intellectual property rights must be express and approved by Intel in writing.
7 */
8
9 #include <glib.h>
10 #include <string.h>
11 #include "mixlog.h"
12
13 #define MIX_DELOG_COMPS "MIX_DELOG_COMPS"
14 #define MIX_DELOG_FILES "MIX_DELOG_FILES"
15 #define MIX_DELOG_FUNCS "MIX_DELOG_FUNCS"
16 #define MIX_LOG_ENABLE "MIX_LOG_ENABLE"
17 #define MIX_DELOG_DELIMITERS " ,;"
18
19 #define MIX_LOG_LEVEL "MIX_LOG_LEVEL"
20
21 static GStaticMutex g_mutex = G_STATIC_MUTEX_INIT;
22
23 #ifdef MIX_LOG_USE_HT
24 static GHashTable *g_defile_ht = NULL, *g_defunc_ht = NULL, *g_decom_ht = NULL;
25 static gint g_mix_log_level = MIX_LOG_LEVEL_VERBOSE;
26 static gint g_refcount = 0;
27
28 #define mix_log_destroy_ht(ht) if(ht) { g_hash_table_destroy(ht); ht = NULL; }
29
mix_log_get_ht(GHashTable ** ht,const gchar * var)30 void mix_log_get_ht(GHashTable **ht, const gchar *var) {
31
32 const char *delog_list = NULL;
33 char *item = NULL;
34 if (!ht || !var) {
35 return;
36 }
37
38 delog_list = g_getenv(var);
39 if (!delog_list) {
40 return;
41 }
42
43 if (*ht == NULL) {
44 *ht = g_hash_table_new(g_str_hash, g_str_equal);
45 if (*ht == NULL) {
46 return;
47 }
48 }
49
50 item = strtok((char *) delog_list, MIX_DELOG_DELIMITERS);
51 while (item != NULL) {
52 g_hash_table_insert(*ht, item, "true");
53 item = strtok(NULL, MIX_DELOG_DELIMITERS);
54 }
55 }
56
mix_log_initialize_func()57 void mix_log_initialize_func() {
58
59 const gchar *mix_log_level = NULL;
60 g_static_mutex_lock(&g_mutex);
61
62 if (g_refcount == 0) {
63
64 mix_log_level = g_getenv(MIX_LOG_LEVEL);
65 if (mix_log_level) {
66 g_mix_log_level = atoi(mix_log_level);
67 }
68
69 mix_log_get_ht(&g_decom_ht, MIX_DELOG_COMPS);
70 mix_log_get_ht(&g_defile_ht, MIX_DELOG_FILES);
71 mix_log_get_ht(&g_defunc_ht, MIX_DELOG_FUNCS);
72 }
73
74 g_refcount++;
75
76 g_static_mutex_unlock(&g_mutex);
77 }
78
mix_log_finalize_func()79 void mix_log_finalize_func() {
80
81 g_static_mutex_lock(&g_mutex);
82
83 g_refcount--;
84
85 if (g_refcount == 0) {
86 mix_log_destroy_ht(g_decom_ht);
87 mix_log_destroy_ht(g_defile_ht);
88 mix_log_destroy_ht(g_defunc_ht);
89
90 g_mix_log_level = MIX_LOG_LEVEL_VERBOSE;
91 }
92
93 if (g_refcount < 0) {
94 g_refcount = 0;
95 }
96
97 g_static_mutex_unlock(&g_mutex);
98 }
99
mix_log_func(const gchar * comp,gint level,const gchar * file,const gchar * func,gint line,const gchar * format,...)100 void mix_log_func(const gchar* comp, gint level, const gchar *file,
101 const gchar *func, gint line, const gchar *format, ...) {
102
103 va_list args;
104 static gchar* loglevel[4] = {"**ERROR", "*WARNING", "INFO", "VERBOSE"};
105
106 if (!format) {
107 return;
108 }
109
110 g_static_mutex_lock(&g_mutex);
111
112 if (level > g_mix_log_level) {
113 goto exit;
114 }
115
116 if (g_decom_ht) {
117 if (g_hash_table_lookup(g_decom_ht, comp)) {
118 goto exit;
119 }
120 }
121
122 if (g_defile_ht) {
123 if (g_hash_table_lookup(g_defile_ht, file)) {
124 goto exit;
125 }
126 }
127
128 if (g_defunc_ht) {
129 if (g_hash_table_lookup(g_defunc_ht, func)) {
130 goto exit;
131 }
132 }
133
134 if(level > MIX_LOG_LEVEL_VERBOSE) {
135 level = MIX_LOG_LEVEL_VERBOSE;
136 }
137 if(level < MIX_LOG_LEVEL_ERROR) {
138 level = MIX_LOG_LEVEL_ERROR;
139 }
140
141 g_print("%s : %s : %s : ", loglevel[level - 1], file, func);
142
143 va_start(args, format);
144 g_vprintf(format, args);
145 va_end(args);
146
147 exit: g_static_mutex_unlock(&g_mutex);
148 }
149
150 #else /* MIX_LOG_USE_HT */
151
mix_shall_delog(const gchar * name,const gchar * var)152 gboolean mix_shall_delog(const gchar *name, const gchar *var) {
153
154 const char *delog_list = NULL;
155 char *item = NULL;
156 gboolean delog = FALSE;
157
158 if (!name || !var) {
159 return delog;
160 }
161
162 delog_list = g_getenv(var);
163 if (!delog_list) {
164 return delog;
165 }
166
167 item = strtok((char *) delog_list, MIX_DELOG_DELIMITERS);
168 while (item != NULL) {
169 if (strcmp(item, name) == 0) {
170 delog = TRUE;
171 break;
172 }
173 item = strtok(NULL, MIX_DELOG_DELIMITERS);
174 }
175
176 return delog;
177 }
178
mix_log_enabled()179 gboolean mix_log_enabled() {
180
181 const char *value = NULL;
182 value = g_getenv(MIX_LOG_ENABLE);
183 if(!value) {
184 return FALSE;
185 }
186
187 if(value[0] == '0') {
188 return FALSE;
189 }
190 return TRUE;
191 }
192
mix_log_func(const gchar * comp,gint level,const gchar * file,const gchar * func,gint line,const gchar * format,...)193 void mix_log_func(const gchar* comp, gint level, const gchar *file,
194 const gchar *func, gint line, const gchar *format, ...) {
195
196 va_list args;
197 static gchar* loglevel[4] = { "**ERROR", "*WARNING", "INFO", "VERBOSE" };
198
199 const gchar *env_mix_log_level = NULL;
200 gint mix_log_level_threhold = MIX_LOG_LEVEL_VERBOSE;
201
202 if(!mix_log_enabled()) {
203 return;
204 }
205
206 if (!format) {
207 return;
208 }
209
210 g_static_mutex_lock(&g_mutex);
211
212 /* log level */
213 env_mix_log_level = g_getenv(MIX_LOG_LEVEL);
214 if (env_mix_log_level) {
215 mix_log_level_threhold = atoi(env_mix_log_level);
216 }
217
218 if (level > mix_log_level_threhold) {
219 goto exit;
220 }
221
222 /* component */
223 if (mix_shall_delog(comp, MIX_DELOG_COMPS)) {
224 goto exit;
225 }
226
227 /* files */
228 if (mix_shall_delog(file, MIX_DELOG_FILES)) {
229 goto exit;
230 }
231
232 /* functions */
233 if (mix_shall_delog(func, MIX_DELOG_FUNCS)) {
234 goto exit;
235 }
236
237 if (level > MIX_LOG_LEVEL_VERBOSE) {
238 level = MIX_LOG_LEVEL_VERBOSE;
239 }
240 if (level < MIX_LOG_LEVEL_ERROR) {
241 level = MIX_LOG_LEVEL_ERROR;
242 }
243
244 g_print("%s : %s : %s : ", loglevel[level - 1], file, func);
245
246 va_start(args, format);
247 g_vprintf(format, args);
248 va_end(args);
249
250 exit:
251 g_static_mutex_unlock(&g_mutex);
252 }
253
254
255 #endif /* MIX_LOG_USE_HT */
256
257
258