Implement a very simple cookie state machine to handle lookup, invalidation, withdrawal, relinquishment and, to be added later, commit on LRU discard. Three cache methods are provided: ->lookup_cookie() to look up and, if necessary, create a data storage object; ->withdraw_cookie() to free the resources associated with that object and potentially delete it; and ->prepare_to_write(), to do prepare for changes to the cached data to be modified locally. Changes ======= ver #3: - Fix a race between LRU discard and relinquishment whereby the former would override the latter and thus the latter would never happen[1]. ver #2: - Don't hold n_accesses elevated whilst cache is bound to a cookie, but rather add a flag that prevents the state machine from being queued when n_accesses reaches 0.
Showing the changes to include (2 of 3 files). Show all
Unified · Split
| @@ -57,6 +57,15 @@ struct fscache_cache_ops { · 56 unmodified lines | ||
| 57 | 57 | |
| 58 | 58 | /* Free the cache's data attached to a volume */ |
| 59 | 59 | void (*free_volume)(struct fscache_volume *volume); |
| 60 | + | |
| 61 | + /* Look up a cookie in the cache */ | |
| 62 | + bool (*lookup_cookie)(struct fscache_cookie *cookie); | |
| 63 | + | |
| 64 | + /* Withdraw an object without any cookie access counts held */ | |
| 65 | + void (*withdraw_cookie)(struct fscache_cookie *cookie); | |
| 66 | + | |
| 67 | + /* Prepare to write to a live cache object */ | |
| 68 | + void (*prepare_to_write)(struct fscache_cookie *cookie); | |
| 60 | 69 | }; |
| 61 | 70 | |
| 62 | 71 | extern struct workqueue_struct *fscache_wq; |
| @@ -72,6 +81,7 @@ extern int fscache_add_cache(struct fscache_cache *cache, · 9 unmodified lines | ||
| 72 | 81 | void *cache_priv); |
| 73 | 82 | extern void fscache_withdraw_cache(struct fscache_cache *cache); |
| 74 | 83 | extern void fscache_withdraw_volume(struct fscache_volume *volume); |
| 84 | +extern void fscache_withdraw_cookie(struct fscache_cookie *cookie); | |
| 75 | 85 | |
| 76 | 86 | extern void fscache_io_error(struct fscache_cache *cache); |
| 77 | 87 | |
| @@ -85,8 +95,21 @@ extern void fscache_put_cookie(struct fscache_cookie *cookie, · 7 unmodified lines | ||
| 85 | 95 | enum fscache_cookie_trace where); |
| 86 | 96 | extern void fscache_end_cookie_access(struct fscache_cookie *cookie, |
| 87 | 97 | enum fscache_access_trace why); |
| 88 | −extern void fscache_set_cookie_state(struct fscache_cookie *cookie, | |
| 89 | − enum fscache_cookie_state state); | |
| 98 | +extern void fscache_cookie_lookup_negative(struct fscache_cookie *cookie); | |
| 99 | +extern void fscache_caching_failed(struct fscache_cookie *cookie); | |
| 100 | + | |
| 101 | +/** | |
| 102 | + * fscache_cookie_state - Read the state of a cookie | |
| 103 | + * @cookie: The cookie to query | |
| 104 | + * | |
| 105 | + * Get the state of a cookie, imposing an ordering between the cookie contents | |
| 106 | + * and the state value. Paired with fscache_set_cookie_state(). | |
| 107 | + */ | |
| 108 | +static inline | |
| 109 | +enum fscache_cookie_state fscache_cookie_state(struct fscache_cookie *cookie) | |
| 110 | +{ | |
| 111 | + return smp_load_acquire(&cookie->state); | |
| 112 | +} | |
| 90 | 113 | |
| 91 | 114 | /** |
| 92 | 115 | * fscache_get_key - Get a pointer to the cookie key |
| @@ -68,6 +68,8 @@ enum fscache_access_trace { · 67 unmodified lines | ||
| 68 | 68 | fscache_access_acquire_volume_end, |
| 69 | 69 | fscache_access_cache_pin, |
| 70 | 70 | fscache_access_cache_unpin, |
| 71 | + fscache_access_lookup_cookie_end, | |
| 72 | + fscache_access_lookup_cookie_end_failed, | |
| 71 | 73 | fscache_access_relinquish_volume, |
| 72 | 74 | fscache_access_relinquish_volume_end, |
| 73 | 75 | fscache_access_unlive, |
| @@ -124,6 +126,8 @@ enum fscache_access_trace { · 50 unmodified lines | ||
| 124 | 126 | EM(fscache_access_acquire_volume_end, "END acq_vol") \ |
| 125 | 127 | EM(fscache_access_cache_pin, "PIN cache ") \ |
| 126 | 128 | EM(fscache_access_cache_unpin, "UNPIN cache ") \ |
| 129 | + EM(fscache_access_lookup_cookie_end, "END lookup ") \ | |
| 130 | + EM(fscache_access_lookup_cookie_end_failed,"END lookupf") \ | |
| 127 | 131 | EM(fscache_access_relinquish_volume, "BEGIN rlq_vol") \ |
| 128 | 132 | EM(fscache_access_relinquish_volume_end,"END rlq_vol") \ |
| 129 | 133 | E_(fscache_access_unlive, "END unlive ") |