From 8e213f10fe4ac55c9c0f404113ed588a8c4f65a2 Mon Sep 17 00:00:00 2001 From: wbaumann Date: Sun, 7 Jun 2009 15:17:14 +0000 Subject: [PATCH] retry failed uploads with increasing delay --- ChangeLog | 5 +++++ src/cache.c | 25 ++++++++++++++++++++++--- src/cache.h | 1 + 3 files changed, 28 insertions(+), 3 deletions(-) diff --git a/ChangeLog b/ChangeLog index 7ce59ec..dee6e7a 100644 --- a/ChangeLog +++ b/ChangeLog @@ -5,6 +5,11 @@ ChangeLog for davfs2 * webdav.c, prop_result: If property not found try property without namespace. (idea by Dirk Arend ) + * cache.c, add_to_changed: + Fixed: wrong size in malloc. + * cache.c: + When upload fails temporarily: retry with + increasing delays. 2009-06-06 Werner Baumann (werner.baumann@onlinehome.de) * cache.c, dav_statfs: diff --git a/src/cache.c b/src/cache.c index 54e0b07..fa2dc0f 100644 --- a/src/cache.c +++ b/src/cache.c @@ -124,6 +124,8 @@ static const char* const type[] = { [END] = NULL }; +#define MAX_UPLOAD_ATTEMPTS 20 + /* Private global variables */ /*==========================*/ @@ -297,6 +299,20 @@ remove_from_tree(dav_node *node); static void remove_node(dav_node *node); +static inline int +set_next_upload_attempt(dav_node *node) +{ + dav_node_list_item *item = changed; + while (item && item->node != node) + item = item->next; + if (!item) return 0; + item->attempts++; + if (item->attempts > MAX_UPLOAD_ATTEMPTS) + return -1; + item->save_at += item->attempts * min_retry; + return 0; +} + static inline void set_upload_time(dav_node *node) { @@ -764,7 +780,8 @@ dav_tidy_cache(void) dav_get_webdav_error()); } if (ret == EACCES || ret == EINVAL || ret == ENOENT - || ret == EPERM || ret == ENOSPC || ret == EEXIST) { + || ret == EPERM || ret == ENOSPC || ret == EEXIST + || set_next_upload_attempt(node) < 0) { dav_unlock(node->path, &node->lock_expire); delete_cache_file(node->parent); node->parent->utime = 0; @@ -858,7 +875,8 @@ dav_close(dav_node *node, int fd, int flags, pid_t pid, pid_t pgid) dav_get_webdav_error()); } if (ret == EACCES || ret == EINVAL || ret == ENOENT - || ret == EPERM || ret == ENOSPC || ret == EEXIST) { + || ret == EPERM || ret == ENOSPC || ret == EEXIST + || set_next_upload_attempt(node) < 0) { dav_unlock(node->path, &node->lock_expire); delete_cache_file(node->parent); node->parent->utime = 0; @@ -1644,11 +1662,12 @@ add_to_changed(dav_node *node) return; chp = &(*chp)->next; } - *chp = (dav_node_list_item *) malloc(sizeof(*chp)); + *chp = (dav_node_list_item *) malloc(sizeof(dav_node_list_item)); if (!*chp) abort(); (*chp)->node = node; (*chp)->next = NULL; + (*chp)->attempts = 0; (*chp)->save_at = 0; nchanged++; } diff --git a/src/cache.h b/src/cache.h index a95f252..e3dc6b7 100644 --- a/src/cache.h +++ b/src/cache.h @@ -140,6 +140,7 @@ typedef struct dav_node_item dav_node_list_item; struct dav_node_item { dav_node_list_item *next; dav_node *node; + int attempts; time_t save_at; };