ASF Bugzilla – Attachment 23956 Details for
Bug 39815
Atomic Creation of uploaded files in mod_dav
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Help
|
New Account
|
Log In
Remember
[x]
|
Forgot Password
Login:
[x]
[patch]
also disable inode keyed locks and cleanup the tempfile if something goes wrong
dav_lock_fname.diff (text/plain), 4.97 KB, created by
Stefan Fritsch
on 2009-07-10 10:10:30 UTC
(
hide
)
Description:
also disable inode keyed locks and cleanup the tempfile if something goes wrong
Filename:
MIME Type:
Creator:
Stefan Fritsch
Created:
2009-07-10 10:10:30 UTC
Size:
4.97 KB
patch
obsolete
>--- modules/dav/fs/repos.c.orig 2008-08-16 00:12:47.000000000 +0200 >+++ modules/dav/fs/repos.c 2009-07-10 19:01:24.000000000 +0200 >@@ -191,6 +191,7 @@ > apr_pool_t *p; > apr_file_t *f; > const char *pathname; /* we may need to remove it at close time */ >+ const char *temppath; > }; > > /* returns an appropriate HTTP status code given an APR status code for a >@@ -841,6 +842,14 @@ > && ctx2->pathname[len1] == '/'); > } > >+static apr_status_t tmpfile_cleanup(void *data) { >+ dav_stream *ds = data; >+ if (ds->temppath) { >+ apr_file_remove(ds->temppath, ds->p); >+ } >+ return APR_SUCCESS; >+} >+ > static dav_error * dav_fs_open_stream(const dav_resource *resource, > dav_stream_mode mode, > dav_stream **stream) >@@ -849,6 +858,7 @@ > dav_stream *ds = apr_pcalloc(p, sizeof(*ds)); > apr_int32_t flags; > apr_status_t rv; >+ char* fpath; > > switch (mode) { > default: >@@ -865,7 +875,18 @@ > > ds->p = p; > ds->pathname = resource->info->pathname; >- rv = apr_file_open(&ds->f, ds->pathname, flags, APR_OS_DEFAULT, ds->p); >+ ds->temppath = NULL; >+ >+ if (mode == DAV_MODE_WRITE_TRUNC) { >+ fpath = apr_pstrcat(p, ds->pathname, ".tmp.XXXXXX", NULL); >+ rv = apr_file_mktemp(&ds->f, fpath, flags, ds->p); >+ ds->temppath = fpath; >+ apr_pool_cleanup_register(p, ds, tmpfile_cleanup, apr_pool_cleanup_null); >+ } >+ else { >+ rv = apr_file_open(&ds->f, ds->pathname, flags, APR_OS_DEFAULT, ds->p); >+ } >+ > if (rv != APR_SUCCESS) { > return dav_new_error(p, MAP_IO2HTTP(rv), 0, > "An error occurred while opening a resource."); >@@ -879,16 +900,32 @@ > > static dav_error * dav_fs_close_stream(dav_stream *stream, int commit) > { >+ apr_status_t rv; >+ > apr_file_close(stream->f); > > if (!commit) { >- if (apr_file_remove(stream->pathname, stream->p) != APR_SUCCESS) { >- /* ### use a better description? */ >- return dav_new_error(stream->p, HTTP_INTERNAL_SERVER_ERROR, 0, >- "There was a problem removing (rolling " >- "back) the resource " >- "when it was being closed."); >+ if (stream->temppath) { >+ apr_pool_cleanup_run(stream->p, stream, tmpfile_cleanup); >+ } >+ else { >+ if (apr_file_remove(stream->pathname, stream->p) != APR_SUCCESS) { >+ /* ### use a better description? */ >+ return dav_new_error(stream->p, HTTP_INTERNAL_SERVER_ERROR, 0, >+ "There was a problem removing (rolling " >+ "back) the resource " >+ "when it was being closed."); >+ } >+ } >+ } >+ else if (stream->temppath) { >+ rv = apr_file_rename(stream->temppath, stream->pathname, stream->p); >+ if (rv) { >+ return dav_new_error(stream->p, HTTP_INTERNAL_SERVER_ERROR, rv, >+ "There was a problem writing the file " >+ "atomically after writes."); > } >+ apr_pool_cleanup_kill(stream->p, stream, tmpfile_cleanup); > } > > return NULL; >--- modules/dav/fs/lock.c.orig 2007-11-29 21:21:10.000000000 +0100 >+++ modules/dav/fs/lock.c 2009-07-10 13:42:43.000000000 +0200 >@@ -398,46 +398,48 @@ > ** to look up lock information for this file. > ** > ** (inode/dev not supported or file is lock-null): > ** apr_datum_t->dvalue = full path > ** > ** (inode/dev supported and file exists ): > ** apr_datum_t->dvalue = inode, dev > */ > static apr_datum_t dav_fs_build_key(apr_pool_t *p, > const dav_resource *resource) > { > const char *file = dav_fs_pathname(resource); >+#if 0 > apr_datum_t key; > apr_finfo_t finfo; > apr_status_t rv; > > /* ### use lstat() ?? */ > /* > * XXX: What for platforms with no IDENT (dev/inode)? > */ > rv = apr_stat(&finfo, file, APR_FINFO_IDENT, p); > if ((rv == APR_SUCCESS || rv == APR_INCOMPLETE) > && ((finfo.valid & APR_FINFO_IDENT) == APR_FINFO_IDENT)) > { > /* ### can we use a buffer for this? */ > key.dsize = 1 + sizeof(finfo.inode) + sizeof(finfo.device); > key.dptr = apr_palloc(p, key.dsize); > *key.dptr = DAV_TYPE_INODE; > memcpy(key.dptr + 1, &finfo.inode, sizeof(finfo.inode)); > memcpy(key.dptr + 1 + sizeof(finfo.inode), &finfo.device, > sizeof(finfo.device)); > > return key; > } >+#endif > > return dav_fs_build_fname_key(p, file); > } > > /* > ** dav_fs_lock_expired: return 1 (true) if the given timeout is in the past > ** or present (the lock has expired), or 0 (false) if in the future > ** (the lock has not yet expired). > */ > static int dav_fs_lock_expired(time_t expires) > { > return expires != DAV_TIMEOUT_INFINITE && time(NULL) >= expires;
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 39815
:
18472
| 23956