1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 /* 22 * Copyright 2006 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 */ 25 26 /* 27 * Routines for traversing and packing/unpacking the handle 28 * returned from ri_init. 29 */ 30 31 #include <stdlib.h> 32 #include <strings.h> 33 #include "rsrc_info.h" 34 #include "rsrc_info_impl.h" 35 36 static int ap_list_pack(ri_ap_t *, char **, size_t *, int); 37 static int ap_list_unpack(char *, size_t, ri_ap_t **); 38 static int ap_pack(ri_ap_t *, char **, size_t *, int); 39 static int ap_unpack(char *, size_t, ri_ap_t *); 40 static int dev_list_pack(ri_dev_t *, char **, size_t *, int); 41 static int dev_list_unpack(char *, size_t, ri_dev_t **); 42 static int dev_pack(ri_dev_t *, char **, size_t *, int); 43 static int dev_unpack(char *, size_t, ri_dev_t *); 44 static int client_list_pack(ri_client_t *, char **, size_t *, int); 45 static int client_list_unpack(char *, size_t, ri_client_t **); 46 static int client_pack(ri_client_t *, char **, size_t *, int); 47 static int client_unpack(char *, size_t, ri_client_t *); 48 static int pack_add_byte_array(nvlist_t *, char *, nvlist_t *, int); 49 static int lookup_unpack_byte_array(nvlist_t *, char *, nvlist_t **); 50 static void ri_ap_free(ri_ap_t *); 51 52 void 53 ri_fini(ri_hdl_t *hdl) 54 { 55 ri_ap_t *ap; 56 ri_client_t *client; 57 58 if (hdl == NULL) 59 return; 60 61 while ((ap = hdl->aps) != NULL) { 62 hdl->aps = ap->next; 63 ri_ap_free(ap); 64 } 65 while ((client = hdl->cpu_cap_clients) != NULL) { 66 hdl->cpu_cap_clients = client->next; 67 ri_client_free(client); 68 } 69 while ((client = hdl->mem_cap_clients) != NULL) { 70 hdl->mem_cap_clients = client->next; 71 ri_client_free(client); 72 } 73 free(hdl); 74 } 75 76 static void 77 ri_ap_free(ri_ap_t *ap) 78 { 79 ri_dev_t *dev; 80 81 assert(ap != NULL); 82 83 nvlist_free(ap->conf_props); 84 85 while ((dev = ap->cpus) != NULL) { 86 ap->cpus = dev->next; 87 ri_dev_free(dev); 88 } 89 while ((dev = ap->mems) != NULL) { 90 ap->mems = dev->next; 91 ri_dev_free(dev); 92 } 93 while ((dev = ap->ios) != NULL) { 94 ap->ios = dev->next; 95 ri_dev_free(dev); 96 } 97 free(ap); 98 } 99 100 void 101 ri_dev_free(ri_dev_t *dev) 102 { 103 ri_client_t *client; 104 105 assert(dev != NULL); 106 107 nvlist_free(dev->conf_props); 108 while ((client = dev->rcm_clients) != NULL) { 109 dev->rcm_clients = client->next; 110 ri_client_free(client); 111 } 112 free(dev); 113 } 114 115 void 116 ri_client_free(ri_client_t *client) 117 { 118 assert(client != NULL); 119 120 nvlist_free(client->usg_props); 121 nvlist_free(client->v_props); 122 free(client); 123 } 124 125 /* 126 * Pack everything contained in the handle up inside out. 127 */ 128 int 129 ri_pack(ri_hdl_t *hdl, caddr_t *bufp, size_t *sizep, int encoding) 130 { 131 nvlist_t *nvl = NULL; 132 char *buf = NULL; 133 size_t size = 0; 134 135 if (bufp == NULL || sizep == NULL) 136 return (RI_INVAL); 137 138 *sizep = 0; 139 *bufp = NULL; 140 141 /* 142 * Check the handle. If it is NULL, there 143 * is nothing to pack, so we are done. 144 */ 145 if (hdl == NULL) { 146 return (RI_SUCCESS); 147 } 148 149 if (nvlist_alloc(&nvl, NV_UNIQUE_NAME, 0) != 0) { 150 dprintf((stderr, "nvlist_alloc fail\n", errno)); 151 goto fail; 152 } 153 154 if (nvlist_add_int32(nvl, RI_HDL_FLAGS, hdl->flags) != 0) { 155 dprintf((stderr, "nvlist_add_int32 fail\n")); 156 goto fail; 157 } 158 159 if (ap_list_pack(hdl->aps, &buf, &size, encoding) != 0 || 160 nvlist_add_byte_array(nvl, RI_HDL_APS, (uchar_t *)buf, size) != 0) { 161 goto fail; 162 } 163 164 s_free(buf); 165 if (client_list_pack(hdl->cpu_cap_clients, &buf, &size, 166 encoding) != 0 || 167 nvlist_add_byte_array(nvl, RI_HDL_CPU_CAPS, (uchar_t *)buf, 168 size) != 0) { 169 goto fail; 170 } 171 172 s_free(buf); 173 if (client_list_pack(hdl->mem_cap_clients, &buf, &size, 174 encoding) != 0 || 175 nvlist_add_byte_array(nvl, RI_HDL_MEM_CAPS, (uchar_t *)buf, 176 size) != 0) { 177 goto fail; 178 } 179 180 s_free(buf); 181 if (nvlist_pack(nvl, &buf, &size, encoding, 0) != 0) { 182 dprintf((stderr, "nvlist_pack fail\n")); 183 goto fail; 184 } 185 186 nvlist_free(nvl); 187 *bufp = buf; 188 *sizep = size; 189 190 return (RI_SUCCESS); 191 192 fail: 193 s_free(buf); 194 nvlist_free(nvl); 195 196 return (RI_FAILURE); 197 } 198 199 /* 200 * Pack a list of attachment point handles. 201 */ 202 static int 203 ap_list_pack(ri_ap_t *aplist, char **bufp, size_t *sizep, int encoding) 204 { 205 nvlist_t *nvl = NULL; 206 char *buf = NULL; 207 size_t size; 208 209 assert(bufp != NULL && sizep != NULL); 210 211 *sizep = 0; 212 *bufp = NULL; 213 214 if (nvlist_alloc(&nvl, 0, 0) != 0) { 215 dprintf((stderr, "nvlist_alloc fail\n")); 216 return (-1); 217 } 218 219 while (aplist != NULL) { 220 s_free(buf); 221 if (ap_pack(aplist, &buf, &size, encoding) != 0) 222 goto fail; 223 224 if (nvlist_add_byte_array(nvl, RI_AP_T, (uchar_t *)buf, 225 size) != 0) { 226 dprintf((stderr, "nvlist_add_byte_array fail " 227 "(%s)\n", RI_AP_T)); 228 goto fail; 229 } 230 aplist = aplist->next; 231 } 232 233 s_free(buf); 234 if (nvlist_pack(nvl, &buf, &size, encoding, 0) != 0) { 235 dprintf((stderr, "nvlist_pack fail\n")); 236 goto fail; 237 } 238 239 nvlist_free(nvl); 240 *bufp = buf; 241 *sizep = size; 242 243 return (0); 244 245 fail: 246 s_free(buf); 247 nvlist_free(nvl); 248 249 return (-1); 250 } 251 252 /* 253 * Pack a list of ri_dev_t's. 254 */ 255 static int 256 dev_list_pack(ri_dev_t *devlist, char **bufp, size_t *sizep, int encoding) 257 { 258 nvlist_t *nvl = NULL; 259 char *buf = NULL; 260 size_t size = 0; 261 262 assert(bufp != NULL && sizep != NULL); 263 264 *sizep = 0; 265 *bufp = NULL; 266 267 if (nvlist_alloc(&nvl, 0, 0) != 0) { 268 dprintf((stderr, "nvlist_alloc fail\n")); 269 return (-1); 270 } 271 272 while (devlist != NULL) { 273 s_free(buf); 274 if (dev_pack(devlist, &buf, &size, encoding) != 0) 275 goto fail; 276 277 if (nvlist_add_byte_array(nvl, RI_DEV_T, (uchar_t *)buf, 278 size) != 0) { 279 dprintf((stderr, "nvlist_add_byte_array fail " 280 "(%s)\n", RI_DEV_T)); 281 goto fail; 282 } 283 devlist = devlist->next; 284 } 285 286 s_free(buf); 287 if (nvlist_pack(nvl, &buf, &size, encoding, 0) != 0) { 288 dprintf((stderr, "nvlist_pack fail\n")); 289 goto fail; 290 } 291 292 nvlist_free(nvl); 293 *bufp = buf; 294 *sizep = size; 295 296 return (0); 297 298 fail: 299 s_free(buf); 300 nvlist_free(nvl); 301 302 return (-1); 303 } 304 305 /* 306 * Pack a list of ri_client_t's. 307 */ 308 static int 309 client_list_pack(ri_client_t *client_list, char **bufp, size_t *sizep, 310 int encoding) 311 { 312 nvlist_t *nvl = NULL; 313 char *buf = NULL; 314 size_t size = 0; 315 316 assert(bufp != NULL && sizep != NULL); 317 318 *sizep = 0; 319 *bufp = NULL; 320 321 if (nvlist_alloc(&nvl, 0, 0) != 0) { 322 dprintf((stderr, "nvlist_alloc fail\n")); 323 return (-1); 324 } 325 326 while (client_list != NULL) { 327 s_free(buf); 328 if (client_pack(client_list, &buf, &size, encoding) != 0) 329 goto fail; 330 331 if (nvlist_add_byte_array(nvl, RI_CLIENT_T, (uchar_t *)buf, 332 size) != 0) { 333 dprintf((stderr, "nvlist_add_byte_array fail " 334 "(%s)\n", RI_CLIENT_T)); 335 goto fail; 336 } 337 client_list = client_list->next; 338 } 339 340 s_free(buf); 341 if (nvlist_pack(nvl, &buf, &size, encoding, 0) != 0) { 342 dprintf((stderr, "nvlist_pack fail\n")); 343 goto fail; 344 } 345 346 nvlist_free(nvl); 347 *bufp = buf; 348 *sizep = size; 349 350 return (0); 351 352 fail: 353 s_free(buf); 354 nvlist_free(nvl); 355 356 return (-1); 357 } 358 359 static int 360 ap_pack(ri_ap_t *ap, char **bufp, size_t *sizep, int encoding) 361 { 362 nvlist_t *nvl = NULL; 363 char *buf = NULL; 364 size_t size = 0; 365 366 if (nvlist_alloc(&nvl, NV_UNIQUE_NAME, 0) != 0) { 367 dprintf((stderr, "nvlist_alloc fail\n")); 368 return (-1); 369 } 370 371 if (pack_add_byte_array(ap->conf_props, RI_AP_PROPS, nvl, 372 encoding) != 0) 373 goto fail; 374 375 if (dev_list_pack(ap->cpus, &buf, &size, encoding) != 0) 376 goto fail; 377 378 if (nvlist_add_byte_array(nvl, RI_AP_CPUS, (uchar_t *)buf, 379 size) != 0) { 380 dprintf((stderr, "nvlist_add_byte_array (%s)\n", RI_AP_CPUS)); 381 goto fail; 382 } 383 384 s_free(buf); 385 if (dev_list_pack(ap->mems, &buf, &size, encoding) != 0) 386 goto fail; 387 388 if (nvlist_add_byte_array(nvl, RI_AP_MEMS, (uchar_t *)buf, 389 size) != 0) { 390 dprintf((stderr, "nvlist_add_byte_array (%s)n", RI_AP_MEMS)); 391 goto fail; 392 } 393 394 s_free(buf); 395 if (dev_list_pack(ap->ios, &buf, &size, encoding) != 0) 396 goto fail; 397 398 if (nvlist_add_byte_array(nvl, RI_AP_IOS, (uchar_t *)buf, 399 size) != 0) { 400 dprintf((stderr, "nvlist_add_byte_array (%s)n", RI_AP_IOS)); 401 goto fail; 402 } 403 404 s_free(buf); 405 if (nvlist_pack(nvl, &buf, &size, encoding, 0) != 0) { 406 dprintf((stderr, "nvlist_pack fail\n")); 407 goto fail; 408 } 409 410 nvlist_free(nvl); 411 *bufp = buf; 412 *sizep = size; 413 414 return (0); 415 416 fail: 417 s_free(buf); 418 nvlist_free(nvl); 419 420 return (-1); 421 } 422 423 static int 424 dev_pack(ri_dev_t *dev, char **bufp, size_t *sizep, int encoding) 425 { 426 nvlist_t *nvl = NULL; 427 char *buf = NULL; 428 size_t size = 0; 429 430 if (nvlist_alloc(&nvl, NV_UNIQUE_NAME, 0) != 0) { 431 dprintf((stderr, "nvlist_alloc fail\n")); 432 return (-1); 433 } 434 435 if (pack_add_byte_array(dev->conf_props, RI_DEV_PROPS, nvl, 436 encoding) != 0) 437 goto fail; 438 439 if (client_list_pack(dev->rcm_clients, &buf, &size, encoding) != 0) 440 goto fail; 441 442 if (nvlist_add_byte_array(nvl, RI_DEV_CLIENTS, (uchar_t *)buf, 443 size) != 0) { 444 dprintf((stderr, "nvlist_add_byte_array (%s)n", 445 RI_DEV_CLIENTS)); 446 goto fail; 447 } 448 449 s_free(buf); 450 if (nvlist_pack(nvl, &buf, &size, encoding, 0) != 0) { 451 dprintf((stderr, "nvlist_pack fail\n")); 452 goto fail; 453 } 454 455 nvlist_free(nvl); 456 *bufp = buf; 457 *sizep = size; 458 459 return (0); 460 461 fail: 462 s_free(buf); 463 nvlist_free(nvl); 464 465 return (-1); 466 } 467 468 static int 469 client_pack(ri_client_t *client, char **bufp, size_t *sizep, int encoding) 470 { 471 nvlist_t *nvl = NULL; 472 char *buf = NULL; 473 size_t size = 0; 474 475 if (nvlist_alloc(&nvl, NV_UNIQUE_NAME, 0) != 0) { 476 dprintf((stderr, "nvlist_alloc fail\n")); 477 return (-1); 478 } 479 480 if (pack_add_byte_array(client->usg_props, RI_CLIENT_USAGE_PROPS, 481 nvl, encoding) != 0) { 482 goto fail; 483 } 484 485 /* 486 * This will only be present if RI_VERBOSE was specified 487 * in the call to ri_init. 488 */ 489 if (client->v_props != NULL && pack_add_byte_array(client->v_props, 490 RI_CLIENT_VERB_PROPS, nvl, encoding) != 0) { 491 goto fail; 492 } 493 494 if (nvlist_pack(nvl, &buf, &size, encoding, 0) != 0) { 495 dprintf((stderr, "nvlist_pack fail\n")); 496 goto fail; 497 } 498 499 nvlist_free(nvl); 500 *bufp = buf; 501 *sizep = size; 502 503 return (0); 504 505 fail: 506 s_free(buf); 507 nvlist_free(nvl); 508 509 return (-1); 510 } 511 512 /* 513 * Pack nvlist_t and add as byte array to another nvlist_t. 514 */ 515 static int 516 pack_add_byte_array(nvlist_t *nvl_packme, char *name, nvlist_t *nvl, 517 int encoding) 518 { 519 char *buf = NULL; 520 size_t size = 0; 521 522 if (nvlist_pack(nvl_packme, &buf, &size, encoding, 0) != 0) { 523 dprintf((stderr, "nvlist_pack fail (%s)\n", name)); 524 s_free(buf); 525 return (-1); 526 } 527 528 if (nvlist_add_byte_array(nvl, name, (uchar_t *)buf, size) != 0) { 529 dprintf((stderr, "nvlist_add_byte_array fail (%s)\n", name)); 530 return (-1); 531 } 532 533 s_free(buf); 534 return (0); 535 } 536 537 /* 538 * Unpack buf into ri_hdl_t. 539 */ 540 int 541 ri_unpack(caddr_t buf, size_t size, ri_hdl_t **hdlp) 542 { 543 ri_hdl_t *ri_hdl = NULL; 544 nvlist_t *nvl = NULL; 545 546 if (hdlp == NULL) 547 return (RI_INVAL); 548 549 *hdlp = NULL; 550 if ((ri_hdl = calloc(1, sizeof (*ri_hdl))) == NULL) { 551 dprintf((stderr, "calloc: %s\n", strerror(errno))); 552 return (RI_FAILURE); 553 } 554 555 if (nvlist_unpack(buf, size, &nvl, 0) != 0) { 556 dprintf((stderr, "nvlist_unpack fail\n")); 557 goto fail; 558 } 559 560 if (nvlist_lookup_int32(nvl, RI_HDL_FLAGS, &ri_hdl->flags) != 0) { 561 dprintf((stderr, "nvlist_lookup_int32 fail (%s)\n", 562 RI_HDL_FLAGS)); 563 goto fail; 564 } 565 566 buf = NULL; 567 size = 0; 568 if (nvlist_lookup_byte_array(nvl, RI_HDL_APS, (uchar_t **)&buf, 569 (uint_t *)&size) != 0) { 570 dprintf((stderr, "nvlist_lookup_int32 fail (%s)\n", 571 RI_HDL_APS)); 572 goto fail; 573 } 574 575 if (ap_list_unpack(buf, size, &ri_hdl->aps) != 0) 576 goto fail; 577 578 buf = NULL; 579 size = 0; 580 if (nvlist_lookup_byte_array(nvl, RI_HDL_CPU_CAPS, (uchar_t **)&buf, 581 (uint_t *)&size) != 0) { 582 dprintf((stderr, "nvlist_lookup_byte_array fail (%s)\n", 583 RI_HDL_CPU_CAPS)); 584 goto fail; 585 } 586 587 if (client_list_unpack(buf, size, &ri_hdl->cpu_cap_clients) != 0) 588 goto fail; 589 590 buf = NULL; 591 size = 0; 592 if (nvlist_lookup_byte_array(nvl, RI_HDL_MEM_CAPS, (uchar_t **)&buf, 593 (uint_t *)&size) != 0) { 594 dprintf((stderr, "nvlist_lookup_byte_array fail (%s)\n", 595 RI_HDL_MEM_CAPS)); 596 goto fail; 597 } 598 599 if (client_list_unpack(buf, size, &ri_hdl->mem_cap_clients) != 0) 600 goto fail; 601 602 *hdlp = ri_hdl; 603 604 return (0); 605 606 fail: 607 free(ri_hdl); 608 nvlist_free(nvl); 609 610 return (-1); 611 } 612 613 static int 614 ap_list_unpack(char *buf, size_t size, ri_ap_t **aps) 615 { 616 nvpair_t *nvp = NULL; 617 nvlist_t *nvl; 618 ri_ap_t *aplist = NULL; 619 ri_ap_t *prev = NULL; 620 ri_ap_t *tmp = NULL; 621 622 if (nvlist_unpack(buf, size, &nvl, 0) != 0) { 623 dprintf((stderr, "nvlist_unpack fail\n")); 624 return (-1); 625 } 626 627 while ((nvp = nvlist_next_nvpair(nvl, nvp)) != NULL) { 628 assert(strcmp(nvpair_name(nvp), RI_AP_T) == 0 && 629 nvpair_type(nvp) == DATA_TYPE_BYTE_ARRAY); 630 631 if ((tmp = calloc(1, sizeof (*tmp))) == NULL) { 632 dprintf((stderr, "calloc: %s\n", strerror(errno))); 633 goto fail; 634 } 635 636 buf = NULL; 637 size = 0; 638 if (nvpair_value_byte_array(nvp, (uchar_t **)&buf, 639 (uint_t *)&size) != 0) { 640 dprintf((stderr, "nvpair_value_byte_array fail\n")); 641 goto fail; 642 } 643 644 if (ap_unpack(buf, size, tmp) != 0) 645 goto fail; 646 647 if (aplist == NULL) { 648 prev = aplist = tmp; 649 } else { 650 prev->next = tmp; 651 prev = tmp; 652 } 653 } 654 655 nvlist_free(nvl); 656 *aps = aplist; 657 658 return (0); 659 660 fail: 661 nvlist_free(nvl); 662 if (aplist != NULL) { 663 while ((tmp = aplist) != NULL) { 664 aplist = aplist->next; 665 ri_ap_free(tmp); 666 } 667 } 668 669 return (-1); 670 } 671 672 static int 673 dev_list_unpack(char *buf, size_t size, ri_dev_t **devs) 674 { 675 nvpair_t *nvp = NULL; 676 nvlist_t *nvl; 677 ri_dev_t *devlist = NULL; 678 ri_dev_t *prev = NULL; 679 ri_dev_t *tmp = NULL; 680 681 if (nvlist_unpack(buf, size, &nvl, 0) != 0) { 682 dprintf((stderr, "nvlist_unpack fail\n")); 683 return (-1); 684 } 685 686 while ((nvp = nvlist_next_nvpair(nvl, nvp)) != NULL) { 687 assert(strcmp(nvpair_name(nvp), RI_DEV_T) == 0 && 688 nvpair_type(nvp) == DATA_TYPE_BYTE_ARRAY); 689 690 if ((tmp = calloc(1, sizeof (*tmp))) == NULL) { 691 dprintf((stderr, "calloc: %s\n", strerror(errno))); 692 goto fail; 693 } 694 695 if (nvpair_value_byte_array(nvp, (uchar_t **)&buf, 696 (uint_t *)&size) != 0) { 697 dprintf((stderr, "nvpair_value_byte_array fail\n")); 698 goto fail; 699 } 700 701 if (dev_unpack(buf, size, tmp) != 0) 702 goto fail; 703 704 if (devlist == NULL) { 705 prev = devlist = tmp; 706 } else { 707 prev->next = tmp; 708 prev = tmp; 709 } 710 } 711 712 nvlist_free(nvl); 713 *devs = devlist; 714 715 return (0); 716 717 fail: 718 nvlist_free(nvl); 719 if (devlist != NULL) { 720 while ((tmp = devlist) != NULL) { 721 devlist = devlist->next; 722 ri_dev_free(tmp); 723 } 724 } 725 726 return (-1); 727 } 728 729 static int 730 client_list_unpack(char *buf, size_t size, ri_client_t **clients) 731 { 732 nvpair_t *nvp = NULL; 733 nvlist_t *nvl; 734 ri_client_t *client_list = NULL; 735 ri_client_t *prev = NULL; 736 ri_client_t *tmp = NULL; 737 738 if (nvlist_unpack(buf, size, &nvl, 0) != 0) { 739 dprintf((stderr, "nvlist_unpack fail\n")); 740 return (-1); 741 } 742 743 while ((nvp = nvlist_next_nvpair(nvl, nvp)) != NULL) { 744 assert(strcmp(nvpair_name(nvp), RI_CLIENT_T) == 0); 745 assert(nvpair_type(nvp) == DATA_TYPE_BYTE_ARRAY); 746 747 if ((tmp = calloc(1, sizeof (*tmp))) == NULL) { 748 dprintf((stderr, "calloc: %s\n", strerror(errno))); 749 goto fail; 750 } 751 752 buf = NULL; 753 size = 0; 754 if (nvpair_value_byte_array(nvp, (uchar_t **)&buf, 755 (uint_t *)&size) != 0) { 756 dprintf((stderr, "nvpair_value_byte_array fail\n")); 757 goto fail; 758 } 759 760 if (client_unpack(buf, size, tmp) != 0) 761 goto fail; 762 763 if (client_list == NULL) { 764 prev = client_list = tmp; 765 } else { 766 prev->next = tmp; 767 prev = tmp; 768 } 769 } 770 771 nvlist_free(nvl); 772 *clients = client_list; 773 774 return (0); 775 776 fail: 777 nvlist_free(nvl); 778 if (client_list != NULL) { 779 while ((tmp = client_list) != NULL) { 780 client_list = client_list->next; 781 ri_client_free(tmp); 782 } 783 } 784 785 return (-1); 786 } 787 788 static int 789 client_unpack(char *buf, size_t size, ri_client_t *client) 790 { 791 nvlist_t *nvl; 792 793 if (nvlist_unpack(buf, size, &nvl, 0) != 0) { 794 dprintf((stderr, "nvlist_unpack fail\n")); 795 return (-1); 796 } 797 798 if (lookup_unpack_byte_array(nvl, RI_CLIENT_USAGE_PROPS, 799 &client->usg_props) != 0) { 800 nvlist_free(nvl); 801 return (-1); 802 } 803 804 #ifdef DEBUG 805 nvlist_print(stderr, client->usg_props); 806 #endif /* DEBUG */ 807 808 /* 809 * Verbose properties for RCM clients only present if 810 * RI_VERBOSE was specified for ri_init. 811 */ 812 buf = NULL; 813 size = 0; 814 if (nvlist_lookup_byte_array(nvl, RI_CLIENT_VERB_PROPS, 815 (uchar_t **)&buf, (uint_t *)&size) == 0) { 816 if (nvlist_unpack(buf, size, &client->v_props, 0) != 0) { 817 dprintf((stderr, "nvlist_unpack fail (%s)\n", 818 RI_CLIENT_VERB_PROPS)); 819 nvlist_free(nvl); 820 return (-1); 821 } 822 } 823 824 nvlist_free(nvl); 825 826 return (0); 827 } 828 829 static int 830 dev_unpack(char *buf, size_t size, ri_dev_t *dev) 831 { 832 nvlist_t *nvl; 833 834 if (nvlist_unpack(buf, size, &nvl, 0) != 0) { 835 dprintf((stderr, "nvlist_unpack fail\n")); 836 return (-1); 837 } 838 839 if (lookup_unpack_byte_array(nvl, RI_DEV_PROPS, 840 &dev->conf_props) != 0) { 841 nvlist_free(nvl); 842 return (-1); 843 } 844 845 #ifdef DEBUG 846 nvlist_print(stderr, dev->conf_props); 847 #endif /* DEBUG */ 848 849 if (nvlist_lookup_byte_array(nvl, RI_DEV_CLIENTS, (uchar_t **)&buf, 850 (uint_t *)&size) != 0) { 851 dprintf((stderr, "nvlist_lookup_byte_array fail (%s)\n", 852 RI_DEV_CLIENTS)); 853 nvlist_free(nvl); 854 return (-1); 855 } 856 857 if (client_list_unpack(buf, size, &dev->rcm_clients) != 0) { 858 nvlist_free(nvl); 859 return (-1); 860 } 861 862 nvlist_free(nvl); 863 864 return (0); 865 } 866 867 static int 868 ap_unpack(char *buf, size_t size, ri_ap_t *ap) 869 { 870 nvlist_t *nvl; 871 872 if (nvlist_unpack(buf, size, &nvl, 0) != 0) { 873 dprintf((stderr, "nvlist_unpack fail\n")); 874 return (-1); 875 } 876 877 if (lookup_unpack_byte_array(nvl, RI_AP_PROPS, &ap->conf_props) != 0) { 878 nvlist_free(nvl); 879 return (-1); 880 } 881 882 #ifdef DEBUG 883 nvlist_print(stderr, ap->conf_props); 884 #endif /* DEBUG */ 885 886 if (nvlist_lookup_byte_array(nvl, RI_AP_CPUS, (uchar_t **)&buf, 887 (uint_t *)&size) != 0) { 888 dprintf((stderr, "nvlist_lookup_byte_array fail (%s)\n", 889 RI_AP_CPUS)); 890 nvlist_free(nvl); 891 return (-1); 892 } 893 894 if (dev_list_unpack(buf, size, &ap->cpus) != 0) { 895 nvlist_free(nvl); 896 return (-1); 897 } 898 899 if (nvlist_lookup_byte_array(nvl, RI_AP_MEMS, (uchar_t **)&buf, 900 (uint_t *)&size) != 0) { 901 dprintf((stderr, "nvlist_lookup_byte_array fail (%s)\n", 902 RI_AP_MEMS)); 903 nvlist_free(nvl); 904 return (-1); 905 } 906 907 if (dev_list_unpack(buf, size, &ap->mems) != 0) { 908 nvlist_free(nvl); 909 return (-1); 910 } 911 912 if (nvlist_lookup_byte_array(nvl, RI_AP_IOS, (uchar_t **)&buf, 913 (uint_t *)&size) != 0) { 914 dprintf((stderr, "nvlist_lookup_byte_array fail (%s)\n", 915 RI_AP_IOS)); 916 nvlist_free(nvl); 917 return (-1); 918 } 919 920 if (dev_list_unpack(buf, size, &ap->ios) != 0) { 921 nvlist_free(nvl); 922 return (-1); 923 } 924 925 nvlist_free(nvl); 926 927 return (0); 928 } 929 930 /* 931 * Lookup byte array in old nvlist_t and unpack into new nvlist_t. 932 */ 933 static int 934 lookup_unpack_byte_array(nvlist_t *old_nvl, char *name, nvlist_t **new_nvl) 935 { 936 char *buf = NULL; 937 size_t size = 0; 938 939 if (nvlist_lookup_byte_array(old_nvl, name, (uchar_t **)&buf, 940 (uint_t *)&size) != 0) { 941 dprintf((stderr, "nvlist_lookup_byte_array fail (%s)\n", 942 name)); 943 return (-1); 944 } 945 946 if (nvlist_unpack(buf, size, new_nvl, 0) != 0) { 947 dprintf((stderr, "nvlist_unpack fail (%s)\n", name)); 948 return (-1); 949 } 950 951 return (0); 952 } 953 954 ri_ap_t * 955 ri_ap_next(ri_hdl_t *hdl, ri_ap_t *ap) 956 { 957 if (hdl == NULL) { 958 errno = EINVAL; 959 return (NULL); 960 } 961 return ((ap == NULL) ? hdl->aps : ap->next); 962 } 963 964 nvlist_t * 965 ri_ap_conf_props(ri_ap_t *ap) 966 { 967 if (ap == NULL) { 968 errno = EINVAL; 969 return (NULL); 970 } 971 return (ap->conf_props); 972 } 973 974 ri_dev_t * 975 ri_cpu_next(ri_ap_t *ap, ri_dev_t *cpu) 976 { 977 if (ap == NULL) { 978 errno = EINVAL; 979 return (NULL); 980 } 981 return ((cpu == NULL) ? ap->cpus : cpu->next); 982 } 983 984 ri_dev_t * 985 ri_mem_next(ri_ap_t *ap, ri_dev_t *mem) 986 { 987 if (ap == NULL) { 988 errno = EINVAL; 989 return (NULL); 990 } 991 return ((mem == NULL) ? ap->mems : mem->next); 992 } 993 994 ri_dev_t * 995 ri_io_next(ri_ap_t *ap, ri_dev_t *io) 996 { 997 if (ap == NULL) { 998 errno = EINVAL; 999 return (NULL); 1000 } 1001 return ((io == NULL) ? ap->ios : io->next); 1002 } 1003 1004 ri_client_t * 1005 ri_client_next(ri_dev_t *dev, ri_client_t *rcm_client) 1006 { 1007 if (dev == NULL) { 1008 errno = EINVAL; 1009 return (NULL); 1010 } 1011 return ((rcm_client == NULL) ? dev->rcm_clients : rcm_client->next); 1012 } 1013 1014 nvlist_t * 1015 ri_dev_conf_props(ri_dev_t *dev) 1016 { 1017 if (dev == NULL) { 1018 errno = EINVAL; 1019 return (NULL); 1020 } 1021 return (dev->conf_props); 1022 } 1023 1024 nvlist_t * 1025 ri_client_usage_props(ri_client_t *rcm_client) 1026 { 1027 if (rcm_client == NULL) { 1028 errno = EINVAL; 1029 return (NULL); 1030 } 1031 return (rcm_client->usg_props); 1032 } 1033 1034 nvlist_t * 1035 ri_client_verbose_props(ri_client_t *rcm_client) 1036 { 1037 if (rcm_client == NULL) { 1038 errno = EINVAL; 1039 return (NULL); 1040 } 1041 return (rcm_client->v_props); 1042 } 1043 1044 ri_client_t * 1045 ri_cpu_cap_client_next(ri_hdl_t *hdl, ri_client_t *rcm_client) 1046 { 1047 if (hdl == NULL) { 1048 errno = EINVAL; 1049 return (NULL); 1050 } 1051 return ((rcm_client == NULL) ? hdl->cpu_cap_clients : rcm_client->next); 1052 } 1053 1054 ri_client_t * 1055 ri_mem_cap_client_next(ri_hdl_t *hdl, ri_client_t *rcm_client) 1056 { 1057 if (hdl == NULL) { 1058 errno = EINVAL; 1059 return (NULL); 1060 } 1061 return ((rcm_client == NULL) ? hdl->mem_cap_clients : rcm_client->next); 1062 } 1063