Fix: sessiond: ODR violation results in memory corruption
[lttng-tools.git] / src / common / ini-config / ini-config.cpp
CommitLineData
3299fd31
SM
1/*
2 * Copyright (C) 2013 Jérémie Galarneau <jeremie.galarneau@efficios.com>
3 *
4 * SPDX-License-Identifier: GPL-2.0-only
5 *
6 */
7
c9e313bc 8#include "ini-config.hpp"
3299fd31 9
c9e313bc
SM
10#include <common/defaults.hpp>
11#include <common/error.hpp>
12#include <common/ini-config/ini.hpp>
13#include <common/macros.hpp>
14#include <common/utils.hpp>
3299fd31
SM
15#include <ctype.h>
16
17LTTNG_EXPORT const char *config_str_yes = "yes";
18LTTNG_EXPORT const char *config_str_true = "true";
19LTTNG_EXPORT const char *config_str_on = "on";
20LTTNG_EXPORT const char *config_str_no = "no";
21LTTNG_EXPORT const char *config_str_false = "false";
22LTTNG_EXPORT const char *config_str_off = "off";
23
f1494934 24namespace {
3299fd31
SM
25struct handler_filter_args {
26 const char* section;
27 config_entry_handler_cb handler;
28 void *user_data;
29};
f1494934 30} /* namespace */
3299fd31
SM
31
32static int config_entry_handler_filter(struct handler_filter_args *args,
33 const char *section, const char *name, const char *value)
34{
35 int ret = 0;
36 struct config_entry entry = { section, name, value };
37
38 LTTNG_ASSERT(args);
39
40 if (!section || !name || !value) {
41 ret = -EIO;
42 goto end;
43 }
44
45 if (args->section) {
46 if (strcmp(args->section, section)) {
47 goto end;
48 }
49 }
50
51 ret = args->handler(&entry, args->user_data);
52end:
53 return ret;
54}
55
56int config_get_section_entries(const char *override_path, const char *section,
57 config_entry_handler_cb handler, void *user_data)
58{
59 int ret = 0;
60 const char *path;
61 FILE *config_file = NULL;
62 struct handler_filter_args filter = { section, handler, user_data };
63
64 /* First, try system-wide conf. file. */
65 path = DEFAULT_DAEMON_SYSTEM_CONFIGPATH;
66
67 config_file = fopen(path, "r");
68 if (config_file) {
69 DBG("Loading daemon conf file at %s", path);
70 /*
71 * Return value is not very important here since error or not, we
72 * continue and try the next possible conf. file.
73 */
74 (void) ini_parse_file(config_file,
75 (ini_entry_handler) config_entry_handler_filter,
76 (void *) &filter);
77 fclose(config_file);
78 }
79
80 /* Second is the user local configuration. */
81 path = utils_get_home_dir();
82 if (path) {
83 char fullpath[PATH_MAX];
84
85 ret = snprintf(fullpath, sizeof(fullpath),
86 DEFAULT_DAEMON_HOME_CONFIGPATH, path);
87 if (ret < 0) {
88 PERROR("snprintf user conf. path");
89 goto error;
90 }
91
92 config_file = fopen(fullpath, "r");
93 if (config_file) {
94 DBG("Loading daemon user conf file at %s", path);
95 /*
96 * Return value is not very important here since error or not, we
97 * continue and try the next possible conf. file.
98 */
99 (void) ini_parse_file(config_file,
100 (ini_entry_handler) config_entry_handler_filter,
101 (void *) &filter);
102 fclose(config_file);
103 }
104 }
105
106 /* Final path is the one that the user might have provided. */
107 if (override_path) {
108 config_file = fopen(override_path, "r");
109 if (config_file) {
110 DBG("Loading daemon command line conf file at %s", override_path);
111 (void) ini_parse_file(config_file,
112 (ini_entry_handler) config_entry_handler_filter,
113 (void *) &filter);
114 fclose(config_file);
115 } else {
116 ERR("Failed to open daemon configuration file at %s",
117 override_path);
118 ret = -ENOENT;
119 goto error;
120 }
121 }
122
123 /* Everything went well. */
124 ret = 0;
125
126error:
127 return ret;
128}
129
130int config_parse_value(const char *value)
131{
132 int i, ret = 0;
133 char *endptr, *lower_str;
134 size_t len;
135 unsigned long v;
136
137 len = strlen(value);
138 if (!len) {
139 ret = -1;
140 goto end;
141 }
142
143 v = strtoul(value, &endptr, 10);
144 if (endptr != value) {
145 ret = v;
146 goto end;
147 }
148
64803277 149 lower_str = zmalloc<char>(len + 1);
3299fd31
SM
150 if (!lower_str) {
151 PERROR("zmalloc");
152 ret = -errno;
153 goto end;
154 }
155
156 for (i = 0; i < len; i++) {
157 lower_str[i] = tolower(value[i]);
158 }
159
160 if (!strcmp(lower_str, config_str_yes) ||
161 !strcmp(lower_str, config_str_true) ||
162 !strcmp(lower_str, config_str_on)) {
163 ret = 1;
164 } else if (!strcmp(lower_str, config_str_no) ||
165 !strcmp(lower_str, config_str_false) ||
166 !strcmp(lower_str, config_str_off)) {
167 ret = 0;
168 } else {
169 ret = -1;
170 }
171
172 free(lower_str);
173end:
174 return ret;
175}
This page took 0.03702 seconds and 4 git commands to generate.