CacheFiles: Implement interface to check cache consistency

Implement the FS-Cache interface to check the consistency of a cache object in
CacheFiles.

Original-author: Hongyi Jia <jiayisuse@gmail.com>
Signed-off-by: David Howells <dhowells@redhat.com>
cc: Hongyi Jia <jiayisuse@gmail.com>
cc: Milosz Tanski <milosz@adfin.com>
This commit is contained in:
David Howells 2013-08-21 17:29:21 -04:00
parent da9803bc88
commit 5002d7bef8
3 changed files with 63 additions and 0 deletions

View File

@ -377,6 +377,31 @@ static void cachefiles_sync_cache(struct fscache_cache *_cache)
ret);
}
/*
* check if the backing cache is updated to FS-Cache
* - called by FS-Cache when evaluates if need to invalidate the cache
*/
static bool cachefiles_check_consistency(struct fscache_operation *op)
{
struct cachefiles_object *object;
struct cachefiles_cache *cache;
const struct cred *saved_cred;
int ret;
_enter("{OBJ%x}", op->object->debug_id);
object = container_of(op->object, struct cachefiles_object, fscache);
cache = container_of(object->fscache.cache,
struct cachefiles_cache, cache);
cachefiles_begin_secure(cache, &saved_cred);
ret = cachefiles_check_auxdata(object);
cachefiles_end_secure(cache, saved_cred);
_leave(" = %d", ret);
return ret;
}
/*
* notification the attributes on an object have changed
* - called with reads/writes excluded by FS-Cache
@ -522,4 +547,5 @@ const struct fscache_cache_ops cachefiles_cache_ops = {
.write_page = cachefiles_write_page,
.uncache_page = cachefiles_uncache_page,
.dissociate_pages = cachefiles_dissociate_pages,
.check_consistency = cachefiles_check_consistency,
};

View File

@ -235,6 +235,7 @@ extern int cachefiles_set_object_xattr(struct cachefiles_object *object,
struct cachefiles_xattr *auxdata);
extern int cachefiles_update_object_xattr(struct cachefiles_object *object,
struct cachefiles_xattr *auxdata);
extern int cachefiles_check_auxdata(struct cachefiles_object *object);
extern int cachefiles_check_object_xattr(struct cachefiles_object *object,
struct cachefiles_xattr *auxdata);
extern int cachefiles_remove_object_xattr(struct cachefiles_cache *cache,

View File

@ -156,6 +156,42 @@ int cachefiles_update_object_xattr(struct cachefiles_object *object,
return ret;
}
/*
* check the consistency between the backing cache and the FS-Cache cookie
*/
int cachefiles_check_auxdata(struct cachefiles_object *object)
{
struct cachefiles_xattr *auxbuf;
struct dentry *dentry = object->dentry;
unsigned int dlen;
int ret;
ASSERT(dentry);
ASSERT(dentry->d_inode);
ASSERT(object->fscache.cookie->def->check_aux);
auxbuf = kmalloc(sizeof(struct cachefiles_xattr) + 512, GFP_KERNEL);
if (!auxbuf)
return -ENOMEM;
auxbuf->len = vfs_getxattr(dentry, cachefiles_xattr_cache,
&auxbuf->type, 512 + 1);
if (auxbuf->len < 1)
return -ESTALE;
if (auxbuf->type != object->fscache.cookie->def->type)
return -ESTALE;
dlen = auxbuf->len - 1;
ret = fscache_check_aux(&object->fscache, &auxbuf->data, dlen);
kfree(auxbuf);
if (ret != FSCACHE_CHECKAUX_OKAY)
return -ESTALE;
return 0;
}
/*
* check the state xattr on a cache file
* - return -ESTALE if the object should be deleted