1 /* AFS cell and server record management 2 * 3 * Copyright (C) 2002, 2017 Red Hat, Inc. All Rights Reserved. 4 * Written by David Howells (dhowells@redhat.com) 5 * 6 * This program is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU General Public License 8 * as published by the Free Software Foundation; either version 9 * 2 of the License, or (at your option) any later version. 10 */ 11 12 #include <linux/slab.h> 13 #include <linux/key.h> 14 #include <linux/ctype.h> 15 #include <linux/dns_resolver.h> 16 #include <linux/sched.h> 17 #include <linux/inet.h> 18 #include <linux/namei.h> 19 #include <keys/rxrpc-type.h> 20 #include "internal.h" 21 22 static unsigned __read_mostly afs_cell_gc_delay = 10; 23 static unsigned __read_mostly afs_cell_min_ttl = 10 * 60; 24 static unsigned __read_mostly afs_cell_max_ttl = 24 * 60 * 60; 25 26 static void afs_manage_cell(struct work_struct *); 27 28 static void afs_dec_cells_outstanding(struct afs_net *net) 29 { 30 if (atomic_dec_and_test(&net->cells_outstanding)) 31 wake_up_var(&net->cells_outstanding); 32 } 33 34 /* 35 * Set the cell timer to fire after a given delay, assuming it's not already 36 * set for an earlier time. 37 */ 38 static void afs_set_cell_timer(struct afs_net *net, time64_t delay) 39 { 40 if (net->live) { 41 atomic_inc(&net->cells_outstanding); 42 if (timer_reduce(&net->cells_timer, jiffies + delay * HZ)) 43 afs_dec_cells_outstanding(net); 44 } 45 } 46 47 /* 48 * Look up and get an activation reference on a cell record under RCU 49 * conditions. The caller must hold the RCU read lock. 50 */ 51 struct afs_cell *afs_lookup_cell_rcu(struct afs_net *net, 52 const char *name, unsigned int namesz) 53 { 54 struct afs_cell *cell = NULL; 55 struct rb_node *p; 56 int n, seq = 0, ret = 0; 57 58 _enter("%*.*s", namesz, namesz, name); 59 60 if (name && namesz == 0) 61 return ERR_PTR(-EINVAL); 62 if (namesz > AFS_MAXCELLNAME) 63 return ERR_PTR(-ENAMETOOLONG); 64 65 do { 66 /* Unfortunately, rbtree walking doesn't give reliable results 67 * under just the RCU read lock, so we have to check for 68 * changes. 69 */ 70 if (cell) 71 afs_put_cell(net, cell); 72 cell = NULL; 73 ret = -ENOENT; 74 75 read_seqbegin_or_lock(&net->cells_lock, &seq); 76 77 if (!name) { 78 cell = rcu_dereference_raw(net->ws_cell); 79 if (cell) { 80 afs_get_cell(cell); 81 break; 82 } 83 ret = -EDESTADDRREQ; 84 continue; 85 } 86 87 p = rcu_dereference_raw(net->cells.rb_node); 88 while (p) { 89 cell = rb_entry(p, struct afs_cell, net_node); 90 91 n = strncasecmp(cell->name, name, 92 min_t(size_t, cell->name_len, namesz)); 93 if (n == 0) 94 n = cell->name_len - namesz; 95 if (n < 0) { 96 p = rcu_dereference_raw(p->rb_left); 97 } else if (n > 0) { 98 p = rcu_dereference_raw(p->rb_right); 99 } else { 100 if (atomic_inc_not_zero(&cell->usage)) { 101 ret = 0; 102 break; 103 } 104 /* We want to repeat the search, this time with 105 * the lock properly locked. 106 */ 107 } 108 cell = NULL; 109 } 110 111 } while (need_seqretry(&net->cells_lock, seq)); 112 113 done_seqretry(&net->cells_lock, seq); 114 115 return ret == 0 ? cell : ERR_PTR(ret); 116 } 117 118 /* 119 * Set up a cell record and fill in its name, VL server address list and 120 * allocate an anonymous key 121 */ 122 static struct afs_cell *afs_alloc_cell(struct afs_net *net, 123 const char *name, unsigned int namelen, 124 const char *addresses) 125 { 126 struct afs_cell *cell; 127 int i, ret; 128 129 ASSERT(name); 130 if (namelen == 0) 131 return ERR_PTR(-EINVAL); 132 if (namelen > AFS_MAXCELLNAME) { 133 _leave(" = -ENAMETOOLONG"); 134 return ERR_PTR(-ENAMETOOLONG); 135 } 136 if (namelen == 5 && memcmp(name, "@cell", 5) == 0) 137 return ERR_PTR(-EINVAL); 138 139 _enter("%*.*s,%s", namelen, namelen, name, addresses); 140 141 cell = kzalloc(sizeof(struct afs_cell), GFP_KERNEL); 142 if (!cell) { 143 _leave(" = -ENOMEM"); 144 return ERR_PTR(-ENOMEM); 145 } 146 147 cell->net = net; 148 cell->name_len = namelen; 149 for (i = 0; i < namelen; i++) 150 cell->name[i] = tolower(name[i]); 151 152 atomic_set(&cell->usage, 2); 153 INIT_WORK(&cell->manager, afs_manage_cell); 154 cell->flags = ((1 << AFS_CELL_FL_NOT_READY) | 155 (1 << AFS_CELL_FL_NO_LOOKUP_YET)); 156 INIT_LIST_HEAD(&cell->proc_volumes); 157 rwlock_init(&cell->proc_lock); 158 rwlock_init(&cell->vl_servers_lock); 159 160 /* Fill in the VL server list if we were given a list of addresses to 161 * use. 162 */ 163 if (addresses) { 164 struct afs_vlserver_list *vllist; 165 166 vllist = afs_parse_text_addrs(net, 167 addresses, strlen(addresses), ':', 168 VL_SERVICE, AFS_VL_PORT); 169 if (IS_ERR(vllist)) { 170 ret = PTR_ERR(vllist); 171 goto parse_failed; 172 } 173 174 rcu_assign_pointer(cell->vl_servers, vllist); 175 cell->dns_expiry = TIME64_MAX; 176 __clear_bit(AFS_CELL_FL_NO_LOOKUP_YET, &cell->flags); 177 } else { 178 cell->dns_expiry = ktime_get_real_seconds(); 179 } 180 181 _leave(" = %p", cell); 182 return cell; 183 184 parse_failed: 185 if (ret == -EINVAL) 186 printk(KERN_ERR "kAFS: bad VL server IP address\n"); 187 kfree(cell); 188 _leave(" = %d", ret); 189 return ERR_PTR(ret); 190 } 191 192 /* 193 * afs_lookup_cell - Look up or create a cell record. 194 * @net: The network namespace 195 * @name: The name of the cell. 196 * @namesz: The strlen of the cell name. 197 * @vllist: A colon/comma separated list of numeric IP addresses or NULL. 198 * @excl: T if an error should be given if the cell name already exists. 199 * 200 * Look up a cell record by name and query the DNS for VL server addresses if 201 * needed. Note that that actual DNS query is punted off to the manager thread 202 * so that this function can return immediately if interrupted whilst allowing 203 * cell records to be shared even if not yet fully constructed. 204 */ 205 struct afs_cell *afs_lookup_cell(struct afs_net *net, 206 const char *name, unsigned int namesz, 207 const char *vllist, bool excl) 208 { 209 struct afs_cell *cell, *candidate, *cursor; 210 struct rb_node *parent, **pp; 211 int ret, n; 212 213 _enter("%s,%s", name, vllist); 214 215 if (!excl) { 216 rcu_read_lock(); 217 cell = afs_lookup_cell_rcu(net, name, namesz); 218 rcu_read_unlock(); 219 if (!IS_ERR(cell)) 220 goto wait_for_cell; 221 } 222 223 /* Assume we're probably going to create a cell and preallocate and 224 * mostly set up a candidate record. We can then use this to stash the 225 * name, the net namespace and VL server addresses. 226 * 227 * We also want to do this before we hold any locks as it may involve 228 * upcalling to userspace to make DNS queries. 229 */ 230 candidate = afs_alloc_cell(net, name, namesz, vllist); 231 if (IS_ERR(candidate)) { 232 _leave(" = %ld", PTR_ERR(candidate)); 233 return candidate; 234 } 235 236 /* Find the insertion point and check to see if someone else added a 237 * cell whilst we were allocating. 238 */ 239 write_seqlock(&net->cells_lock); 240 241 pp = &net->cells.rb_node; 242 parent = NULL; 243 while (*pp) { 244 parent = *pp; 245 cursor = rb_entry(parent, struct afs_cell, net_node); 246 247 n = strncasecmp(cursor->name, name, 248 min_t(size_t, cursor->name_len, namesz)); 249 if (n == 0) 250 n = cursor->name_len - namesz; 251 if (n < 0) 252 pp = &(*pp)->rb_left; 253 else if (n > 0) 254 pp = &(*pp)->rb_right; 255 else 256 goto cell_already_exists; 257 } 258 259 cell = candidate; 260 candidate = NULL; 261 rb_link_node_rcu(&cell->net_node, parent, pp); 262 rb_insert_color(&cell->net_node, &net->cells); 263 atomic_inc(&net->cells_outstanding); 264 write_sequnlock(&net->cells_lock); 265 266 queue_work(afs_wq, &cell->manager); 267 268 wait_for_cell: 269 _debug("wait_for_cell"); 270 ret = wait_on_bit(&cell->flags, AFS_CELL_FL_NOT_READY, TASK_INTERRUPTIBLE); 271 smp_rmb(); 272 273 switch (READ_ONCE(cell->state)) { 274 case AFS_CELL_FAILED: 275 ret = cell->error; 276 goto error; 277 default: 278 _debug("weird %u %d", cell->state, cell->error); 279 goto error; 280 case AFS_CELL_ACTIVE: 281 break; 282 } 283 284 _leave(" = %p [cell]", cell); 285 return cell; 286 287 cell_already_exists: 288 _debug("cell exists"); 289 cell = cursor; 290 if (excl) { 291 ret = -EEXIST; 292 } else { 293 afs_get_cell(cursor); 294 ret = 0; 295 } 296 write_sequnlock(&net->cells_lock); 297 kfree(candidate); 298 if (ret == 0) 299 goto wait_for_cell; 300 goto error_noput; 301 error: 302 afs_put_cell(net, cell); 303 error_noput: 304 _leave(" = %d [error]", ret); 305 return ERR_PTR(ret); 306 } 307 308 /* 309 * set the root cell information 310 * - can be called with a module parameter string 311 * - can be called from a write to /proc/fs/afs/rootcell 312 */ 313 int afs_cell_init(struct afs_net *net, const char *rootcell) 314 { 315 struct afs_cell *old_root, *new_root; 316 const char *cp, *vllist; 317 size_t len; 318 319 _enter(""); 320 321 if (!rootcell) { 322 /* module is loaded with no parameters, or built statically. 323 * - in the future we might initialize cell DB here. 324 */ 325 _leave(" = 0 [no root]"); 326 return 0; 327 } 328 329 cp = strchr(rootcell, ':'); 330 if (!cp) { 331 _debug("kAFS: no VL server IP addresses specified"); 332 vllist = NULL; 333 len = strlen(rootcell); 334 } else { 335 vllist = cp + 1; 336 len = cp - rootcell; 337 } 338 339 /* allocate a cell record for the root cell */ 340 new_root = afs_lookup_cell(net, rootcell, len, vllist, false); 341 if (IS_ERR(new_root)) { 342 _leave(" = %ld", PTR_ERR(new_root)); 343 return PTR_ERR(new_root); 344 } 345 346 if (!test_and_set_bit(AFS_CELL_FL_NO_GC, &new_root->flags)) 347 afs_get_cell(new_root); 348 349 /* install the new cell */ 350 write_seqlock(&net->cells_lock); 351 old_root = rcu_access_pointer(net->ws_cell); 352 rcu_assign_pointer(net->ws_cell, new_root); 353 write_sequnlock(&net->cells_lock); 354 355 afs_put_cell(net, old_root); 356 _leave(" = 0"); 357 return 0; 358 } 359 360 /* 361 * Update a cell's VL server address list from the DNS. 362 */ 363 static void afs_update_cell(struct afs_cell *cell) 364 { 365 struct afs_vlserver_list *vllist, *old; 366 unsigned int min_ttl = READ_ONCE(afs_cell_min_ttl); 367 unsigned int max_ttl = READ_ONCE(afs_cell_max_ttl); 368 time64_t now, expiry = 0; 369 370 _enter("%s", cell->name); 371 372 vllist = afs_dns_query(cell, &expiry); 373 374 now = ktime_get_real_seconds(); 375 if (min_ttl > max_ttl) 376 max_ttl = min_ttl; 377 if (expiry < now + min_ttl) 378 expiry = now + min_ttl; 379 else if (expiry > now + max_ttl) 380 expiry = now + max_ttl; 381 382 if (IS_ERR(vllist)) { 383 switch (PTR_ERR(vllist)) { 384 case -ENODATA: 385 case -EDESTADDRREQ: 386 /* The DNS said that the cell does not exist or there 387 * weren't any addresses to be had. 388 */ 389 set_bit(AFS_CELL_FL_NOT_FOUND, &cell->flags); 390 clear_bit(AFS_CELL_FL_DNS_FAIL, &cell->flags); 391 cell->dns_expiry = expiry; 392 break; 393 394 case -EAGAIN: 395 case -ECONNREFUSED: 396 default: 397 set_bit(AFS_CELL_FL_DNS_FAIL, &cell->flags); 398 cell->dns_expiry = now + 10; 399 break; 400 } 401 402 cell->error = -EDESTADDRREQ; 403 } else { 404 clear_bit(AFS_CELL_FL_DNS_FAIL, &cell->flags); 405 clear_bit(AFS_CELL_FL_NOT_FOUND, &cell->flags); 406 407 /* Exclusion on changing vl_addrs is achieved by a 408 * non-reentrant work item. 409 */ 410 old = rcu_dereference_protected(cell->vl_servers, true); 411 rcu_assign_pointer(cell->vl_servers, vllist); 412 cell->dns_expiry = expiry; 413 414 if (old) 415 afs_put_vlserverlist(cell->net, old); 416 } 417 418 if (test_and_clear_bit(AFS_CELL_FL_NO_LOOKUP_YET, &cell->flags)) 419 wake_up_bit(&cell->flags, AFS_CELL_FL_NO_LOOKUP_YET); 420 421 now = ktime_get_real_seconds(); 422 afs_set_cell_timer(cell->net, cell->dns_expiry - now); 423 _leave(""); 424 } 425 426 /* 427 * Destroy a cell record 428 */ 429 static void afs_cell_destroy(struct rcu_head *rcu) 430 { 431 struct afs_cell *cell = container_of(rcu, struct afs_cell, rcu); 432 433 _enter("%p{%s}", cell, cell->name); 434 435 ASSERTCMP(atomic_read(&cell->usage), ==, 0); 436 437 afs_put_vlserverlist(cell->net, rcu_access_pointer(cell->vl_servers)); 438 key_put(cell->anonymous_key); 439 kfree(cell); 440 441 _leave(" [destroyed]"); 442 } 443 444 /* 445 * Queue the cell manager. 446 */ 447 static void afs_queue_cell_manager(struct afs_net *net) 448 { 449 int outstanding = atomic_inc_return(&net->cells_outstanding); 450 451 _enter("%d", outstanding); 452 453 if (!queue_work(afs_wq, &net->cells_manager)) 454 afs_dec_cells_outstanding(net); 455 } 456 457 /* 458 * Cell management timer. We have an increment on cells_outstanding that we 459 * need to pass along to the work item. 460 */ 461 void afs_cells_timer(struct timer_list *timer) 462 { 463 struct afs_net *net = container_of(timer, struct afs_net, cells_timer); 464 465 _enter(""); 466 if (!queue_work(afs_wq, &net->cells_manager)) 467 afs_dec_cells_outstanding(net); 468 } 469 470 /* 471 * Get a reference on a cell record. 472 */ 473 struct afs_cell *afs_get_cell(struct afs_cell *cell) 474 { 475 atomic_inc(&cell->usage); 476 return cell; 477 } 478 479 /* 480 * Drop a reference on a cell record. 481 */ 482 void afs_put_cell(struct afs_net *net, struct afs_cell *cell) 483 { 484 time64_t now, expire_delay; 485 486 if (!cell) 487 return; 488 489 _enter("%s", cell->name); 490 491 now = ktime_get_real_seconds(); 492 cell->last_inactive = now; 493 expire_delay = 0; 494 if (!test_bit(AFS_CELL_FL_DNS_FAIL, &cell->flags) && 495 !test_bit(AFS_CELL_FL_NOT_FOUND, &cell->flags)) 496 expire_delay = afs_cell_gc_delay; 497 498 if (atomic_dec_return(&cell->usage) > 1) 499 return; 500 501 /* 'cell' may now be garbage collected. */ 502 afs_set_cell_timer(net, expire_delay); 503 } 504 505 /* 506 * Allocate a key to use as a placeholder for anonymous user security. 507 */ 508 static int afs_alloc_anon_key(struct afs_cell *cell) 509 { 510 struct key *key; 511 char keyname[4 + AFS_MAXCELLNAME + 1], *cp, *dp; 512 513 /* Create a key to represent an anonymous user. */ 514 memcpy(keyname, "afs@", 4); 515 dp = keyname + 4; 516 cp = cell->name; 517 do { 518 *dp++ = tolower(*cp); 519 } while (*cp++); 520 521 key = rxrpc_get_null_key(keyname); 522 if (IS_ERR(key)) 523 return PTR_ERR(key); 524 525 cell->anonymous_key = key; 526 527 _debug("anon key %p{%x}", 528 cell->anonymous_key, key_serial(cell->anonymous_key)); 529 return 0; 530 } 531 532 /* 533 * Activate a cell. 534 */ 535 static int afs_activate_cell(struct afs_net *net, struct afs_cell *cell) 536 { 537 struct hlist_node **p; 538 struct afs_cell *pcell; 539 int ret; 540 541 if (!cell->anonymous_key) { 542 ret = afs_alloc_anon_key(cell); 543 if (ret < 0) 544 return ret; 545 } 546 547 #ifdef CONFIG_AFS_FSCACHE 548 cell->cache = fscache_acquire_cookie(afs_cache_netfs.primary_index, 549 &afs_cell_cache_index_def, 550 cell->name, strlen(cell->name), 551 NULL, 0, 552 cell, 0, true); 553 #endif 554 ret = afs_proc_cell_setup(cell); 555 if (ret < 0) 556 return ret; 557 558 mutex_lock(&net->proc_cells_lock); 559 for (p = &net->proc_cells.first; *p; p = &(*p)->next) { 560 pcell = hlist_entry(*p, struct afs_cell, proc_link); 561 if (strcmp(cell->name, pcell->name) < 0) 562 break; 563 } 564 565 cell->proc_link.pprev = p; 566 cell->proc_link.next = *p; 567 rcu_assign_pointer(*p, &cell->proc_link.next); 568 if (cell->proc_link.next) 569 cell->proc_link.next->pprev = &cell->proc_link.next; 570 571 afs_dynroot_mkdir(net, cell); 572 mutex_unlock(&net->proc_cells_lock); 573 return 0; 574 } 575 576 /* 577 * Deactivate a cell. 578 */ 579 static void afs_deactivate_cell(struct afs_net *net, struct afs_cell *cell) 580 { 581 _enter("%s", cell->name); 582 583 afs_proc_cell_remove(cell); 584 585 mutex_lock(&net->proc_cells_lock); 586 hlist_del_rcu(&cell->proc_link); 587 afs_dynroot_rmdir(net, cell); 588 mutex_unlock(&net->proc_cells_lock); 589 590 #ifdef CONFIG_AFS_FSCACHE 591 fscache_relinquish_cookie(cell->cache, NULL, false); 592 cell->cache = NULL; 593 #endif 594 595 _leave(""); 596 } 597 598 /* 599 * Manage a cell record, initialising and destroying it, maintaining its DNS 600 * records. 601 */ 602 static void afs_manage_cell(struct work_struct *work) 603 { 604 struct afs_cell *cell = container_of(work, struct afs_cell, manager); 605 struct afs_net *net = cell->net; 606 bool deleted; 607 int ret, usage; 608 609 _enter("%s", cell->name); 610 611 again: 612 _debug("state %u", cell->state); 613 switch (cell->state) { 614 case AFS_CELL_INACTIVE: 615 case AFS_CELL_FAILED: 616 write_seqlock(&net->cells_lock); 617 usage = 1; 618 deleted = atomic_try_cmpxchg_relaxed(&cell->usage, &usage, 0); 619 if (deleted) 620 rb_erase(&cell->net_node, &net->cells); 621 write_sequnlock(&net->cells_lock); 622 if (deleted) 623 goto final_destruction; 624 if (cell->state == AFS_CELL_FAILED) 625 goto done; 626 cell->state = AFS_CELL_UNSET; 627 goto again; 628 629 case AFS_CELL_UNSET: 630 cell->state = AFS_CELL_ACTIVATING; 631 goto again; 632 633 case AFS_CELL_ACTIVATING: 634 ret = afs_activate_cell(net, cell); 635 if (ret < 0) 636 goto activation_failed; 637 638 cell->state = AFS_CELL_ACTIVE; 639 smp_wmb(); 640 clear_bit(AFS_CELL_FL_NOT_READY, &cell->flags); 641 wake_up_bit(&cell->flags, AFS_CELL_FL_NOT_READY); 642 goto again; 643 644 case AFS_CELL_ACTIVE: 645 if (atomic_read(&cell->usage) > 1) { 646 time64_t now = ktime_get_real_seconds(); 647 if (cell->dns_expiry <= now && net->live) 648 afs_update_cell(cell); 649 goto done; 650 } 651 cell->state = AFS_CELL_DEACTIVATING; 652 goto again; 653 654 case AFS_CELL_DEACTIVATING: 655 set_bit(AFS_CELL_FL_NOT_READY, &cell->flags); 656 if (atomic_read(&cell->usage) > 1) 657 goto reverse_deactivation; 658 afs_deactivate_cell(net, cell); 659 cell->state = AFS_CELL_INACTIVE; 660 goto again; 661 662 default: 663 break; 664 } 665 _debug("bad state %u", cell->state); 666 BUG(); /* Unhandled state */ 667 668 activation_failed: 669 cell->error = ret; 670 afs_deactivate_cell(net, cell); 671 672 cell->state = AFS_CELL_FAILED; 673 smp_wmb(); 674 if (test_and_clear_bit(AFS_CELL_FL_NOT_READY, &cell->flags)) 675 wake_up_bit(&cell->flags, AFS_CELL_FL_NOT_READY); 676 goto again; 677 678 reverse_deactivation: 679 cell->state = AFS_CELL_ACTIVE; 680 smp_wmb(); 681 clear_bit(AFS_CELL_FL_NOT_READY, &cell->flags); 682 wake_up_bit(&cell->flags, AFS_CELL_FL_NOT_READY); 683 _leave(" [deact->act]"); 684 return; 685 686 done: 687 _leave(" [done %u]", cell->state); 688 return; 689 690 final_destruction: 691 call_rcu(&cell->rcu, afs_cell_destroy); 692 afs_dec_cells_outstanding(net); 693 _leave(" [destruct %d]", atomic_read(&net->cells_outstanding)); 694 } 695 696 /* 697 * Manage the records of cells known to a network namespace. This includes 698 * updating the DNS records and garbage collecting unused cells that were 699 * automatically added. 700 * 701 * Note that constructed cell records may only be removed from net->cells by 702 * this work item, so it is safe for this work item to stash a cursor pointing 703 * into the tree and then return to caller (provided it skips cells that are 704 * still under construction). 705 * 706 * Note also that we were given an increment on net->cells_outstanding by 707 * whoever queued us that we need to deal with before returning. 708 */ 709 void afs_manage_cells(struct work_struct *work) 710 { 711 struct afs_net *net = container_of(work, struct afs_net, cells_manager); 712 struct rb_node *cursor; 713 time64_t now = ktime_get_real_seconds(), next_manage = TIME64_MAX; 714 bool purging = !net->live; 715 716 _enter(""); 717 718 /* Trawl the cell database looking for cells that have expired from 719 * lack of use and cells whose DNS results have expired and dispatch 720 * their managers. 721 */ 722 read_seqlock_excl(&net->cells_lock); 723 724 for (cursor = rb_first(&net->cells); cursor; cursor = rb_next(cursor)) { 725 struct afs_cell *cell = 726 rb_entry(cursor, struct afs_cell, net_node); 727 unsigned usage; 728 bool sched_cell = false; 729 730 usage = atomic_read(&cell->usage); 731 _debug("manage %s %u", cell->name, usage); 732 733 ASSERTCMP(usage, >=, 1); 734 735 if (purging) { 736 if (test_and_clear_bit(AFS_CELL_FL_NO_GC, &cell->flags)) 737 usage = atomic_dec_return(&cell->usage); 738 ASSERTCMP(usage, ==, 1); 739 } 740 741 if (usage == 1) { 742 time64_t expire_at = cell->last_inactive; 743 744 if (!test_bit(AFS_CELL_FL_DNS_FAIL, &cell->flags) && 745 !test_bit(AFS_CELL_FL_NOT_FOUND, &cell->flags)) 746 expire_at += afs_cell_gc_delay; 747 if (purging || expire_at <= now) 748 sched_cell = true; 749 else if (expire_at < next_manage) 750 next_manage = expire_at; 751 } 752 753 if (!purging) { 754 if (cell->dns_expiry <= now) 755 sched_cell = true; 756 else if (cell->dns_expiry <= next_manage) 757 next_manage = cell->dns_expiry; 758 } 759 760 if (sched_cell) 761 queue_work(afs_wq, &cell->manager); 762 } 763 764 read_sequnlock_excl(&net->cells_lock); 765 766 /* Update the timer on the way out. We have to pass an increment on 767 * cells_outstanding in the namespace that we are in to the timer or 768 * the work scheduler. 769 */ 770 if (!purging && next_manage < TIME64_MAX) { 771 now = ktime_get_real_seconds(); 772 773 if (next_manage - now <= 0) { 774 if (queue_work(afs_wq, &net->cells_manager)) 775 atomic_inc(&net->cells_outstanding); 776 } else { 777 afs_set_cell_timer(net, next_manage - now); 778 } 779 } 780 781 afs_dec_cells_outstanding(net); 782 _leave(" [%d]", atomic_read(&net->cells_outstanding)); 783 } 784 785 /* 786 * Purge in-memory cell database. 787 */ 788 void afs_cell_purge(struct afs_net *net) 789 { 790 struct afs_cell *ws; 791 792 _enter(""); 793 794 write_seqlock(&net->cells_lock); 795 ws = rcu_access_pointer(net->ws_cell); 796 RCU_INIT_POINTER(net->ws_cell, NULL); 797 write_sequnlock(&net->cells_lock); 798 afs_put_cell(net, ws); 799 800 _debug("del timer"); 801 if (del_timer_sync(&net->cells_timer)) 802 atomic_dec(&net->cells_outstanding); 803 804 _debug("kick mgr"); 805 afs_queue_cell_manager(net); 806 807 _debug("wait"); 808 wait_var_event(&net->cells_outstanding, 809 !atomic_read(&net->cells_outstanding)); 810 _leave(""); 811 } 812