| /* Licensed to the Apache Software Foundation (ASF) under one or more |
| * contributor license agreements. See the NOTICE file distributed with |
| * this work for additional information regarding copyright ownership. |
| * The ASF licenses this file to You under the Apache License, Version 2.0 |
| * (the "License"); you may not use this file except in compliance with |
| * the License. You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */ |
| |
| #define C_LUCY_DEBUG |
| #define LUCY_USE_SHORT_NAMES |
| #define CHY_USE_SHORT_NAMES |
| |
| #include "Lucy/Util/Debug.h" |
| |
| int32_t Debug_num_allocated = 0; |
| int32_t Debug_num_freed = 0; |
| int32_t Debug_num_globals = 0; |
| |
| #if DEBUG_ENABLED |
| |
| #include <stdarg.h> |
| #include <ctype.h> |
| #include <string.h> |
| #include <stdlib.h> |
| |
| static char env_cache_buf[256]; |
| static char *env_cache = NULL; |
| static char *env_cache_limit = NULL; |
| static int env_cache_is_current = 0; |
| |
| // Cache the system call to getenv. |
| static void |
| S_cache_debug_env_var(char *override) { |
| const char *debug_env = override ? override : getenv("DEBUG"); |
| if (debug_env != NULL) { |
| size_t len = strlen(debug_env); |
| if (len > sizeof(env_cache_buf) - 1) { |
| len = sizeof(env_cache_buf) - 1; |
| } |
| strncpy(env_cache_buf, debug_env, len); |
| env_cache = env_cache_buf; |
| env_cache_limit = env_cache + len; |
| } |
| env_cache_is_current = 1; |
| } |
| |
| void |
| Debug_print_mess(const char *file, int line, const char *func, |
| const char *pat, ...) { |
| va_list args; |
| fprintf(stderr, "%s:%d %s(): ", file, line, func); |
| va_start(args, pat); |
| vfprintf(stderr, pat, args); |
| va_end(args); |
| fprintf(stderr, "\n"); |
| } |
| |
| int |
| Debug_debug_should_print(const char *path, const char *func) { |
| if (!env_cache_is_current) { |
| S_cache_debug_env_var(NULL); |
| } |
| |
| if (!env_cache) { |
| // Do not print if DEBUG environment var is not set. |
| return 0; |
| } |
| else { |
| const char *test, *next; |
| const char *file = strrchr(path, '/'); |
| const int filename_len = file ? strlen(file) : 0; |
| const int funcname_len = func ? strlen(func) : 0; |
| |
| // Use just file name if given path. |
| if (file) { file++; } |
| else { file = path; } |
| |
| // Split criteria on commas. Bail when we run out of critieria. |
| for (test = env_cache; test != NULL; test = next) { |
| const char *last_char; |
| |
| // Skip whitespace. |
| while (isspace(*test)) { test++; } |
| if (test >= env_cache_limit) { return 0; } |
| |
| // Find end of criteria or end of string. |
| next = strchr(test, ','); |
| last_char = next ? next - 1 : env_cache_limit - 1; |
| while (last_char > test && isspace(*last_char)) { last_char--; } |
| |
| if (*last_char == '*') { |
| const int len = last_char - test; |
| if (!strncmp(test, file, len)) { return 1; } |
| if (!strncmp(test, func, len)) { return 1; } |
| } |
| else { |
| if (!strncmp(test, file, filename_len)) { return 1; } |
| if (!strncmp(test, func, funcname_len)) { return 1; } |
| } |
| } |
| |
| // No matches against the DEBUG environment var, so don't print. |
| return 0; |
| } |
| } |
| |
| void |
| Debug_set_env_cache(char *override) { |
| S_cache_debug_env_var(override); |
| } |
| |
| #else // DEBUG |
| |
| void |
| Debug_set_env_cache(char *override) { |
| (void)override; |
| } |
| |
| #endif // DEBUG |
| |