aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--fs/nfs/dns_resolve.c6
-rw-r--r--fs/nfsd/nfs4idmap.c2
-rw-r--r--include/linux/sunrpc/cache.h28
-rw-r--r--net/sunrpc/cache.c36
4 files changed, 48 insertions, 24 deletions
diff --git a/fs/nfs/dns_resolve.c b/fs/nfs/dns_resolve.c
index dba50a5625db..a6e711ad130f 100644
--- a/fs/nfs/dns_resolve.c
+++ b/fs/nfs/dns_resolve.c
@@ -167,7 +167,7 @@ static int nfs_dns_show(struct seq_file *m, struct cache_detail *cd,
167 return 0; 167 return 0;
168 } 168 }
169 item = container_of(h, struct nfs_dns_ent, h); 169 item = container_of(h, struct nfs_dns_ent, h);
170 ttl = (long)item->h.expiry_time - (long)get_seconds(); 170 ttl = item->h.expiry_time - seconds_since_boot();
171 if (ttl < 0) 171 if (ttl < 0)
172 ttl = 0; 172 ttl = 0;
173 173
@@ -239,7 +239,7 @@ static int nfs_dns_parse(struct cache_detail *cd, char *buf, int buflen)
239 ttl = get_expiry(&buf); 239 ttl = get_expiry(&buf);
240 if (ttl == 0) 240 if (ttl == 0)
241 goto out; 241 goto out;
242 key.h.expiry_time = ttl + get_seconds(); 242 key.h.expiry_time = ttl + seconds_since_boot();
243 243
244 ret = -ENOMEM; 244 ret = -ENOMEM;
245 item = nfs_dns_lookup(cd, &key); 245 item = nfs_dns_lookup(cd, &key);
@@ -301,7 +301,7 @@ static int do_cache_lookup_nowait(struct cache_detail *cd,
301 goto out_err; 301 goto out_err;
302 ret = -ETIMEDOUT; 302 ret = -ETIMEDOUT;
303 if (!test_bit(CACHE_VALID, &(*item)->h.flags) 303 if (!test_bit(CACHE_VALID, &(*item)->h.flags)
304 || (*item)->h.expiry_time < get_seconds() 304 || (*item)->h.expiry_time < seconds_since_boot()
305 || cd->flush_time > (*item)->h.last_refresh) 305 || cd->flush_time > (*item)->h.last_refresh)
306 goto out_put; 306 goto out_put;
307 ret = -ENOENT; 307 ret = -ENOENT;
diff --git a/fs/nfsd/nfs4idmap.c b/fs/nfsd/nfs4idmap.c
index c78dbf493424..808b33a4a090 100644
--- a/fs/nfsd/nfs4idmap.c
+++ b/fs/nfsd/nfs4idmap.c
@@ -550,7 +550,7 @@ do_idmap_lookup_nowait(struct ent *(*lookup_fn)(struct ent *),
550 goto out_err; 550 goto out_err;
551 ret = -ETIMEDOUT; 551 ret = -ETIMEDOUT;
552 if (!test_bit(CACHE_VALID, &(*item)->h.flags) 552 if (!test_bit(CACHE_VALID, &(*item)->h.flags)
553 || (*item)->h.expiry_time < get_seconds() 553 || (*item)->h.expiry_time < seconds_since_boot()
554 || detail->flush_time > (*item)->h.last_refresh) 554 || detail->flush_time > (*item)->h.last_refresh)
555 goto out_put; 555 goto out_put;
556 ret = -ENOENT; 556 ret = -ENOENT;
diff --git a/include/linux/sunrpc/cache.h b/include/linux/sunrpc/cache.h
index 0e1febf4e5bc..ece432b7f87f 100644
--- a/include/linux/sunrpc/cache.h
+++ b/include/linux/sunrpc/cache.h
@@ -218,20 +218,42 @@ static inline int get_int(char **bpp, int *anint)
218 return 0; 218 return 0;
219} 219}
220 220
221/*
222 * timestamps kept in the cache are expressed in seconds
223 * since boot. This is the best for measuring differences in
224 * real time.
225 */
226static inline time_t seconds_since_boot(void)
227{
228 struct timespec boot;
229 getboottime(&boot);
230 return get_seconds() - boot.tv_sec;
231}
232
233static inline time_t convert_to_wallclock(time_t sinceboot)
234{
235 struct timespec boot;
236 getboottime(&boot);
237 return boot.tv_sec + sinceboot;
238}
239
221static inline time_t get_expiry(char **bpp) 240static inline time_t get_expiry(char **bpp)
222{ 241{
223 int rv; 242 int rv;
243 struct timespec boot;
244
224 if (get_int(bpp, &rv)) 245 if (get_int(bpp, &rv))
225 return 0; 246 return 0;
226 if (rv < 0) 247 if (rv < 0)
227 return 0; 248 return 0;
228 return rv; 249 getboottime(&boot);
250 return rv - boot.tv_sec;
229} 251}
230 252
231static inline void sunrpc_invalidate(struct cache_head *h, 253static inline void sunrpc_invalidate(struct cache_head *h,
232 struct cache_detail *detail) 254 struct cache_detail *detail)
233{ 255{
234 h->expiry_time = get_seconds() - 1; 256 h->expiry_time = seconds_since_boot() - 1;
235 detail->nextcheck = get_seconds(); 257 detail->nextcheck = seconds_since_boot();
236} 258}
237#endif /* _LINUX_SUNRPC_CACHE_H_ */ 259#endif /* _LINUX_SUNRPC_CACHE_H_ */
diff --git a/net/sunrpc/cache.c b/net/sunrpc/cache.c
index 2b06410e584e..8dc121955fdc 100644
--- a/net/sunrpc/cache.c
+++ b/net/sunrpc/cache.c
@@ -42,7 +42,7 @@ static void cache_revisit_request(struct cache_head *item);
42 42
43static void cache_init(struct cache_head *h) 43static void cache_init(struct cache_head *h)
44{ 44{
45 time_t now = get_seconds(); 45 time_t now = seconds_since_boot();
46 h->next = NULL; 46 h->next = NULL;
47 h->flags = 0; 47 h->flags = 0;
48 kref_init(&h->ref); 48 kref_init(&h->ref);
@@ -52,7 +52,7 @@ static void cache_init(struct cache_head *h)
52 52
53static inline int cache_is_expired(struct cache_detail *detail, struct cache_head *h) 53static inline int cache_is_expired(struct cache_detail *detail, struct cache_head *h)
54{ 54{
55 return (h->expiry_time < get_seconds()) || 55 return (h->expiry_time < seconds_since_boot()) ||
56 (detail->flush_time > h->last_refresh); 56 (detail->flush_time > h->last_refresh);
57} 57}
58 58
@@ -127,7 +127,7 @@ static void cache_dequeue(struct cache_detail *detail, struct cache_head *ch);
127static void cache_fresh_locked(struct cache_head *head, time_t expiry) 127static void cache_fresh_locked(struct cache_head *head, time_t expiry)
128{ 128{
129 head->expiry_time = expiry; 129 head->expiry_time = expiry;
130 head->last_refresh = get_seconds(); 130 head->last_refresh = seconds_since_boot();
131 set_bit(CACHE_VALID, &head->flags); 131 set_bit(CACHE_VALID, &head->flags);
132} 132}
133 133
@@ -238,7 +238,7 @@ int cache_check(struct cache_detail *detail,
238 238
239 /* now see if we want to start an upcall */ 239 /* now see if we want to start an upcall */
240 refresh_age = (h->expiry_time - h->last_refresh); 240 refresh_age = (h->expiry_time - h->last_refresh);
241 age = get_seconds() - h->last_refresh; 241 age = seconds_since_boot() - h->last_refresh;
242 242
243 if (rqstp == NULL) { 243 if (rqstp == NULL) {
244 if (rv == -EAGAIN) 244 if (rv == -EAGAIN)
@@ -253,7 +253,7 @@ int cache_check(struct cache_detail *detail,
253 cache_revisit_request(h); 253 cache_revisit_request(h);
254 if (rv == -EAGAIN) { 254 if (rv == -EAGAIN) {
255 set_bit(CACHE_NEGATIVE, &h->flags); 255 set_bit(CACHE_NEGATIVE, &h->flags);
256 cache_fresh_locked(h, get_seconds()+CACHE_NEW_EXPIRY); 256 cache_fresh_locked(h, seconds_since_boot()+CACHE_NEW_EXPIRY);
257 cache_fresh_unlocked(h, detail); 257 cache_fresh_unlocked(h, detail);
258 rv = -ENOENT; 258 rv = -ENOENT;
259 } 259 }
@@ -388,11 +388,11 @@ static int cache_clean(void)
388 return -1; 388 return -1;
389 } 389 }
390 current_detail = list_entry(next, struct cache_detail, others); 390 current_detail = list_entry(next, struct cache_detail, others);
391 if (current_detail->nextcheck > get_seconds()) 391 if (current_detail->nextcheck > seconds_since_boot())
392 current_index = current_detail->hash_size; 392 current_index = current_detail->hash_size;
393 else { 393 else {
394 current_index = 0; 394 current_index = 0;
395 current_detail->nextcheck = get_seconds()+30*60; 395 current_detail->nextcheck = seconds_since_boot()+30*60;
396 } 396 }
397 } 397 }
398 398
@@ -477,7 +477,7 @@ EXPORT_SYMBOL_GPL(cache_flush);
477void cache_purge(struct cache_detail *detail) 477void cache_purge(struct cache_detail *detail)
478{ 478{
479 detail->flush_time = LONG_MAX; 479 detail->flush_time = LONG_MAX;
480 detail->nextcheck = get_seconds(); 480 detail->nextcheck = seconds_since_boot();
481 cache_flush(); 481 cache_flush();
482 detail->flush_time = 1; 482 detail->flush_time = 1;
483} 483}
@@ -902,7 +902,7 @@ static int cache_release(struct inode *inode, struct file *filp,
902 filp->private_data = NULL; 902 filp->private_data = NULL;
903 kfree(rp); 903 kfree(rp);
904 904
905 cd->last_close = get_seconds(); 905 cd->last_close = seconds_since_boot();
906 atomic_dec(&cd->readers); 906 atomic_dec(&cd->readers);
907 } 907 }
908 module_put(cd->owner); 908 module_put(cd->owner);
@@ -1034,7 +1034,7 @@ int sunrpc_cache_pipe_upcall(struct cache_detail *detail, struct cache_head *h,
1034 int len; 1034 int len;
1035 1035
1036 if (atomic_read(&detail->readers) == 0 && 1036 if (atomic_read(&detail->readers) == 0 &&
1037 detail->last_close < get_seconds() - 30) { 1037 detail->last_close < seconds_since_boot() - 30) {
1038 warn_no_listener(detail); 1038 warn_no_listener(detail);
1039 return -EINVAL; 1039 return -EINVAL;
1040 } 1040 }
@@ -1219,7 +1219,8 @@ static int c_show(struct seq_file *m, void *p)
1219 1219
1220 ifdebug(CACHE) 1220 ifdebug(CACHE)
1221 seq_printf(m, "# expiry=%ld refcnt=%d flags=%lx\n", 1221 seq_printf(m, "# expiry=%ld refcnt=%d flags=%lx\n",
1222 cp->expiry_time, atomic_read(&cp->ref.refcount), cp->flags); 1222 convert_to_wallclock(cp->expiry_time),
1223 atomic_read(&cp->ref.refcount), cp->flags);
1223 cache_get(cp); 1224 cache_get(cp);
1224 if (cache_check(cd, cp, NULL)) 1225 if (cache_check(cd, cp, NULL))
1225 /* cache_check does a cache_put on failure */ 1226 /* cache_check does a cache_put on failure */
@@ -1285,7 +1286,7 @@ static ssize_t read_flush(struct file *file, char __user *buf,
1285 unsigned long p = *ppos; 1286 unsigned long p = *ppos;
1286 size_t len; 1287 size_t len;
1287 1288
1288 sprintf(tbuf, "%lu\n", cd->flush_time); 1289 sprintf(tbuf, "%lu\n", convert_to_wallclock(cd->flush_time));
1289 len = strlen(tbuf); 1290 len = strlen(tbuf);
1290 if (p >= len) 1291 if (p >= len)
1291 return 0; 1292 return 0;
@@ -1303,19 +1304,20 @@ static ssize_t write_flush(struct file *file, const char __user *buf,
1303 struct cache_detail *cd) 1304 struct cache_detail *cd)
1304{ 1305{
1305 char tbuf[20]; 1306 char tbuf[20];
1306 char *ep; 1307 char *bp, *ep;
1307 long flushtime; 1308
1308 if (*ppos || count > sizeof(tbuf)-1) 1309 if (*ppos || count > sizeof(tbuf)-1)
1309 return -EINVAL; 1310 return -EINVAL;
1310 if (copy_from_user(tbuf, buf, count)) 1311 if (copy_from_user(tbuf, buf, count))
1311 return -EFAULT; 1312 return -EFAULT;
1312 tbuf[count] = 0; 1313 tbuf[count] = 0;
1313 flushtime = simple_strtoul(tbuf, &ep, 0); 1314 simple_strtoul(tbuf, &ep, 0);
1314 if (*ep && *ep != '\n') 1315 if (*ep && *ep != '\n')
1315 return -EINVAL; 1316 return -EINVAL;
1316 1317
1317 cd->flush_time = flushtime; 1318 bp = tbuf;
1318 cd->nextcheck = get_seconds(); 1319 cd->flush_time = get_expiry(&bp);
1320 cd->nextcheck = seconds_since_boot();
1319 cache_flush(); 1321 cache_flush();
1320 1322
1321 *ppos += count; 1323 *ppos += count;