X-Git-Url: http://mj.ucw.cz/gitweb/?a=blobdiff_plain;ds=sidebyside;f=submit%2Ftasks.c;h=ecb4cbfc34c925598ec0eebd19ff2bad39373052;hb=0964fde49f014747a8252c6e02a1373d3763b44a;hp=675f4d8a471f5d5f95b6954abd1e3addcabe3da0;hpb=6324cb417d421274a384cfae916b039cbe56d6e0;p=eval.git diff --git a/submit/tasks.c b/submit/tasks.c index 675f4d8..ecb4cbf 100644 --- a/submit/tasks.c +++ b/submit/tasks.c @@ -4,18 +4,19 @@ * (c) 2007 Martin Mares */ -#include "lib/lib.h" -#include "lib/conf.h" -#include "lib/fastbuf.h" -#include "lib/stkstring.h" -#include "lib/simple-lists.h" -#include "lib/mempool.h" +#include "ucw/lib.h" +#include "ucw/conf.h" +#include "ucw/fastbuf.h" +#include "ucw/stkstring.h" +#include "ucw/simple-lists.h" +#include "ucw/mempool.h" #include "sherlock/object.h" #include #include #include #include +#include #include "submitd.h" @@ -23,7 +24,7 @@ clist task_list; static clist extensions; static clist open_data_extensions; -static byte * +static char * tasks_conf_commit(void *p UNUSED) { // We do not do any journaling here as we do not switch config files on the fly @@ -33,7 +34,7 @@ tasks_conf_commit(void *p UNUSED) if (t->open_data) { for (uns i=1; i<=t->open_data; i++) - simp_append(cf_pool, &t->parts)->s = mp_printf(cf_pool, "%d", i); + simp_append(cf_pool, &t->parts)->s = mp_printf(cf_pool, "%02d", i); t->extensions = &open_data_extensions; } else @@ -50,6 +51,7 @@ static struct cf_section task_conf = { CF_ITEMS { CF_STRING("Name", PTR_TO(struct task, name)), CF_UNS("OpenData", PTR_TO(struct task, open_data)), + CF_UNS("MaxSize", PTR_TO(struct task, max_size)), CF_END } }; @@ -65,7 +67,7 @@ struct cf_section tasks_conf = { }; struct task * -task_find(byte *name) +task_find(char *name) { CLIST_FOR_EACH(struct task *, t, task_list) if (!strcasecmp(t->name, name)) @@ -74,7 +76,7 @@ task_find(byte *name) } int -part_exists_p(struct task *t, byte *name) +part_exists_p(struct task *t, char *name) { CLIST_FOR_EACH(simp_node *, p, t->parts) if (!strcmp(p->s, name)) @@ -83,7 +85,7 @@ part_exists_p(struct task *t, byte *name) } int -ext_exists_p(struct task *t, byte *ext) +ext_exists_p(struct task *t, char *ext) { CLIST_FOR_EACH(simp_node *, x, *t->extensions) if (!strcmp(x->s, ext)) @@ -92,9 +94,9 @@ ext_exists_p(struct task *t, byte *ext) } int -user_exists_p(byte *user) +user_exists_p(char *user) { - byte *fn = stk_printf("solutions/%s", user); + char *fn = stk_printf("solutions/%s", user); struct stat st; return !stat(fn, &st) && S_ISDIR(st.st_mode); } @@ -139,7 +141,7 @@ task_unlock_status(struct conn *c, uns write_back) obj_write(fb, c->task_status, BUCKET_TYPE_PLAIN); brewind(fb); bconfig(fb, BCONFIG_IS_TEMP_FILE, 0); - byte *name = stk_printf("solutions/%s/status", c->user); + char *name = stk_printf("solutions/%s/status", c->user); if (rename(fb->name, name) < 0) die("Unable to rename %s to %s: %m", fb->name, name); bclose(fb); @@ -162,7 +164,7 @@ task_status_find_task(struct conn *c, struct task *t, uns create) for (struct oattr *a = obj_find_attr(c->task_status, 'T' + OBJ_ATTR_SON); a; a=a->same) { struct odes *o = a->son; - byte *name = obj_find_aval(o, 'T'); + char *name = obj_find_aval(o, 'T'); ASSERT(name); if (!strcmp(name, t->name)) return o; @@ -175,12 +177,12 @@ task_status_find_task(struct conn *c, struct task *t, uns create) } struct odes * -task_status_find_part(struct odes *to, byte *part, uns create) +task_status_find_part(struct odes *to, char *part, uns create) { for (struct oattr *a = obj_find_attr(to, 'P' + OBJ_ATTR_SON); a; a=a->same) { struct odes *o = a->son; - byte *name = obj_find_aval(o, 'P'); + char *name = obj_find_aval(o, 'P'); ASSERT(name); if (!strcmp(name, part)) return o; @@ -192,10 +194,34 @@ task_status_find_part(struct odes *to, byte *part, uns create) return o; } -void task_submit_part(byte *user, byte *task, byte *part, byte *ext, uns version UNUSED, struct fastbuf *fb) +static void +task_record_history(char *user, char *task, char *part, char *ext, uns version, char *submitted_name) { - byte *dir = stk_printf("solutions/%s/%s", user, task); - byte *name = stk_printf("%s/%s.%s", dir, part, ext); + if (!history_format) + return; + + time_t now = time(NULL); + struct tm *tm = localtime(&now); + char prefix[256]; + if (strftime(prefix, sizeof(prefix), history_format, tm) <= 0) + { + msg(L_ERROR, "Error formatting history prefix: too long"); + return; + } + + char *name = stk_printf("%s%s:%s:%s:v%d.%s", prefix, user, task, (strcmp(task, part) ? part : (char*)""), version, ext); + struct fastbuf *orig = bopen(submitted_name, O_RDONLY, 4096); + struct fastbuf *hist = bopen(name, O_WRONLY | O_CREAT | O_EXCL, 4096); + bbcopy_slow(orig, hist, ~0U); + bclose(hist); + bclose(orig); +} + +void +task_submit_part(char *user, char *task, char *part, char *ext, uns version, struct fastbuf *fb) +{ + char *dir = stk_printf("solutions/%s/%s", user, task); + char *name = stk_printf("%s/%s.%s", dir, part, ext); struct stat st; if (stat(dir, &st) < 0 && errno == ENOENT && mkdir(dir, 0777) < 0) @@ -204,12 +230,15 @@ void task_submit_part(byte *user, byte *task, byte *part, byte *ext, uns version bconfig(fb, BCONFIG_IS_TEMP_FILE, 0); if (rename(fb->name, name) < 0) die("Cannot rename %s to %s: %m", fb->name, name); + + task_record_history(user, task, part, ext, version, name); } -void task_delete_part(byte *user, byte *task, byte *part, byte *ext, uns version UNUSED) +void +task_delete_part(char *user, char *task, char *part, char *ext, uns version UNUSED) { - byte *dir = stk_printf("solutions/%s/%s", user, task); - byte *name = stk_printf("%s/%s.%s", dir, part, ext); + char *dir = stk_printf("solutions/%s/%s", user, task); + char *name = stk_printf("%s/%s.%s", dir, part, ext); if (unlink(name) < 0) msg(L_ERROR, "Cannot delete %s: %m", name); }