]> git.proxmox.com Git - libgit2.git/blame - src/config_mem.c
New upstream version 1.1.0+dfsg.1
[libgit2.git] / src / config_mem.c
CommitLineData
ac3d33df
JK
1/*
2 * Copyright (C) the libgit2 contributors. All rights reserved.
3 *
4 * This file is part of libgit2, distributed under the GNU GPL v2 with
5 * a Linking Exception. For full terms see the included COPYING file.
6 */
7
8#include "config.h"
9
10#include "config_backend.h"
11#include "config_parse.h"
12#include "config_entries.h"
13
14typedef struct {
15 git_config_backend parent;
16 git_config_entries *entries;
17 git_buf cfg;
18} config_memory_backend;
19
20typedef struct {
21 git_config_entries *entries;
22 git_config_level_t level;
23} config_memory_parse_data;
24
25static int config_error_readonly(void)
26{
27 git_error_set(GIT_ERROR_CONFIG, "this backend is read-only");
28 return -1;
29}
30
31static int read_variable_cb(
32 git_config_parser *reader,
33 const char *current_section,
34 const char *var_name,
35 const char *var_value,
36 const char *line,
37 size_t line_len,
38 void *payload)
39{
40 config_memory_parse_data *parse_data = (config_memory_parse_data *) payload;
41 git_buf buf = GIT_BUF_INIT;
42 git_config_entry *entry;
43 const char *c;
44 int result;
45
46 GIT_UNUSED(reader);
47 GIT_UNUSED(line);
48 GIT_UNUSED(line_len);
49
50 if (current_section) {
51 /* TODO: Once warnings land, we should likely warn
52 * here. Git appears to warn in most cases if it sees
53 * un-namespaced config options.
54 */
55 git_buf_puts(&buf, current_section);
56 git_buf_putc(&buf, '.');
57 }
58
59 for (c = var_name; *c; c++)
60 git_buf_putc(&buf, git__tolower(*c));
61
62 if (git_buf_oom(&buf))
63 return -1;
64
65 entry = git__calloc(1, sizeof(git_config_entry));
66 GIT_ERROR_CHECK_ALLOC(entry);
67 entry->name = git_buf_detach(&buf);
68 entry->value = var_value ? git__strdup(var_value) : NULL;
69 entry->level = parse_data->level;
70 entry->include_depth = 0;
71
72 if ((result = git_config_entries_append(parse_data->entries, entry)) < 0)
73 return result;
74
75 return result;
76}
77
78static int config_memory_open(git_config_backend *backend, git_config_level_t level, const git_repository *repo)
79{
80 config_memory_backend *memory_backend = (config_memory_backend *) backend;
22a2d3d5 81 git_config_parser parser = GIT_PARSE_CTX_INIT;
ac3d33df 82 config_memory_parse_data parse_data;
22a2d3d5 83 int error;
ac3d33df
JK
84
85 GIT_UNUSED(repo);
86
22a2d3d5
UG
87 if ((error = git_config_parser_init(&parser, "in-memory", memory_backend->cfg.ptr,
88 memory_backend->cfg.size)) < 0)
89 goto out;
ac3d33df
JK
90 parse_data.entries = memory_backend->entries;
91 parse_data.level = level;
92
22a2d3d5
UG
93 if ((error = git_config_parse(&parser, NULL, read_variable_cb, NULL, NULL, &parse_data)) < 0)
94 goto out;
95
96out:
97 git_config_parser_dispose(&parser);
98 return error;
ac3d33df
JK
99}
100
101static int config_memory_get(git_config_backend *backend, const char *key, git_config_entry **out)
102{
103 config_memory_backend *memory_backend = (config_memory_backend *) backend;
104 return git_config_entries_get(out, memory_backend->entries, key);
105}
106
107static int config_memory_iterator(
108 git_config_iterator **iter,
109 git_config_backend *backend)
110{
111 config_memory_backend *memory_backend = (config_memory_backend *) backend;
112 git_config_entries *entries;
113 int error;
114
115 if ((error = git_config_entries_dup(&entries, memory_backend->entries)) < 0)
116 goto out;
117
118 if ((error = git_config_entries_iterator_new(iter, entries)) < 0)
119 goto out;
120
121out:
122 /* Let iterator delete duplicated entries when it's done */
123 git_config_entries_free(entries);
124 return error;
125}
126
127static int config_memory_set(git_config_backend *backend, const char *name, const char *value)
128{
129 GIT_UNUSED(backend);
130 GIT_UNUSED(name);
131 GIT_UNUSED(value);
132 return config_error_readonly();
133}
134
135static int config_memory_set_multivar(
136 git_config_backend *backend, const char *name, const char *regexp, const char *value)
137{
138 GIT_UNUSED(backend);
139 GIT_UNUSED(name);
140 GIT_UNUSED(regexp);
141 GIT_UNUSED(value);
142 return config_error_readonly();
143}
144
145static int config_memory_delete(git_config_backend *backend, const char *name)
146{
147 GIT_UNUSED(backend);
148 GIT_UNUSED(name);
149 return config_error_readonly();
150}
151
152static int config_memory_delete_multivar(git_config_backend *backend, const char *name, const char *regexp)
153{
154 GIT_UNUSED(backend);
155 GIT_UNUSED(name);
156 GIT_UNUSED(regexp);
157 return config_error_readonly();
158}
159
160static int config_memory_lock(git_config_backend *backend)
161{
162 GIT_UNUSED(backend);
163 return config_error_readonly();
164}
165
166static int config_memory_unlock(git_config_backend *backend, int success)
167{
168 GIT_UNUSED(backend);
169 GIT_UNUSED(success);
170 return config_error_readonly();
171}
172
ac3d33df
JK
173static void config_memory_free(git_config_backend *_backend)
174{
175 config_memory_backend *backend = (config_memory_backend *)_backend;
176
177 if (backend == NULL)
178 return;
179
180 git_config_entries_free(backend->entries);
181 git_buf_dispose(&backend->cfg);
182 git__free(backend);
183}
184
185int git_config_backend_from_string(git_config_backend **out, const char *cfg, size_t len)
186{
187 config_memory_backend *backend;
188
189 backend = git__calloc(1, sizeof(config_memory_backend));
190 GIT_ERROR_CHECK_ALLOC(backend);
191
192 if (git_config_entries_new(&backend->entries) < 0) {
193 git__free(backend);
194 return -1;
195 }
196
197 if (git_buf_set(&backend->cfg, cfg, len) < 0) {
198 git_config_entries_free(backend->entries);
199 git__free(backend);
200 return -1;
201 }
202
203 backend->parent.version = GIT_CONFIG_BACKEND_VERSION;
204 backend->parent.readonly = 1;
205 backend->parent.open = config_memory_open;
206 backend->parent.get = config_memory_get;
207 backend->parent.set = config_memory_set;
208 backend->parent.set_multivar = config_memory_set_multivar;
209 backend->parent.del = config_memory_delete;
210 backend->parent.del_multivar = config_memory_delete_multivar;
211 backend->parent.iterator = config_memory_iterator;
212 backend->parent.lock = config_memory_lock;
213 backend->parent.unlock = config_memory_unlock;
22a2d3d5 214 backend->parent.snapshot = git_config_backend_snapshot;
ac3d33df
JK
215 backend->parent.free = config_memory_free;
216
217 *out = (git_config_backend *)backend;
218
219 return 0;
220}