]>
Commit | Line | Data |
---|---|---|
d00d5464 ET |
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 | ||
eae0bfdc | 8 | #include "refdb.h" |
4dcd8780 | 9 | |
d00d5464 ET |
10 | #include "git2/object.h" |
11 | #include "git2/refs.h" | |
12 | #include "git2/refdb.h" | |
4dcd8780 RB |
13 | #include "git2/sys/refdb_backend.h" |
14 | ||
d00d5464 | 15 | #include "hash.h" |
d00d5464 | 16 | #include "refs.h" |
b976f3c2 | 17 | #include "reflog.h" |
eae0bfdc | 18 | #include "posix.h" |
d00d5464 | 19 | |
d00d5464 ET |
20 | int git_refdb_new(git_refdb **out, git_repository *repo) |
21 | { | |
22 | git_refdb *db; | |
23 | ||
24 | assert(out && repo); | |
25 | ||
26 | db = git__calloc(1, sizeof(*db)); | |
ac3d33df | 27 | GIT_ERROR_CHECK_ALLOC(db); |
d00d5464 ET |
28 | |
29 | db->repo = repo; | |
30 | ||
31 | *out = db; | |
32 | GIT_REFCOUNT_INC(db); | |
33 | return 0; | |
34 | } | |
35 | ||
36 | int git_refdb_open(git_refdb **out, git_repository *repo) | |
37 | { | |
38 | git_refdb *db; | |
39 | git_refdb_backend *dir; | |
40 | ||
41 | assert(out && repo); | |
42 | ||
43 | *out = NULL; | |
44 | ||
45 | if (git_refdb_new(&db, repo) < 0) | |
46 | return -1; | |
47 | ||
48 | /* Add the default (filesystem) backend */ | |
4e4eab52 | 49 | if (git_refdb_backend_fs(&dir, repo) < 0) { |
d00d5464 ET |
50 | git_refdb_free(db); |
51 | return -1; | |
52 | } | |
53 | ||
54 | db->repo = repo; | |
55 | db->backend = dir; | |
56 | ||
57 | *out = db; | |
58 | return 0; | |
59 | } | |
60 | ||
21ca0451 | 61 | static void refdb_free_backend(git_refdb *db) |
d00d5464 | 62 | { |
d3b29fb9 AS |
63 | if (db->backend) |
64 | db->backend->free(db->backend); | |
21ca0451 | 65 | } |
d00d5464 | 66 | |
21ca0451 RB |
67 | int git_refdb_set_backend(git_refdb *db, git_refdb_backend *backend) |
68 | { | |
69 | refdb_free_backend(db); | |
d00d5464 ET |
70 | db->backend = backend; |
71 | ||
72 | return 0; | |
73 | } | |
74 | ||
75 | int git_refdb_compress(git_refdb *db) | |
76 | { | |
77 | assert(db); | |
4dcd8780 | 78 | |
21ca0451 | 79 | if (db->backend->compress) |
d00d5464 | 80 | return db->backend->compress(db->backend); |
4dcd8780 | 81 | |
d00d5464 ET |
82 | return 0; |
83 | } | |
84 | ||
979f75d8 | 85 | void git_refdb__free(git_refdb *db) |
d00d5464 | 86 | { |
21ca0451 | 87 | refdb_free_backend(db); |
6de9b2ee | 88 | git__memzero(db, sizeof(*db)); |
d00d5464 ET |
89 | git__free(db); |
90 | } | |
91 | ||
7ebc249c ET |
92 | void git_refdb_free(git_refdb *db) |
93 | { | |
94 | if (db == NULL) | |
95 | return; | |
96 | ||
979f75d8 | 97 | GIT_REFCOUNT_DEC(db, git_refdb__free); |
7ebc249c ET |
98 | } |
99 | ||
d00d5464 ET |
100 | int git_refdb_exists(int *exists, git_refdb *refdb, const char *ref_name) |
101 | { | |
102 | assert(exists && refdb && refdb->backend); | |
103 | ||
104 | return refdb->backend->exists(exists, refdb->backend, ref_name); | |
105 | } | |
106 | ||
107 | int git_refdb_lookup(git_reference **out, git_refdb *db, const char *ref_name) | |
108 | { | |
4e4eab52 ET |
109 | git_reference *ref; |
110 | int error; | |
111 | ||
21ca0451 | 112 | assert(db && db->backend && out && ref_name); |
4e4eab52 | 113 | |
ec24e542 VM |
114 | error = db->backend->lookup(&ref, db->backend, ref_name); |
115 | if (error < 0) | |
116 | return error; | |
117 | ||
118 | GIT_REFCOUNT_INC(db); | |
119 | ref->db = db; | |
4e4eab52 | 120 | |
ec24e542 VM |
121 | *out = ref; |
122 | return 0; | |
d00d5464 ET |
123 | } |
124 | ||
ec24e542 | 125 | int git_refdb_iterator(git_reference_iterator **out, git_refdb *db, const char *glob) |
4def7035 | 126 | { |
ce5553d4 CMN |
127 | int error; |
128 | ||
51fc5e89 | 129 | if (!db->backend || !db->backend->iterator) { |
ac3d33df | 130 | git_error_set(GIT_ERROR_REFERENCE, "this backend doesn't support iterators"); |
51fc5e89 CMN |
131 | return -1; |
132 | } | |
133 | ||
ce5553d4 CMN |
134 | if ((error = db->backend->iterator(out, db->backend, glob)) < 0) |
135 | return error; | |
c58cac12 | 136 | |
ec24e542 VM |
137 | GIT_REFCOUNT_INC(db); |
138 | (*out)->db = db; | |
139 | ||
c58cac12 CMN |
140 | return 0; |
141 | } | |
142 | ||
ec24e542 | 143 | int git_refdb_iterator_next(git_reference **out, git_reference_iterator *iter) |
c58cac12 | 144 | { |
ec24e542 | 145 | int error; |
c58cac12 | 146 | |
ec24e542 VM |
147 | if ((error = iter->next(out, iter)) < 0) |
148 | return error; | |
c58cac12 | 149 | |
ec24e542 VM |
150 | GIT_REFCOUNT_INC(iter->db); |
151 | (*out)->db = iter->db; | |
4def7035 | 152 | |
4def7035 CMN |
153 | return 0; |
154 | } | |
155 | ||
ec24e542 | 156 | int git_refdb_iterator_next_name(const char **out, git_reference_iterator *iter) |
4def7035 | 157 | { |
ec24e542 | 158 | return iter->next_name(out, iter); |
4def7035 CMN |
159 | } |
160 | ||
161 | void git_refdb_iterator_free(git_reference_iterator *iter) | |
162 | { | |
979f75d8 | 163 | GIT_REFCOUNT_DEC(iter->db, git_refdb__free); |
ec24e542 | 164 | iter->free(iter); |
4def7035 CMN |
165 | } |
166 | ||
91123661 | 167 | int git_refdb_write(git_refdb *db, git_reference *ref, int force, const git_signature *who, const char *message, const git_oid *old_id, const char *old_target) |
d00d5464 ET |
168 | { |
169 | assert(db && db->backend); | |
4e6e2ff2 VM |
170 | |
171 | GIT_REFCOUNT_INC(db); | |
172 | ref->db = db; | |
173 | ||
91123661 | 174 | return db->backend->write(db->backend, ref, force, who, message, old_id, old_target); |
4e6e2ff2 VM |
175 | } |
176 | ||
177 | int git_refdb_rename( | |
178 | git_reference **out, | |
179 | git_refdb *db, | |
180 | const char *old_name, | |
181 | const char *new_name, | |
110df893 | 182 | int force, |
a57dd3b7 | 183 | const git_signature *who, |
110df893 | 184 | const char *message) |
4e6e2ff2 VM |
185 | { |
186 | int error; | |
187 | ||
188 | assert(db && db->backend); | |
a57dd3b7 | 189 | error = db->backend->rename(out, db->backend, old_name, new_name, force, who, message); |
4e6e2ff2 VM |
190 | if (error < 0) |
191 | return error; | |
192 | ||
193 | if (out) { | |
194 | GIT_REFCOUNT_INC(db); | |
195 | (*out)->db = db; | |
196 | } | |
197 | ||
198 | return 0; | |
d00d5464 ET |
199 | } |
200 | ||
7ee8c7e6 | 201 | int git_refdb_delete(struct git_refdb *db, const char *ref_name, const git_oid *old_id, const char *old_target) |
d00d5464 ET |
202 | { |
203 | assert(db && db->backend); | |
7ee8c7e6 | 204 | return db->backend->del(db->backend, ref_name, old_id, old_target); |
d00d5464 | 205 | } |
b976f3c2 CMN |
206 | |
207 | int git_refdb_reflog_read(git_reflog **out, git_refdb *db, const char *name) | |
208 | { | |
209 | int error; | |
210 | ||
211 | assert(db && db->backend); | |
212 | ||
213 | if ((error = db->backend->reflog_read(out, db->backend, name)) < 0) | |
214 | return error; | |
215 | ||
216 | GIT_REFCOUNT_INC(db); | |
217 | (*out)->db = db; | |
218 | ||
219 | return 0; | |
220 | } | |
8d5ec910 | 221 | |
f2105129 CMN |
222 | int git_refdb_has_log(git_refdb *db, const char *refname) |
223 | { | |
224 | assert(db && refname); | |
225 | ||
226 | return db->backend->has_log(db->backend, refname); | |
227 | } | |
228 | ||
8d5ec910 CMN |
229 | int git_refdb_ensure_log(git_refdb *db, const char *refname) |
230 | { | |
231 | assert(db && refname); | |
232 | ||
233 | return db->backend->ensure_log(db->backend, refname); | |
234 | } | |
b9f81997 | 235 | |
bc91347b | 236 | int git_refdb_init_backend(git_refdb_backend *backend, unsigned int version) |
b9f81997 | 237 | { |
bc91347b RB |
238 | GIT_INIT_STRUCTURE_FROM_TEMPLATE( |
239 | backend, version, git_refdb_backend, GIT_REFDB_BACKEND_INIT); | |
240 | return 0; | |
b9f81997 | 241 | } |
ab8d9242 CMN |
242 | |
243 | int git_refdb_lock(void **payload, git_refdb *db, const char *refname) | |
244 | { | |
245 | assert(payload && db && refname); | |
246 | ||
247 | if (!db->backend->lock) { | |
ac3d33df | 248 | git_error_set(GIT_ERROR_REFERENCE, "backend does not support locking"); |
ab8d9242 CMN |
249 | return -1; |
250 | } | |
251 | ||
252 | return db->backend->lock(payload, db->backend, refname); | |
253 | } | |
254 | ||
255 | int git_refdb_unlock(git_refdb *db, void *payload, int success, int update_reflog, const git_reference *ref, const git_signature *sig, const char *message) | |
256 | { | |
257 | assert(db); | |
258 | ||
259 | return db->backend->unlock(db->backend, payload, success, update_reflog, ref, sig, message); | |
260 | } |