aboutsummaryrefslogtreecommitdiffstats
path: root/net/tipc/name_table.c
diff options
context:
space:
mode:
authorAllan Stephens <allan.stephens@windriver.com>2011-05-30 09:44:38 -0400
committerPaul Gortmaker <paul.gortmaker@windriver.com>2011-06-24 16:18:16 -0400
commitb52124a50fa7b870a3d1a18a8ff56273c7d690dd (patch)
tree8f8de3584f1383125cecc60efb67734e2b585945 /net/tipc/name_table.c
parent7eb878ed8e0eae67269439bfd82234f9ba52ffe4 (diff)
tipc: Partition name table instance array info into two parts
Modifies the name table array structure that contains the name sequence instances for a given name type so that the publication lists associated with a given instance are stored in a dynamically allocated structure, rather than being embedded within the array entry itself. This change is being done for several reasons: 1) It reduces the amount of data that needs to be copied whenever a given array is expanded or contracted to accommodate the first publication of a new name sequence or the removal of the last publication of an existing name sequence. 2) It reduces the amount of memory associated with array entries that are currently unused. 3) It facilitates the upcoming conversion of the publication lists from TIPC-specific circular lists to standard kernel lists. (Standard lists cannot be used with the former array structure because the relocation of array entries during array expansion and contraction would corrupt the lists.) Note that, aside from introducing a small amount of code to dynamically allocate and free the structure that now holds publication list info, this change is largely a simple renaming exercise that replaces references to "sseq->LIST" with "sseq->info->LIST" (or "info->LIST"). Signed-off-by: Allan Stephens <allan.stephens@windriver.com> Signed-off-by: Paul Gortmaker <paul.gortmaker@windriver.com>
Diffstat (limited to 'net/tipc/name_table.c')
-rw-r--r--net/tipc/name_table.c150
1 files changed, 89 insertions, 61 deletions
diff --git a/net/tipc/name_table.c b/net/tipc/name_table.c
index 205ed4a4e186..9cd58f8318f1 100644
--- a/net/tipc/name_table.c
+++ b/net/tipc/name_table.c
@@ -44,9 +44,7 @@
44static int tipc_nametbl_size = 1024; /* must be a power of 2 */ 44static int tipc_nametbl_size = 1024; /* must be a power of 2 */
45 45
46/** 46/**
47 * struct sub_seq - container for all published instances of a name sequence 47 * struct name_info - name sequence publication info
48 * @lower: name sequence lower bound
49 * @upper: name sequence upper bound
50 * @node_list: circular list of publications made by own node 48 * @node_list: circular list of publications made by own node
51 * @cluster_list: circular list of publications made by own cluster 49 * @cluster_list: circular list of publications made by own cluster
52 * @zone_list: circular list of publications made by own zone 50 * @zone_list: circular list of publications made by own zone
@@ -59,9 +57,7 @@ static int tipc_nametbl_size = 1024; /* must be a power of 2 */
59 * (The cluster and node lists may be empty.) 57 * (The cluster and node lists may be empty.)
60 */ 58 */
61 59
62struct sub_seq { 60struct name_info {
63 u32 lower;
64 u32 upper;
65 struct publication *node_list; 61 struct publication *node_list;
66 struct publication *cluster_list; 62 struct publication *cluster_list;
67 struct publication *zone_list; 63 struct publication *zone_list;
@@ -71,6 +67,19 @@ struct sub_seq {
71}; 67};
72 68
73/** 69/**
70 * struct sub_seq - container for all published instances of a name sequence
71 * @lower: name sequence lower bound
72 * @upper: name sequence upper bound
73 * @info: pointer to name sequence publication info
74 */
75
76struct sub_seq {
77 u32 lower;
78 u32 upper;
79 struct name_info *info;
80};
81
82/**
74 * struct name_seq - container for all published instances of a name type 83 * struct name_seq - container for all published instances of a name type
75 * @type: 32 bit 'type' value for name sequence 84 * @type: 32 bit 'type' value for name sequence
76 * @sseq: pointer to dynamically-sized array of sub-sequences of this 'type'; 85 * @sseq: pointer to dynamically-sized array of sub-sequences of this 'type';
@@ -246,6 +255,7 @@ static struct publication *tipc_nameseq_insert_publ(struct name_seq *nseq,
246 struct subscription *st; 255 struct subscription *st;
247 struct publication *publ; 256 struct publication *publ;
248 struct sub_seq *sseq; 257 struct sub_seq *sseq;
258 struct name_info *info;
249 int created_subseq = 0; 259 int created_subseq = 0;
250 260
251 sseq = nameseq_find_subseq(nseq, lower); 261 sseq = nameseq_find_subseq(nseq, lower);
@@ -258,6 +268,8 @@ static struct publication *tipc_nameseq_insert_publ(struct name_seq *nseq,
258 type, lower, upper); 268 type, lower, upper);
259 return NULL; 269 return NULL;
260 } 270 }
271
272 info = sseq->info;
261 } else { 273 } else {
262 u32 inspos; 274 u32 inspos;
263 struct sub_seq *freesseq; 275 struct sub_seq *freesseq;
@@ -292,6 +304,13 @@ static struct publication *tipc_nameseq_insert_publ(struct name_seq *nseq,
292 nseq->alloc *= 2; 304 nseq->alloc *= 2;
293 } 305 }
294 306
307 info = kzalloc(sizeof(*info), GFP_ATOMIC);
308 if (!info) {
309 warn("Cannot publish {%u,%u,%u}, no memory\n",
310 type, lower, upper);
311 return NULL;
312 }
313
295 /* Insert new sub-sequence */ 314 /* Insert new sub-sequence */
296 315
297 sseq = &nseq->sseqs[inspos]; 316 sseq = &nseq->sseqs[inspos];
@@ -301,6 +320,7 @@ static struct publication *tipc_nameseq_insert_publ(struct name_seq *nseq,
301 nseq->first_free++; 320 nseq->first_free++;
302 sseq->lower = lower; 321 sseq->lower = lower;
303 sseq->upper = upper; 322 sseq->upper = upper;
323 sseq->info = info;
304 created_subseq = 1; 324 created_subseq = 1;
305 } 325 }
306 326
@@ -310,32 +330,32 @@ static struct publication *tipc_nameseq_insert_publ(struct name_seq *nseq,
310 if (!publ) 330 if (!publ)
311 return NULL; 331 return NULL;
312 332
313 sseq->zone_list_size++; 333 info->zone_list_size++;
314 if (!sseq->zone_list) 334 if (!info->zone_list)
315 sseq->zone_list = publ->zone_list_next = publ; 335 info->zone_list = publ->zone_list_next = publ;
316 else { 336 else {
317 publ->zone_list_next = sseq->zone_list->zone_list_next; 337 publ->zone_list_next = info->zone_list->zone_list_next;
318 sseq->zone_list->zone_list_next = publ; 338 info->zone_list->zone_list_next = publ;
319 } 339 }
320 340
321 if (in_own_cluster(node)) { 341 if (in_own_cluster(node)) {
322 sseq->cluster_list_size++; 342 info->cluster_list_size++;
323 if (!sseq->cluster_list) 343 if (!info->cluster_list)
324 sseq->cluster_list = publ->cluster_list_next = publ; 344 info->cluster_list = publ->cluster_list_next = publ;
325 else { 345 else {
326 publ->cluster_list_next = 346 publ->cluster_list_next =
327 sseq->cluster_list->cluster_list_next; 347 info->cluster_list->cluster_list_next;
328 sseq->cluster_list->cluster_list_next = publ; 348 info->cluster_list->cluster_list_next = publ;
329 } 349 }
330 } 350 }
331 351
332 if (node == tipc_own_addr) { 352 if (node == tipc_own_addr) {
333 sseq->node_list_size++; 353 info->node_list_size++;
334 if (!sseq->node_list) 354 if (!info->node_list)
335 sseq->node_list = publ->node_list_next = publ; 355 info->node_list = publ->node_list_next = publ;
336 else { 356 else {
337 publ->node_list_next = sseq->node_list->node_list_next; 357 publ->node_list_next = info->node_list->node_list_next;
338 sseq->node_list->node_list_next = publ; 358 info->node_list->node_list_next = publ;
339 } 359 }
340 } 360 }
341 361
@@ -373,6 +393,7 @@ static struct publication *tipc_nameseq_remove_publ(struct name_seq *nseq, u32 i
373 struct publication *curr; 393 struct publication *curr;
374 struct publication *prev; 394 struct publication *prev;
375 struct sub_seq *sseq = nameseq_find_subseq(nseq, inst); 395 struct sub_seq *sseq = nameseq_find_subseq(nseq, inst);
396 struct name_info *info;
376 struct sub_seq *free; 397 struct sub_seq *free;
377 struct subscription *s, *st; 398 struct subscription *s, *st;
378 int removed_subseq = 0; 399 int removed_subseq = 0;
@@ -380,40 +401,42 @@ static struct publication *tipc_nameseq_remove_publ(struct name_seq *nseq, u32 i
380 if (!sseq) 401 if (!sseq)
381 return NULL; 402 return NULL;
382 403
404 info = sseq->info;
405
383 /* Remove publication from zone scope list */ 406 /* Remove publication from zone scope list */
384 407
385 prev = sseq->zone_list; 408 prev = info->zone_list;
386 publ = sseq->zone_list->zone_list_next; 409 publ = info->zone_list->zone_list_next;
387 while ((publ->key != key) || (publ->ref != ref) || 410 while ((publ->key != key) || (publ->ref != ref) ||
388 (publ->node && (publ->node != node))) { 411 (publ->node && (publ->node != node))) {
389 prev = publ; 412 prev = publ;
390 publ = publ->zone_list_next; 413 publ = publ->zone_list_next;
391 if (prev == sseq->zone_list) { 414 if (prev == info->zone_list) {
392 415
393 /* Prevent endless loop if publication not found */ 416 /* Prevent endless loop if publication not found */
394 417
395 return NULL; 418 return NULL;
396 } 419 }
397 } 420 }
398 if (publ != sseq->zone_list) 421 if (publ != info->zone_list)
399 prev->zone_list_next = publ->zone_list_next; 422 prev->zone_list_next = publ->zone_list_next;
400 else if (publ->zone_list_next != publ) { 423 else if (publ->zone_list_next != publ) {
401 prev->zone_list_next = publ->zone_list_next; 424 prev->zone_list_next = publ->zone_list_next;
402 sseq->zone_list = publ->zone_list_next; 425 info->zone_list = publ->zone_list_next;
403 } else { 426 } else {
404 sseq->zone_list = NULL; 427 info->zone_list = NULL;
405 } 428 }
406 sseq->zone_list_size--; 429 info->zone_list_size--;
407 430
408 /* Remove publication from cluster scope list, if present */ 431 /* Remove publication from cluster scope list, if present */
409 432
410 if (in_own_cluster(node)) { 433 if (in_own_cluster(node)) {
411 prev = sseq->cluster_list; 434 prev = info->cluster_list;
412 curr = sseq->cluster_list->cluster_list_next; 435 curr = info->cluster_list->cluster_list_next;
413 while (curr != publ) { 436 while (curr != publ) {
414 prev = curr; 437 prev = curr;
415 curr = curr->cluster_list_next; 438 curr = curr->cluster_list_next;
416 if (prev == sseq->cluster_list) { 439 if (prev == info->cluster_list) {
417 440
418 /* Prevent endless loop for malformed list */ 441 /* Prevent endless loop for malformed list */
419 442
@@ -424,27 +447,27 @@ static struct publication *tipc_nameseq_remove_publ(struct name_seq *nseq, u32 i
424 goto end_cluster; 447 goto end_cluster;
425 } 448 }
426 } 449 }
427 if (publ != sseq->cluster_list) 450 if (publ != info->cluster_list)
428 prev->cluster_list_next = publ->cluster_list_next; 451 prev->cluster_list_next = publ->cluster_list_next;
429 else if (publ->cluster_list_next != publ) { 452 else if (publ->cluster_list_next != publ) {
430 prev->cluster_list_next = publ->cluster_list_next; 453 prev->cluster_list_next = publ->cluster_list_next;
431 sseq->cluster_list = publ->cluster_list_next; 454 info->cluster_list = publ->cluster_list_next;
432 } else { 455 } else {
433 sseq->cluster_list = NULL; 456 info->cluster_list = NULL;
434 } 457 }
435 sseq->cluster_list_size--; 458 info->cluster_list_size--;
436 } 459 }
437end_cluster: 460end_cluster:
438 461
439 /* Remove publication from node scope list, if present */ 462 /* Remove publication from node scope list, if present */
440 463
441 if (node == tipc_own_addr) { 464 if (node == tipc_own_addr) {
442 prev = sseq->node_list; 465 prev = info->node_list;
443 curr = sseq->node_list->node_list_next; 466 curr = info->node_list->node_list_next;
444 while (curr != publ) { 467 while (curr != publ) {
445 prev = curr; 468 prev = curr;
446 curr = curr->node_list_next; 469 curr = curr->node_list_next;
447 if (prev == sseq->node_list) { 470 if (prev == info->node_list) {
448 471
449 /* Prevent endless loop for malformed list */ 472 /* Prevent endless loop for malformed list */
450 473
@@ -455,21 +478,22 @@ end_cluster:
455 goto end_node; 478 goto end_node;
456 } 479 }
457 } 480 }
458 if (publ != sseq->node_list) 481 if (publ != info->node_list)
459 prev->node_list_next = publ->node_list_next; 482 prev->node_list_next = publ->node_list_next;
460 else if (publ->node_list_next != publ) { 483 else if (publ->node_list_next != publ) {
461 prev->node_list_next = publ->node_list_next; 484 prev->node_list_next = publ->node_list_next;
462 sseq->node_list = publ->node_list_next; 485 info->node_list = publ->node_list_next;
463 } else { 486 } else {
464 sseq->node_list = NULL; 487 info->node_list = NULL;
465 } 488 }
466 sseq->node_list_size--; 489 info->node_list_size--;
467 } 490 }
468end_node: 491end_node:
469 492
470 /* Contract subseq list if no more publications for that subseq */ 493 /* Contract subseq list if no more publications for that subseq */
471 494
472 if (!sseq->zone_list) { 495 if (!info->zone_list) {
496 kfree(info);
473 free = &nseq->sseqs[nseq->first_free--]; 497 free = &nseq->sseqs[nseq->first_free--];
474 memmove(sseq, sseq + 1, (free - (sseq + 1)) * sizeof(*sseq)); 498 memmove(sseq, sseq + 1, (free - (sseq + 1)) * sizeof(*sseq));
475 removed_subseq = 1; 499 removed_subseq = 1;
@@ -506,7 +530,7 @@ static void tipc_nameseq_subscribe(struct name_seq *nseq, struct subscription *s
506 return; 530 return;
507 531
508 while (sseq != &nseq->sseqs[nseq->first_free]) { 532 while (sseq != &nseq->sseqs[nseq->first_free]) {
509 struct publication *zl = sseq->zone_list; 533 struct publication *zl = sseq->info->zone_list;
510 if (zl && tipc_subscr_overlap(s, sseq->lower, sseq->upper)) { 534 if (zl && tipc_subscr_overlap(s, sseq->lower, sseq->upper)) {
511 struct publication *crs = zl; 535 struct publication *crs = zl;
512 int must_report = 1; 536 int must_report = 1;
@@ -591,6 +615,7 @@ struct publication *tipc_nametbl_remove_publ(u32 type, u32 lower,
591u32 tipc_nametbl_translate(u32 type, u32 instance, u32 *destnode) 615u32 tipc_nametbl_translate(u32 type, u32 instance, u32 *destnode)
592{ 616{
593 struct sub_seq *sseq; 617 struct sub_seq *sseq;
618 struct name_info *info;
594 struct publication *publ = NULL; 619 struct publication *publ = NULL;
595 struct name_seq *seq; 620 struct name_seq *seq;
596 u32 ref; 621 u32 ref;
@@ -606,12 +631,13 @@ u32 tipc_nametbl_translate(u32 type, u32 instance, u32 *destnode)
606 if (unlikely(!sseq)) 631 if (unlikely(!sseq))
607 goto not_found; 632 goto not_found;
608 spin_lock_bh(&seq->lock); 633 spin_lock_bh(&seq->lock);
634 info = sseq->info;
609 635
610 /* Closest-First Algorithm: */ 636 /* Closest-First Algorithm: */
611 if (likely(!*destnode)) { 637 if (likely(!*destnode)) {
612 publ = sseq->node_list; 638 publ = info->node_list;
613 if (publ) { 639 if (publ) {
614 sseq->node_list = publ->node_list_next; 640 info->node_list = publ->node_list_next;
615found: 641found:
616 ref = publ->ref; 642 ref = publ->ref;
617 *destnode = publ->node; 643 *destnode = publ->node;
@@ -619,35 +645,35 @@ found:
619 read_unlock_bh(&tipc_nametbl_lock); 645 read_unlock_bh(&tipc_nametbl_lock);
620 return ref; 646 return ref;
621 } 647 }
622 publ = sseq->cluster_list; 648 publ = info->cluster_list;
623 if (publ) { 649 if (publ) {
624 sseq->cluster_list = publ->cluster_list_next; 650 info->cluster_list = publ->cluster_list_next;
625 goto found; 651 goto found;
626 } 652 }
627 publ = sseq->zone_list; 653 publ = info->zone_list;
628 if (publ) { 654 if (publ) {
629 sseq->zone_list = publ->zone_list_next; 655 info->zone_list = publ->zone_list_next;
630 goto found; 656 goto found;
631 } 657 }
632 } 658 }
633 659
634 /* Round-Robin Algorithm: */ 660 /* Round-Robin Algorithm: */
635 else if (*destnode == tipc_own_addr) { 661 else if (*destnode == tipc_own_addr) {
636 publ = sseq->node_list; 662 publ = info->node_list;
637 if (publ) { 663 if (publ) {
638 sseq->node_list = publ->node_list_next; 664 info->node_list = publ->node_list_next;
639 goto found; 665 goto found;
640 } 666 }
641 } else if (in_own_cluster(*destnode)) { 667 } else if (in_own_cluster(*destnode)) {
642 publ = sseq->cluster_list; 668 publ = info->cluster_list;
643 if (publ) { 669 if (publ) {
644 sseq->cluster_list = publ->cluster_list_next; 670 info->cluster_list = publ->cluster_list_next;
645 goto found; 671 goto found;
646 } 672 }
647 } else { 673 } else {
648 publ = sseq->zone_list; 674 publ = info->zone_list;
649 if (publ) { 675 if (publ) {
650 sseq->zone_list = publ->zone_list_next; 676 info->zone_list = publ->zone_list_next;
651 goto found; 677 goto found;
652 } 678 }
653 } 679 }
@@ -676,6 +702,7 @@ int tipc_nametbl_mc_translate(u32 type, u32 lower, u32 upper, u32 limit,
676 struct name_seq *seq; 702 struct name_seq *seq;
677 struct sub_seq *sseq; 703 struct sub_seq *sseq;
678 struct sub_seq *sseq_stop; 704 struct sub_seq *sseq_stop;
705 struct name_info *info;
679 int res = 0; 706 int res = 0;
680 707
681 read_lock_bh(&tipc_nametbl_lock); 708 read_lock_bh(&tipc_nametbl_lock);
@@ -693,16 +720,17 @@ int tipc_nametbl_mc_translate(u32 type, u32 lower, u32 upper, u32 limit,
693 if (sseq->lower > upper) 720 if (sseq->lower > upper)
694 break; 721 break;
695 722
696 publ = sseq->node_list; 723 info = sseq->info;
724 publ = info->node_list;
697 if (publ) { 725 if (publ) {
698 do { 726 do {
699 if (publ->scope <= limit) 727 if (publ->scope <= limit)
700 tipc_port_list_add(dports, publ->ref); 728 tipc_port_list_add(dports, publ->ref);
701 publ = publ->node_list_next; 729 publ = publ->node_list_next;
702 } while (publ != sseq->node_list); 730 } while (publ != info->node_list);
703 } 731 }
704 732
705 if (sseq->cluster_list_size != sseq->node_list_size) 733 if (info->cluster_list_size != info->node_list_size)
706 res = 1; 734 res = 1;
707 } 735 }
708 736
@@ -840,7 +868,7 @@ static void subseq_list(struct sub_seq *sseq, struct print_buf *buf, u32 depth,
840{ 868{
841 char portIdStr[27]; 869 char portIdStr[27];
842 const char *scope_str[] = {"", " zone", " cluster", " node"}; 870 const char *scope_str[] = {"", " zone", " cluster", " node"};
843 struct publication *publ = sseq->zone_list; 871 struct publication *publ = sseq->info->zone_list;
844 872
845 tipc_printf(buf, "%-10u %-10u ", sseq->lower, sseq->upper); 873 tipc_printf(buf, "%-10u %-10u ", sseq->lower, sseq->upper);
846 874
@@ -860,7 +888,7 @@ static void subseq_list(struct sub_seq *sseq, struct print_buf *buf, u32 depth,
860 } 888 }
861 889
862 publ = publ->zone_list_next; 890 publ = publ->zone_list_next;
863 if (publ == sseq->zone_list) 891 if (publ == sseq->info->zone_list)
864 break; 892 break;
865 893
866 tipc_printf(buf, "\n%33s", " "); 894 tipc_printf(buf, "\n%33s", " ");