author | Lars Hjemli <hjemli@gmail.com> | 2006-12-10 21:31:36 (UTC) |
---|---|---|
committer | Lars Hjemli <hjemli@gmail.com> | 2006-12-10 21:31:36 (UTC) |
commit | 25105d7ecaba474d4b7c364ebb586aac3dfc5abb (patch) (unidiff) | |
tree | 8beb08db1399b8efb8c7fbcd936044ae7fc232e6 /git.h | |
parent | 856c026e221d8ed82c5b75bc8da4bd65e89ea953 (diff) | |
download | cgit-25105d7ecaba474d4b7c364ebb586aac3dfc5abb.zip cgit-25105d7ecaba474d4b7c364ebb586aac3dfc5abb.tar.gz cgit-25105d7ecaba474d4b7c364ebb586aac3dfc5abb.tar.bz2 |
Add caching infrastructure
This enables internal caching of page output.
Page requests are split into four groups:
1) repo listing (front page)
2) repo summary
3) repo pages w/symbolic references in query string
4) repo pages w/constant sha1's in query string
Each group has a TTL specified in minutes. When a page is requested, a cached
filename is stat(2)'ed and st_mtime is compared to time(2). If TTL has expired
(or the file didn't exist), the cached file is regenerated.
When generating a cached file, locking is used to avoid parallell processing
of the request. If multiple processes tries to aquire the same lock, the ones
who fail to get the lock serves the (expired) cached file. If the cached file
don't exist, the process instead calls sched_yield(2) before restarting the
request processing.
Signed-off-by: Lars Hjemli <hjemli@gmail.com>
-rw-r--r-- | git.h | 60 |
1 files changed, 55 insertions, 5 deletions
@@ -20,32 +20,52 @@ | |||
20 | #include <stdio.h> | 20 | #include <stdio.h> |
21 | #include <sys/stat.h> | 21 | #include <sys/stat.h> |
22 | #include <fcntl.h> | 22 | #include <fcntl.h> |
23 | #include <stddef.h> | 23 | #include <stddef.h> |
24 | #include <stdlib.h> | 24 | #include <stdlib.h> |
25 | #include <stdarg.h> | 25 | #include <stdarg.h> |
26 | #include <string.h> | 26 | #include <string.h> |
27 | #include <errno.h> | 27 | #include <errno.h> |
28 | #include <limits.h> | 28 | #include <limits.h> |
29 | #include <sys/param.h> | 29 | #include <sys/param.h> |
30 | #include <netinet/in.h> | 30 | #include <netinet/in.h> |
31 | #include <sys/types.h> | 31 | #include <sys/types.h> |
32 | #include <dirent.h> | 32 | #include <dirent.h> |
33 | #include <time.h> | 33 | #include <time.h> |
34 | 34 | ||
35 | 35 | ||
36 | /* On most systems <limits.h> would have given us this, but | ||
37 | * not on some systems (e.g. GNU/Hurd). | ||
38 | */ | ||
39 | #ifndef PATH_MAX | ||
40 | #define PATH_MAX 4096 | ||
41 | #endif | ||
42 | |||
43 | #ifdef __GNUC__ | ||
44 | #define NORETURN __attribute__((__noreturn__)) | ||
45 | #else | ||
46 | #define NORETURN | ||
47 | #ifndef __attribute__ | ||
48 | #define __attribute__(x) | ||
49 | #endif | ||
50 | #endif | ||
51 | |||
52 | |||
53 | extern void die(const char *err, ...) NORETURN __attribute__((format (printf, 1, 2))); | ||
54 | |||
55 | |||
36 | static inline char* xstrdup(const char *str) | 56 | static inline char* xstrdup(const char *str) |
37 | { | 57 | { |
38 | char *ret = strdup(str); | 58 | char *ret = strdup(str); |
39 | if (!ret) | 59 | if (!ret) |
40 | die("Out of memory, strdup failed"); | 60 | die("Out of memory, strdup failed"); |
41 | return ret; | 61 | return ret; |
42 | } | 62 | } |
43 | 63 | ||
44 | static inline void *xmalloc(size_t size) | 64 | static inline void *xmalloc(size_t size) |
45 | { | 65 | { |
46 | void *ret = malloc(size); | 66 | void *ret = malloc(size); |
47 | if (!ret && !size) | 67 | if (!ret && !size) |
48 | ret = malloc(1); | 68 | ret = malloc(1); |
49 | if (!ret) | 69 | if (!ret) |
50 | die("Out of memory, malloc failed"); | 70 | die("Out of memory, malloc failed"); |
51 | #ifdef XMALLOC_POISON | 71 | #ifdef XMALLOC_POISON |
@@ -95,35 +115,39 @@ static inline ssize_t xwrite(int fd, const void *buf, size_t len) | |||
95 | return nr; | 115 | return nr; |
96 | } | 116 | } |
97 | } | 117 | } |
98 | 118 | ||
99 | 119 | ||
100 | 120 | ||
101 | 121 | ||
102 | /* | 122 | /* |
103 | * from git:cache.h | 123 | * from git:cache.h |
104 | */ | 124 | */ |
105 | 125 | ||
106 | 126 | ||
107 | /* Convert to/from hex/sha1 representation */ | 127 | /* Convert to/from hex/sha1 representation */ |
108 | #define MINIMUM_ABBREV 4 | 128 | #define MINIMUM_ABBREV 4 |
109 | #define DEFAULT_ABBREV 7 | 129 | #define DEFAULT_ABBREV 7 |
110 | 130 | ||
131 | extern int sha1_object_info(const unsigned char *, char *, unsigned long *); | ||
111 | 132 | ||
112 | extern void * read_sha1_file(const unsigned char *sha1, char *type, unsigned long *size); | 133 | extern void * read_sha1_file(const unsigned char *sha1, char *type, unsigned long *size); |
113 | 134 | ||
135 | extern int get_sha1(const char *str, unsigned char *sha1); | ||
136 | extern int get_sha1_hex(const char *hex, unsigned char *sha1); | ||
137 | extern char *sha1_to_hex(const unsigned char *sha1);/* static buffer result! */ | ||
114 | 138 | ||
115 | 139 | ||
116 | 140 | ||
117 | /* | 141 | /* |
118 | * from git:object.h | 142 | * from git:object.h |
119 | */ | 143 | */ |
120 | 144 | ||
121 | struct object_list { | 145 | struct object_list { |
122 | struct object *item; | 146 | struct object *item; |
123 | struct object_list *next; | 147 | struct object_list *next; |
124 | }; | 148 | }; |
125 | 149 | ||
126 | struct object_refs { | 150 | struct object_refs { |
127 | unsigned count; | 151 | unsigned count; |
128 | struct object *base; | 152 | struct object *base; |
129 | struct object *ref[FLEX_ARRAY]; /* more */ | 153 | struct object *ref[FLEX_ARRAY]; /* more */ |
@@ -170,53 +194,64 @@ struct tree { | |||
170 | 194 | ||
171 | struct commit_list { | 195 | struct commit_list { |
172 | struct commit *item; | 196 | struct commit *item; |
173 | struct commit_list *next; | 197 | struct commit_list *next; |
174 | }; | 198 | }; |
175 | 199 | ||
176 | struct commit { | 200 | struct commit { |
177 | struct object object; | 201 | struct object object; |
178 | void *util; | 202 | void *util; |
179 | unsigned long date; | 203 | unsigned long date; |
180 | struct commit_list *parents; | 204 | struct commit_list *parents; |
181 | struct tree *tree; | 205 | struct tree *tree; |
182 | char *buffer; | 206 | char *buffer; |
183 | }; | 207 | }; |
184 | 208 | ||
185 | 209 | ||
210 | struct commit *lookup_commit(const unsigned char *sha1); | ||
211 | struct commit *lookup_commit_reference(const unsigned char *sha1); | ||
212 | struct commit *lookup_commit_reference_gently(const unsigned char *sha1, | ||
213 | int quiet); | ||
214 | |||
215 | int parse_commit_buffer(struct commit *item, void *buffer, unsigned long size); | ||
216 | int parse_commit(struct commit *item); | ||
217 | |||
218 | struct commit_list * commit_list_insert(struct commit *item, struct commit_list **list_p); | ||
219 | struct commit_list * insert_by_date(struct commit *item, struct commit_list **list); | ||
220 | |||
221 | void free_commit_list(struct commit_list *list); | ||
222 | |||
223 | void sort_by_date(struct commit_list **list); | ||
224 | |||
186 | /* Commit formats */ | 225 | /* Commit formats */ |
187 | enum cmit_fmt { | 226 | enum cmit_fmt { |
188 | CMIT_FMT_RAW, | 227 | CMIT_FMT_RAW, |
189 | CMIT_FMT_MEDIUM, | 228 | CMIT_FMT_MEDIUM, |
190 | CMIT_FMT_DEFAULT = CMIT_FMT_MEDIUM, | 229 | CMIT_FMT_DEFAULT = CMIT_FMT_MEDIUM, |
191 | CMIT_FMT_SHORT, | 230 | CMIT_FMT_SHORT, |
192 | CMIT_FMT_FULL, | 231 | CMIT_FMT_FULL, |
193 | CMIT_FMT_FULLER, | 232 | CMIT_FMT_FULLER, |
194 | CMIT_FMT_ONELINE, | 233 | CMIT_FMT_ONELINE, |
195 | CMIT_FMT_EMAIL, | 234 | CMIT_FMT_EMAIL, |
196 | 235 | ||
197 | CMIT_FMT_UNSPECIFIED, | 236 | CMIT_FMT_UNSPECIFIED, |
198 | }; | 237 | }; |
199 | 238 | ||
239 | extern unsigned long pretty_print_commit(enum cmit_fmt fmt, const struct commit *, unsigned long len, char *buf, unsigned long space, int abbrev, const char *subject, const char *after_subject, int relative_date); | ||
200 | 240 | ||
201 | 241 | ||
202 | struct commit *lookup_commit(const unsigned char *sha1); | ||
203 | struct commit *lookup_commit_reference(const unsigned char *sha1); | ||
204 | struct commit *lookup_commit_reference_gently(const unsigned char *sha1, | ||
205 | int quiet); | ||
206 | |||
207 | typedef void (*topo_sort_set_fn_t)(struct commit*, void *data); | 242 | typedef void (*topo_sort_set_fn_t)(struct commit*, void *data); |
208 | typedef void* (*topo_sort_get_fn_t)(struct commit*); | 243 | typedef void* (*topo_sort_get_fn_t)(struct commit*); |
209 | 244 | ||
210 | 245 | ||
211 | 246 | ||
212 | 247 | ||
213 | /* | 248 | /* |
214 | * from git:diff.h | 249 | * from git:diff.h |
215 | */ | 250 | */ |
216 | 251 | ||
217 | 252 | ||
218 | struct rev_info; | 253 | struct rev_info; |
219 | struct diff_options; | 254 | struct diff_options; |
220 | struct diff_queue_struct; | 255 | struct diff_queue_struct; |
221 | 256 | ||
222 | typedef void (*change_fn_t)(struct diff_options *options, | 257 | typedef void (*change_fn_t)(struct diff_options *options, |
@@ -293,32 +328,42 @@ struct diff_options { | |||
293 | }; | 328 | }; |
294 | 329 | ||
295 | enum color_diff { | 330 | enum color_diff { |
296 | DIFF_RESET = 0, | 331 | DIFF_RESET = 0, |
297 | DIFF_PLAIN = 1, | 332 | DIFF_PLAIN = 1, |
298 | DIFF_METAINFO = 2, | 333 | DIFF_METAINFO = 2, |
299 | DIFF_FRAGINFO = 3, | 334 | DIFF_FRAGINFO = 3, |
300 | DIFF_FILE_OLD = 4, | 335 | DIFF_FILE_OLD = 4, |
301 | DIFF_FILE_NEW = 5, | 336 | DIFF_FILE_NEW = 5, |
302 | DIFF_COMMIT = 6, | 337 | DIFF_COMMIT = 6, |
303 | DIFF_WHITESPACE = 7, | 338 | DIFF_WHITESPACE = 7, |
304 | }; | 339 | }; |
305 | 340 | ||
306 | 341 | ||
307 | 342 | ||
308 | 343 | ||
344 | /* | ||
345 | * from git:refs.g | ||
346 | */ | ||
347 | |||
348 | typedef int each_ref_fn(const char *refname, const unsigned char *sha1, int flags, void *cb_data); | ||
349 | extern int head_ref(each_ref_fn, void *); | ||
350 | extern int for_each_ref(each_ref_fn, void *); | ||
351 | extern int for_each_tag_ref(each_ref_fn, void *); | ||
352 | extern int for_each_branch_ref(each_ref_fn, void *); | ||
353 | extern int for_each_remote_ref(each_ref_fn, void *); | ||
309 | 354 | ||
310 | 355 | ||
311 | 356 | ||
312 | /* | 357 | /* |
313 | * from git:revision.h | 358 | * from git:revision.h |
314 | */ | 359 | */ |
315 | 360 | ||
316 | struct rev_info; | 361 | struct rev_info; |
317 | struct log_info; | 362 | struct log_info; |
318 | 363 | ||
319 | typedef void (prune_fn_t)(struct rev_info *revs, struct commit *commit); | 364 | typedef void (prune_fn_t)(struct rev_info *revs, struct commit *commit); |
320 | 365 | ||
321 | struct rev_info { | 366 | struct rev_info { |
322 | /* Starting list */ | 367 | /* Starting list */ |
323 | struct commit_list *commits; | 368 | struct commit_list *commits; |
324 | struct object_array pending; | 369 | struct object_array pending; |
@@ -378,22 +423,27 @@ struct rev_info { | |||
378 | struct grep_opt*grep_filter; | 423 | struct grep_opt*grep_filter; |
379 | 424 | ||
380 | /* special limits */ | 425 | /* special limits */ |
381 | int max_count; | 426 | int max_count; |
382 | unsigned long max_age; | 427 | unsigned long max_age; |
383 | unsigned long min_age; | 428 | unsigned long min_age; |
384 | 429 | ||
385 | /* diff info for patches and for paths limiting */ | 430 | /* diff info for patches and for paths limiting */ |
386 | struct diff_options diffopt; | 431 | struct diff_options diffopt; |
387 | struct diff_options pruning; | 432 | struct diff_options pruning; |
388 | 433 | ||
389 | topo_sort_set_fn_t topo_setter; | 434 | topo_sort_set_fn_t topo_setter; |
390 | topo_sort_get_fn_t topo_getter; | 435 | topo_sort_get_fn_t topo_getter; |
391 | }; | 436 | }; |
392 | 437 | ||
393 | 438 | ||
439 | extern void init_revisions(struct rev_info *revs, const char *prefix); | ||
440 | extern int setup_revisions(int argc, const char **argv, struct rev_info *revs, const char *def); | ||
441 | extern int handle_revision_arg(const char *arg, struct rev_info *revs,int flags,int cant_be_filename); | ||
442 | |||
443 | extern void prepare_revision_walk(struct rev_info *revs); | ||
394 | extern struct commit *get_revision(struct rev_info *revs); | 444 | extern struct commit *get_revision(struct rev_info *revs); |
395 | 445 | ||
396 | 446 | ||
397 | 447 | ||
398 | 448 | ||
399 | #endif /* GIT_H */ | 449 | #endif /* GIT_H */ |