1 /* archives.c:
2 *
3 ****************************************************************
4 * Copyright (C) 2003 Tom Lord
5 *
6 * See the file "COPYING" for further information about
7 * the copyright and warranty status of this work.
8 */
9
10
11 #include "hackerlab/os/errno.h"
12 #include "hackerlab/bugs/panic.h"
13 #include "hackerlab/char/char-class.h"
14 #include "hackerlab/char/str.h"
15 #include "hackerlab/mem/mem.h"
16 #include "hackerlab/fs/file-names.h"
17 #include "hackerlab/fs/cwd.h"
18 #include "hackerlab/vu/safe.h"
19 #include "tla/libfsutils/tmp-files.h"
20 #include "tla/libfsutils/read-line.h"
21 #include "tla/libfsutils/dir-listing.h"
22 #include "tla/libawk/relational.h"
23 #include "tla/libarch/my.h"
24 #include "tla/libarch/namespace.h"
25 #include "tla/libarch/archive-version.h"
26 #include "tla/libarch/archives.h"
27
28
29
30 t_uchar *
arch_archive_location_file(const t_uchar * archive_name)31 arch_archive_location_file (const t_uchar * archive_name)
32 {
33 t_uchar * location_dir = 0;
34 t_uchar * answer = 0;
35
36 if (! arch_valid_archive_name(archive_name))
37 {
38 int ign;
39
40 printfmt (&ign, 2, "Invalid archive name `%s'.", archive_name);
41 exit (2);
42 }
43
44 location_dir = arch_my_archive_locations_dir ();
45 answer = file_name_in_vicinity (0, location_dir, archive_name);
46
47 lim_free (0, location_dir);
48
49 return answer;
50 }
51
52
53 void
arch_set_archive_location(const t_uchar * archive_name,const t_uchar * location,int force_p,int quietly_fail)54 arch_set_archive_location (const t_uchar * archive_name,
55 const t_uchar * location,
56 int force_p,
57 int quietly_fail)
58 {
59 t_uchar * file = 0;
60 t_uchar * dir = 0;
61 t_uchar * tmp_name = 0;
62
63 file = arch_archive_location_file (archive_name);
64 dir = file_name_directory_file (0, file);
65 tmp_name = tmp_file_name (dir, ",,new-location");
66
67 if (!force_p && !safe_access (file, F_OK))
68 {
69 if (! quietly_fail)
70 {
71 safe_printfmt (2, "archive already registered: %s\n", archive_name);
72 if (quietly_fail == ARCH_REG_FAIL_NOFAIL)
73 {
74 return;
75 }
76 else
77 {
78 exit (2);
79 }
80 }
81 }
82 else
83 {
84 int ign;
85 int out_fd;
86
87 arch_ensure_my_arch_params ();
88 vu_mkdir (&ign, dir, 0700);
89
90 out_fd = safe_open (tmp_name, O_WRONLY | O_CREAT | O_EXCL, 0666);
91 safe_printfmt (out_fd, "%s\n", location);
92 safe_close (out_fd);
93
94 safe_rename (tmp_name, file);
95 }
96
97 lim_free (0, file);
98 lim_free (0, dir);
99 lim_free (0, tmp_name);
100 }
101
102
103 t_uchar *
arch_archive_location(const t_uchar * archive_name,int soft)104 arch_archive_location (const t_uchar * archive_name,
105 int soft)
106 {
107 t_uchar * file = 0;
108 t_uchar * first_line = 0;
109 t_uchar * start;
110 t_uchar * end;
111 t_uchar * answer = 0;
112
113 file = arch_archive_location_file (archive_name);
114
115 if (safe_access (file, F_OK))
116 {
117 if (soft)
118 return 0;
119
120 safe_printfmt (2, "archive not registered: %s\n", archive_name);
121 safe_printfmt (2, " (see register-archive)\n");
122 exit (2);
123 }
124
125 first_line = read_line_from_file (file);
126
127 for (start = first_line; char_is_blank (*start); ++start)
128 ;
129 for (end = start; *end && !char_is_space (*start); ++end)
130 ;
131
132 answer = str_save_n (0, start, end - start);
133
134 lim_free (0, file);
135 lim_free (0, first_line);
136
137 return answer;
138 }
139
140
141 void
arch_delete_archive_location(const t_uchar * archive_name,int force_p)142 arch_delete_archive_location (const t_uchar * archive_name,
143 int force_p)
144 {
145 t_uchar * file = 0;
146 int errn;
147
148 file = arch_archive_location_file (archive_name);
149
150 if (vu_unlink (&errn, file))
151 {
152 if (!(force_p && (errn == ENOENT)))
153 {
154 safe_printfmt (2, "archive not registered: %s\n", archive_name);
155 safe_printfmt (2, " (see register-archive)\n");
156 exit (2);
157 }
158 }
159
160 lim_free (0, file);
161 }
162
163
164 rel_table
arch_registered_archives(void)165 arch_registered_archives (void)
166 {
167 t_uchar * dir = 0;
168 rel_table files = rel_table_nil;
169 rel_table answer = rel_table_nil;
170 int x;
171
172 dir = arch_my_archive_locations_dir ();
173 files = maybe_directory_files (dir);
174
175 for (x = 0; x < rel_n_records (files); ++x)
176 {
177 const t_uchar * f;
178
179 f = rel_peek_str (files, x, 0);
180 if (str_cmp (".", f) && str_cmp ("..", f) && arch_valid_archive_name (f))
181 {
182 t_uchar * location = 0;
183
184 location = arch_archive_location (f, 0);
185 rel_add_records (&answer, rel_make_record_2_taking (rel_get_field (files, x, 0), rel_make_field_str (location)), rel_record_null);
186
187 lim_free (0, location);
188 }
189 }
190
191
192 lim_free (0, dir);
193 rel_free_table (files);
194
195 return answer;
196 }
197
198 t_uchar *
arch_mirrored_at_name(const t_uchar * archive)199 arch_mirrored_at_name (const t_uchar * archive)
200 {
201 t_uchar * mirror_name = 0;
202
203 mirror_name = str_alloc_cat (0, archive, "-MIRROR");
204
205 return mirror_name;
206 }
207
208 t_uchar *
arch_mirrored_from_name(const t_uchar * archive)209 arch_mirrored_from_name (const t_uchar * archive)
210 {
211 t_uchar * source_name = 0;
212
213 source_name = str_alloc_cat (0, archive, "-SOURCE");
214
215 return source_name;
216 }
217
218 t_uchar *
arch_mirrored_at(const t_uchar * archive)219 arch_mirrored_at (const t_uchar * archive)
220 {
221 t_uchar * mirror_name = 0;
222 t_uchar * mirror_loc = 0;
223
224 mirror_name = arch_mirrored_at_name (archive);
225 mirror_loc = arch_archive_location (mirror_name, 1);
226
227 if (!mirror_loc)
228 {
229 lim_free (0, mirror_name);
230 mirror_name = 0;
231 }
232
233 lim_free (0, mirror_loc);
234 return mirror_name;
235 }
236
237
238 t_uchar *
arch_mirrored_from(const t_uchar * archive)239 arch_mirrored_from (const t_uchar * archive)
240 {
241 t_uchar * source_name = 0;
242 t_uchar * source_loc = 0;
243
244 source_name = arch_mirrored_from_name (archive);
245 source_loc = arch_archive_location (source_name, 1);
246
247 if (!source_loc)
248 {
249 lim_free (0, source_name);
250 source_name = 0;
251 }
252
253 lim_free (0, source_loc);
254 return source_name;
255 }
256
257
258
259 t_uchar *
arch_fs_archive_archive_version_path(const t_uchar * archive_path)260 arch_fs_archive_archive_version_path (const t_uchar * archive_path)
261 {
262 return file_name_in_vicinity (0, archive_path, ".archive-version");
263 }
264
265
266 t_uchar *
arch_fs_archive_meta_info_path(const t_uchar * archive_path)267 arch_fs_archive_meta_info_path (const t_uchar * archive_path)
268 {
269 return file_name_in_vicinity (0, archive_path, "=meta-info");
270 }
271
272
273 t_uchar *
arch_fs_archive_meta_info_item_path(const t_uchar * archive_path,const t_uchar * meta_info_name)274 arch_fs_archive_meta_info_item_path (const t_uchar * archive_path,
275 const t_uchar * meta_info_name)
276 {
277 t_uchar * meta_info_dir = 0;
278 t_uchar * meta_info_path;
279
280 meta_info_dir = arch_fs_archive_meta_info_path (archive_path);
281 meta_info_path = file_name_in_vicinity (0, meta_info_dir, meta_info_name);
282
283 lim_free (0, meta_info_dir);
284
285 return meta_info_path;
286 }
287
288
289
290
291 /* tag: Tom Lord Sun May 18 19:17:40 2003 (archives.c)
292 */
293