1/* omapi.c 2 3 OMAPI object interfaces for the DHCP server. */ 4 5/* 6 * Copyright (c) 2004 by Internet Systems Consortium, Inc. ("ISC") 7 * Copyright (c) 1999-2003 by Internet Software Consortium 8 * 9 * Permission to use, copy, modify, and distribute this software for any 10 * purpose with or without fee is hereby granted, provided that the above 11 * copyright notice and this permission notice appear in all copies. 12 * 13 * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES 14 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 15 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR 16 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 17 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 18 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT 19 * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 20 * 21 * Internet Systems Consortium, Inc. 22 * 950 Charter Street 23 * Redwood City, CA 94063 24 * <info@isc.org> 25 * http://www.isc.org/ 26 * 27 * This software has been written for Internet Systems Consortium 28 * by Ted Lemon in cooperation with Vixie Enterprises and Nominum, Inc. 29 * To learn more about Internet Systems Consortium, see 30 * ``http://www.isc.org/''. To learn more about Vixie Enterprises, 31 * see ``http://www.vix.com''. To learn more about Nominum, Inc., see 32 * ``http://www.nominum.com''. 33 */ 34 35/* Many, many thanks to Brian Murrell and BCtel for this code - BCtel 36 provided the funding that resulted in this code and the entire 37 OMAPI support library being written, and Brian helped brainstorm 38 and refine the requirements. To the extent that this code is 39 useful, you have Brian and BCtel to thank. Any limitations in the 40 code are a result of mistakes on my part. -- Ted Lemon */ 41 42#ifndef lint 43static char copyright[] = 44"$Id: comapi.c,v 1.6 2005/08/11 17:13:21 drochner Exp $ Copyright (c) 2004 Internet Systems Consortium. All rights reserved.\n"; 45#endif /* not lint */ 46 47#include "dhcpd.h" 48#include <omapip/omapip_p.h> 49 50OMAPI_OBJECT_ALLOC (subnet, struct subnet, dhcp_type_subnet) 51OMAPI_OBJECT_ALLOC (shared_network, struct shared_network, 52 dhcp_type_shared_network) 53OMAPI_OBJECT_ALLOC (group_object, struct group_object, dhcp_type_group) 54OMAPI_OBJECT_ALLOC (dhcp_control, dhcp_control_object_t, dhcp_type_control) 55 56omapi_object_type_t *dhcp_type_interface; 57omapi_object_type_t *dhcp_type_group; 58omapi_object_type_t *dhcp_type_shared_network; 59omapi_object_type_t *dhcp_type_subnet; 60omapi_object_type_t *dhcp_type_control; 61dhcp_control_object_t *dhcp_control_object; 62 63void dhcp_common_objects_setup () 64{ 65 isc_result_t status; 66 67 status = omapi_object_type_register (&dhcp_type_control, 68 "control", 69 dhcp_control_set_value, 70 dhcp_control_get_value, 71 dhcp_control_destroy, 72 dhcp_control_signal_handler, 73 dhcp_control_stuff_values, 74 dhcp_control_lookup, 75 dhcp_control_create, 76 dhcp_control_remove, 0, 0, 0, 77 sizeof (dhcp_control_object_t), 78 0, RC_MISC); 79 if (status != ISC_R_SUCCESS) 80 log_fatal ("Can't register control object type: %s", 81 isc_result_totext (status)); 82 status = dhcp_control_allocate (&dhcp_control_object, MDL); 83 if (status != ISC_R_SUCCESS) 84 log_fatal ("Can't make initial control object: %s", 85 isc_result_totext (status)); 86 dhcp_control_object -> state = server_startup; 87 88 status = omapi_object_type_register (&dhcp_type_group, 89 "group", 90 dhcp_group_set_value, 91 dhcp_group_get_value, 92 dhcp_group_destroy, 93 dhcp_group_signal_handler, 94 dhcp_group_stuff_values, 95 dhcp_group_lookup, 96 dhcp_group_create, 97 dhcp_group_remove, 0, 0, 0, 98 sizeof (struct group_object), 0, 99 RC_MISC); 100 if (status != ISC_R_SUCCESS) 101 log_fatal ("Can't register group object type: %s", 102 isc_result_totext (status)); 103 104 status = omapi_object_type_register (&dhcp_type_subnet, 105 "subnet", 106 dhcp_subnet_set_value, 107 dhcp_subnet_get_value, 108 dhcp_subnet_destroy, 109 dhcp_subnet_signal_handler, 110 dhcp_subnet_stuff_values, 111 dhcp_subnet_lookup, 112 dhcp_subnet_create, 113 dhcp_subnet_remove, 0, 0, 0, 114 sizeof (struct subnet), 0, 115 RC_MISC); 116 if (status != ISC_R_SUCCESS) 117 log_fatal ("Can't register subnet object type: %s", 118 isc_result_totext (status)); 119 120 status = omapi_object_type_register 121 (&dhcp_type_shared_network, 122 "shared-network", 123 dhcp_shared_network_set_value, 124 dhcp_shared_network_get_value, 125 dhcp_shared_network_destroy, 126 dhcp_shared_network_signal_handler, 127 dhcp_shared_network_stuff_values, 128 dhcp_shared_network_lookup, 129 dhcp_shared_network_create, 130 dhcp_shared_network_remove, 0, 0, 0, 131 sizeof (struct shared_network), 0, RC_MISC); 132 if (status != ISC_R_SUCCESS) 133 log_fatal ("Can't register shared network object type: %s", 134 isc_result_totext (status)); 135 136 interface_setup (); 137} 138 139isc_result_t dhcp_group_set_value (omapi_object_t *h, 140 omapi_object_t *id, 141 omapi_data_string_t *name, 142 omapi_typed_data_t *value) 143{ 144 struct group_object *group; 145 isc_result_t status; 146 147 if (h -> type != dhcp_type_group) 148 return ISC_R_INVALIDARG; 149 group = (struct group_object *)h; 150 151 /* XXX For now, we can only set these values on new group objects. 152 XXX Soon, we need to be able to update group objects. */ 153 if (!omapi_ds_strcmp (name, "name")) { 154 if (group -> name) 155 return ISC_R_EXISTS; 156 if (value -> type == omapi_datatype_data || 157 value -> type == omapi_datatype_string) { 158 group -> name = dmalloc (value -> u.buffer.len + 1, 159 MDL); 160 if (!group -> name) 161 return ISC_R_NOMEMORY; 162 memcpy (group -> name, 163 value -> u.buffer.value, 164 value -> u.buffer.len); 165 group -> name [value -> u.buffer.len] = 0; 166 } else 167 return ISC_R_INVALIDARG; 168 return ISC_R_SUCCESS; 169 } 170 171 if (!omapi_ds_strcmp (name, "statements")) { 172 if (group -> group && group -> group -> statements) 173 return ISC_R_EXISTS; 174 if (!group -> group) { 175 if (!clone_group (&group -> group, root_group, MDL)) 176 return ISC_R_NOMEMORY; 177 } 178 if (value -> type == omapi_datatype_data || 179 value -> type == omapi_datatype_string) { 180 struct parse *parse; 181 int lose = 0; 182 parse = (struct parse *)0; 183 status = new_parse (&parse, -1, 184 (char *)value -> u.buffer.value, 185 value -> u.buffer.len, 186 "network client", 0); 187 if (status != ISC_R_SUCCESS) 188 return status; 189 if (!(parse_executable_statements 190 (&group -> group -> statements, parse, &lose, 191 context_any))) { 192 end_parse (&parse); 193 return ISC_R_BADPARSE; 194 } 195 end_parse (&parse); 196 return ISC_R_SUCCESS; 197 } else 198 return ISC_R_INVALIDARG; 199 } 200 201 /* Try to find some inner object that can take the value. */ 202 if (h -> inner && h -> inner -> type -> set_value) { 203 status = ((*(h -> inner -> type -> set_value)) 204 (h -> inner, id, name, value)); 205 if (status == ISC_R_SUCCESS || status == ISC_R_UNCHANGED) 206 return status; 207 } 208 209 return ISC_R_NOTFOUND; 210} 211 212 213isc_result_t dhcp_group_get_value (omapi_object_t *h, omapi_object_t *id, 214 omapi_data_string_t *name, 215 omapi_value_t **value) 216{ 217 struct group_object *group; 218 isc_result_t status; 219 220 if (h -> type != dhcp_type_group) 221 return ISC_R_INVALIDARG; 222 group = (struct group_object *)h; 223 224 if (!omapi_ds_strcmp (name, "name")) 225 return omapi_make_string_value (value, 226 name, group -> name, MDL); 227 228 /* Try to find some inner object that can take the value. */ 229 if (h -> inner && h -> inner -> type -> get_value) { 230 status = ((*(h -> inner -> type -> get_value)) 231 (h -> inner, id, name, value)); 232 if (status == ISC_R_SUCCESS) 233 return status; 234 } 235 return ISC_R_NOTFOUND; 236} 237 238isc_result_t dhcp_group_destroy (omapi_object_t *h, const char *file, int line) 239{ 240 struct group_object *group, *t; 241 242 if (h -> type != dhcp_type_group) 243 return ISC_R_INVALIDARG; 244 group = (struct group_object *)h; 245 246 if (group -> name) { 247 if (group_name_hash) { 248 t = (struct group_object *)0; 249 if (group_hash_lookup (&t, group_name_hash, 250 group -> name, 251 strlen (group -> name), MDL)) { 252 group_hash_delete (group_name_hash, 253 group -> name, 254 strlen (group -> name), 255 MDL); 256 group_object_dereference (&t, MDL); 257 } 258 } 259 dfree (group -> name, file, line); 260 group -> name = (char *)0; 261 } 262 if (group -> group) 263 group_dereference (&group -> group, MDL); 264 265 return ISC_R_SUCCESS; 266} 267 268isc_result_t dhcp_group_signal_handler (omapi_object_t *h, 269 const char *name, va_list ap) 270{ 271 struct group_object *group; 272 isc_result_t status; 273 int updatep = 0; 274 275 if (h -> type != dhcp_type_group) 276 return ISC_R_INVALIDARG; 277 group = (struct group_object *)h; 278 279 if (!strcmp (name, "updated")) { 280 /* A group object isn't valid if a subgroup hasn't yet been 281 associated with it. */ 282 if (!group -> group) 283 return ISC_R_INVALIDARG; 284 285 /* Group objects always have to have names. */ 286 if (!group -> name) { 287 char hnbuf [64]; 288 sprintf (hnbuf, "ng%08lx%08lx", 289 (unsigned long)cur_time, 290 (unsigned long)group); 291 group -> name = dmalloc (strlen (hnbuf) + 1, MDL); 292 if (!group -> name) 293 return ISC_R_NOMEMORY; 294 strcpy (group -> name, hnbuf); 295 } 296 297 supersede_group (group, 1); 298 updatep = 1; 299 } 300 301 /* Try to find some inner object that can take the value. */ 302 if (h -> inner && h -> inner -> type -> get_value) { 303 status = ((*(h -> inner -> type -> signal_handler)) 304 (h -> inner, name, ap)); 305 if (status == ISC_R_SUCCESS) 306 return status; 307 } 308 if (updatep) 309 return ISC_R_SUCCESS; 310 return ISC_R_NOTFOUND; 311} 312 313isc_result_t dhcp_group_stuff_values (omapi_object_t *c, 314 omapi_object_t *id, 315 omapi_object_t *h) 316{ 317 struct group_object *group; 318 isc_result_t status; 319 320 if (h -> type != dhcp_type_group) 321 return ISC_R_INVALIDARG; 322 group = (struct group_object *)h; 323 324#if !defined (SMALL) 325 /* Write out all the values. */ 326 if (group -> name) { 327 status = omapi_connection_put_name (c, "name"); 328 if (status != ISC_R_SUCCESS) 329 return status; 330 status = omapi_connection_put_string (c, group -> name); 331 if (status != ISC_R_SUCCESS) 332 return status; 333 } 334#endif 335 336 /* Write out the inner object, if any. */ 337 if (h -> inner && h -> inner -> type -> stuff_values) { 338 status = ((*(h -> inner -> type -> stuff_values)) 339 (c, id, h -> inner)); 340 if (status == ISC_R_SUCCESS) 341 return status; 342 } 343 344 return ISC_R_SUCCESS; 345} 346 347isc_result_t dhcp_group_lookup (omapi_object_t **lp, 348 omapi_object_t *id, omapi_object_t *ref) 349{ 350 omapi_value_t *tv = (omapi_value_t *)0; 351 isc_result_t status; 352 struct group_object *group; 353 354 if (!ref) 355 return ISC_R_NOKEYS; 356 357 /* First see if we were sent a handle. */ 358 status = omapi_get_value_str (ref, id, "handle", &tv); 359 if (status == ISC_R_SUCCESS) { 360 status = omapi_handle_td_lookup (lp, tv -> value); 361 362 omapi_value_dereference (&tv, MDL); 363 if (status != ISC_R_SUCCESS) 364 return status; 365 366 /* Don't return the object if the type is wrong. */ 367 if ((*lp) -> type != dhcp_type_group) { 368 omapi_object_dereference (lp, MDL); 369 return ISC_R_INVALIDARG; 370 } 371 } 372 373 /* Now look for a name. */ 374 status = omapi_get_value_str (ref, id, "name", &tv); 375 if (status == ISC_R_SUCCESS) { 376 group = (struct group_object *)0; 377 if (group_name_hash && 378 group_hash_lookup (&group, group_name_hash, 379 (const char *) 380 tv -> value -> u.buffer.value, 381 tv -> value -> u.buffer.len, MDL)) { 382 omapi_value_dereference (&tv, MDL); 383 384 if (*lp && *lp != (omapi_object_t *)group) { 385 group_object_dereference (&group, MDL); 386 omapi_object_dereference (lp, MDL); 387 return ISC_R_KEYCONFLICT; 388 } else if (!*lp) { 389 /* XXX fix so that hash lookup itself creates 390 XXX the reference. */ 391 omapi_object_reference (lp, 392 (omapi_object_t *)group, 393 MDL); 394 group_object_dereference (&group, MDL); 395 } 396 } else if (!*lp) 397 return ISC_R_NOTFOUND; 398 } 399 400 /* If we get to here without finding a group, no valid key was 401 specified. */ 402 if (!*lp) 403 return ISC_R_NOKEYS; 404 405 if (((struct group_object *)(*lp)) -> flags & GROUP_OBJECT_DELETED) { 406 omapi_object_dereference (lp, MDL); 407 return ISC_R_NOTFOUND; 408 } 409 return ISC_R_SUCCESS; 410} 411 412isc_result_t dhcp_group_create (omapi_object_t **lp, 413 omapi_object_t *id) 414{ 415 struct group_object *group; 416 isc_result_t status; 417 group = (struct group_object *)0; 418 419 status = group_object_allocate (&group, MDL); 420 if (status != ISC_R_SUCCESS) 421 return status; 422 group -> flags = GROUP_OBJECT_DYNAMIC; 423 status = omapi_object_reference (lp, (omapi_object_t *)group, MDL); 424 group_object_dereference (&group, MDL); 425 return status; 426} 427 428isc_result_t dhcp_group_remove (omapi_object_t *lp, 429 omapi_object_t *id) 430{ 431 struct group_object *group; 432 isc_result_t status; 433 if (lp -> type != dhcp_type_group) 434 return ISC_R_INVALIDARG; 435 group = (struct group_object *)lp; 436 437 group -> flags |= GROUP_OBJECT_DELETED; 438 if (group_write_hook) { 439 if (!(*group_write_hook) (group)) 440 return ISC_R_IOERROR; 441 } 442 443 status = dhcp_group_destroy ((omapi_object_t *)group, MDL); 444 445 return ISC_R_SUCCESS; 446} 447 448isc_result_t dhcp_control_set_value (omapi_object_t *h, 449 omapi_object_t *id, 450 omapi_data_string_t *name, 451 omapi_typed_data_t *value) 452{ 453 dhcp_control_object_t *control; 454 isc_result_t status; 455 unsigned long newstate; 456 457 if (h -> type != dhcp_type_control) 458 return ISC_R_INVALIDARG; 459 control = (dhcp_control_object_t *)h; 460 461 if (!omapi_ds_strcmp (name, "state")) { 462 status = omapi_get_int_value (&newstate, value); 463 if (status != ISC_R_SUCCESS) 464 return status; 465 status = dhcp_set_control_state (control -> state, newstate); 466 if (status == ISC_R_SUCCESS) 467 control -> state = value -> u.integer; 468 return status; 469 } 470 471 /* Try to find some inner object that can take the value. */ 472 if (h -> inner && h -> inner -> type -> set_value) { 473 status = ((*(h -> inner -> type -> set_value)) 474 (h -> inner, id, name, value)); 475 if (status == ISC_R_SUCCESS || status == ISC_R_UNCHANGED) 476 return status; 477 } 478 479 return ISC_R_NOTFOUND; 480} 481 482 483isc_result_t dhcp_control_get_value (omapi_object_t *h, omapi_object_t *id, 484 omapi_data_string_t *name, 485 omapi_value_t **value) 486{ 487 dhcp_control_object_t *control; 488 isc_result_t status; 489 490 if (h -> type != dhcp_type_control) 491 return ISC_R_INVALIDARG; 492 control = (dhcp_control_object_t *)h; 493 494 if (!omapi_ds_strcmp (name, "state")) 495 return omapi_make_int_value (value, 496 name, (int)control -> state, MDL); 497 498 /* Try to find some inner object that can take the value. */ 499 if (h -> inner && h -> inner -> type -> get_value) { 500 status = ((*(h -> inner -> type -> get_value)) 501 (h -> inner, id, name, value)); 502 if (status == ISC_R_SUCCESS) 503 return status; 504 } 505 return ISC_R_NOTFOUND; 506} 507 508isc_result_t dhcp_control_destroy (omapi_object_t *h, 509 const char *file, int line) 510{ 511 512 if (h -> type != dhcp_type_control) 513 return ISC_R_INVALIDARG; 514 515 /* Can't destroy the control object. */ 516 return ISC_R_NOPERM; 517} 518 519isc_result_t dhcp_control_signal_handler (omapi_object_t *h, 520 const char *name, va_list ap) 521{ 522 dhcp_control_object_t *control; 523 isc_result_t status; 524 525 if (h -> type != dhcp_type_control) 526 return ISC_R_INVALIDARG; 527 control = (dhcp_control_object_t *)h; 528 529 /* Try to find some inner object that can take the value. */ 530 if (h -> inner && h -> inner -> type -> get_value) { 531 status = ((*(h -> inner -> type -> signal_handler)) 532 (h -> inner, name, ap)); 533 if (status == ISC_R_SUCCESS) 534 return status; 535 } 536 return ISC_R_NOTFOUND; 537} 538 539isc_result_t dhcp_control_stuff_values (omapi_object_t *c, 540 omapi_object_t *id, 541 omapi_object_t *h) 542{ 543 dhcp_control_object_t *control; 544 isc_result_t status; 545 546 if (h -> type != dhcp_type_control) 547 return ISC_R_INVALIDARG; 548 control = (dhcp_control_object_t *)h; 549 550#ifndef SMALL 551 /* Write out all the values. */ 552 status = omapi_connection_put_name (c, "state"); 553 if (status != ISC_R_SUCCESS) 554 return status; 555 status = omapi_connection_put_uint32 (c, sizeof (u_int32_t)); 556 if (status != ISC_R_SUCCESS) 557 return status; 558 status = omapi_connection_put_uint32 (c, control -> state); 559 if (status != ISC_R_SUCCESS) 560 return status; 561#endif 562 563 /* Write out the inner object, if any. */ 564 if (h -> inner && h -> inner -> type -> stuff_values) { 565 status = ((*(h -> inner -> type -> stuff_values)) 566 (c, id, h -> inner)); 567 if (status == ISC_R_SUCCESS) 568 return status; 569 } 570 571 return ISC_R_SUCCESS; 572} 573 574isc_result_t dhcp_control_lookup (omapi_object_t **lp, 575 omapi_object_t *id, omapi_object_t *ref) 576{ 577 omapi_value_t *tv = (omapi_value_t *)0; 578 isc_result_t status; 579 580 /* First see if we were sent a handle. */ 581 if (ref) { 582 status = omapi_get_value_str (ref, id, "handle", &tv); 583 if (status == ISC_R_SUCCESS) { 584 status = omapi_handle_td_lookup (lp, tv -> value); 585 586 omapi_value_dereference (&tv, MDL); 587 if (status != ISC_R_SUCCESS) 588 return status; 589 590 /* Don't return the object if the type is wrong. */ 591 if ((*lp) -> type != dhcp_type_control) { 592 omapi_object_dereference (lp, MDL); 593 return ISC_R_INVALIDARG; 594 } 595 } 596 } 597 598 /* Otherwise, stop playing coy - there's only one control object, 599 so we can just return it. */ 600 dhcp_control_reference ((dhcp_control_object_t **)lp, 601 dhcp_control_object, MDL); 602 return ISC_R_SUCCESS; 603} 604 605isc_result_t dhcp_control_create (omapi_object_t **lp, 606 omapi_object_t *id) 607{ 608 /* Can't create a control object - there can be only one. */ 609 return ISC_R_NOPERM; 610} 611 612isc_result_t dhcp_control_remove (omapi_object_t *lp, 613 omapi_object_t *id) 614{ 615 /* Form is emptiness; emptiness form. The control object 616 cannot go out of existance. */ 617 return ISC_R_NOPERM; 618} 619 620isc_result_t dhcp_subnet_set_value (omapi_object_t *h, 621 omapi_object_t *id, 622 omapi_data_string_t *name, 623 omapi_typed_data_t *value) 624{ 625 struct subnet *subnet; 626 isc_result_t status; 627 628 if (h -> type != dhcp_type_subnet) 629 return ISC_R_INVALIDARG; 630 subnet = (struct subnet *)h; 631 632 /* No values to set yet. */ 633 634 /* Try to find some inner object that can take the value. */ 635 if (h -> inner && h -> inner -> type -> set_value) { 636 status = ((*(h -> inner -> type -> set_value)) 637 (h -> inner, id, name, value)); 638 if (status == ISC_R_SUCCESS || status == ISC_R_UNCHANGED) 639 return status; 640 } 641 642 return ISC_R_NOTFOUND; 643} 644 645 646isc_result_t dhcp_subnet_get_value (omapi_object_t *h, omapi_object_t *id, 647 omapi_data_string_t *name, 648 omapi_value_t **value) 649{ 650 struct subnet *subnet; 651 isc_result_t status; 652 653 if (h -> type != dhcp_type_subnet) 654 return ISC_R_INVALIDARG; 655 subnet = (struct subnet *)h; 656 657 /* No values to get yet. */ 658 659 /* Try to find some inner object that can provide the value. */ 660 if (h -> inner && h -> inner -> type -> get_value) { 661 status = ((*(h -> inner -> type -> get_value)) 662 (h -> inner, id, name, value)); 663 if (status == ISC_R_SUCCESS) 664 return status; 665 } 666 return ISC_R_NOTFOUND; 667} 668 669isc_result_t dhcp_subnet_destroy (omapi_object_t *h, const char *file, int line) 670{ 671 struct subnet *subnet; 672 673 if (h -> type != dhcp_type_subnet) 674 return ISC_R_INVALIDARG; 675 subnet = (struct subnet *)h; 676 677#if defined (DEBUG_MEMORY_LEAKAGE) || \ 678 defined (DEBUG_MEMORY_LEAKAGE_ON_EXIT) 679 if (subnet -> next_subnet) 680 subnet_dereference (&subnet -> next_subnet, file, line); 681 if (subnet -> next_sibling) 682 subnet_dereference (&subnet -> next_sibling, file, line); 683 if (subnet -> shared_network) 684 shared_network_dereference (&subnet -> shared_network, 685 file, line); 686 if (subnet -> interface) 687 interface_dereference (&subnet -> interface, file, line); 688 if (subnet -> group) 689 group_dereference (&subnet -> group, file, line); 690#endif 691 692 return ISC_R_SUCCESS; 693} 694 695isc_result_t dhcp_subnet_signal_handler (omapi_object_t *h, 696 const char *name, va_list ap) 697{ 698 struct subnet *subnet; 699 isc_result_t status; 700 int updatep = 0; 701 702 if (h -> type != dhcp_type_subnet) 703 return ISC_R_INVALIDARG; 704 subnet = (struct subnet *)h; 705 706 /* Can't write subnets yet. */ 707 708 /* Try to find some inner object that can take the value. */ 709 if (h -> inner && h -> inner -> type -> get_value) { 710 status = ((*(h -> inner -> type -> signal_handler)) 711 (h -> inner, name, ap)); 712 if (status == ISC_R_SUCCESS) 713 return status; 714 } 715 if (updatep) 716 return ISC_R_SUCCESS; 717 return ISC_R_NOTFOUND; 718} 719 720isc_result_t dhcp_subnet_stuff_values (omapi_object_t *c, 721 omapi_object_t *id, 722 omapi_object_t *h) 723{ 724 struct subnet *subnet; 725 isc_result_t status; 726 727 if (h -> type != dhcp_type_subnet) 728 return ISC_R_INVALIDARG; 729 subnet = (struct subnet *)h; 730 731 /* Can't stuff subnet values yet. */ 732 733 /* Write out the inner object, if any. */ 734 if (h -> inner && h -> inner -> type -> stuff_values) { 735 status = ((*(h -> inner -> type -> stuff_values)) 736 (c, id, h -> inner)); 737 if (status == ISC_R_SUCCESS) 738 return status; 739 } 740 741 return ISC_R_SUCCESS; 742} 743 744isc_result_t dhcp_subnet_lookup (omapi_object_t **lp, 745 omapi_object_t *id, 746 omapi_object_t *ref) 747{ 748 749 /* Can't look up subnets yet. */ 750 751 /* If we get to here without finding a subnet, no valid key was 752 specified. */ 753 if (!*lp) 754 return ISC_R_NOKEYS; 755 return ISC_R_SUCCESS; 756} 757 758isc_result_t dhcp_subnet_create (omapi_object_t **lp, 759 omapi_object_t *id) 760{ 761 return ISC_R_NOTIMPLEMENTED; 762} 763 764isc_result_t dhcp_subnet_remove (omapi_object_t *lp, 765 omapi_object_t *id) 766{ 767 return ISC_R_NOTIMPLEMENTED; 768} 769 770isc_result_t dhcp_shared_network_set_value (omapi_object_t *h, 771 omapi_object_t *id, 772 omapi_data_string_t *name, 773 omapi_typed_data_t *value) 774{ 775 struct shared_network *shared_network; 776 isc_result_t status; 777 778 if (h -> type != dhcp_type_shared_network) 779 return ISC_R_INVALIDARG; 780 shared_network = (struct shared_network *)h; 781 782 /* No values to set yet. */ 783 784 /* Try to find some inner object that can take the value. */ 785 if (h -> inner && h -> inner -> type -> set_value) { 786 status = ((*(h -> inner -> type -> set_value)) 787 (h -> inner, id, name, value)); 788 if (status == ISC_R_SUCCESS || status == ISC_R_UNCHANGED) 789 return status; 790 } 791 792 return ISC_R_NOTFOUND; 793} 794 795 796isc_result_t dhcp_shared_network_get_value (omapi_object_t *h, 797 omapi_object_t *id, 798 omapi_data_string_t *name, 799 omapi_value_t **value) 800{ 801 struct shared_network *shared_network; 802 isc_result_t status; 803 804 if (h -> type != dhcp_type_shared_network) 805 return ISC_R_INVALIDARG; 806 shared_network = (struct shared_network *)h; 807 808 /* No values to get yet. */ 809 810 /* Try to find some inner object that can provide the value. */ 811 if (h -> inner && h -> inner -> type -> get_value) { 812 status = ((*(h -> inner -> type -> get_value)) 813 (h -> inner, id, name, value)); 814 if (status == ISC_R_SUCCESS) 815 return status; 816 } 817 return ISC_R_NOTFOUND; 818} 819 820isc_result_t dhcp_shared_network_destroy (omapi_object_t *h, 821 const char *file, int line) 822{ 823 struct shared_network *shared_network; 824 825 if (h -> type != dhcp_type_shared_network) 826 return ISC_R_INVALIDARG; 827 shared_network = (struct shared_network *)h; 828 829#if defined (DEBUG_MEMORY_LEAKAGE) || \ 830 defined (DEBUG_MEMORY_LEAKAGE_ON_EXIT) 831 if (shared_network -> next) 832 shared_network_dereference (&shared_network -> next, 833 file, line); 834 if (shared_network -> name) { 835 dfree (shared_network -> name, file, line); 836 shared_network -> name = 0; 837 } 838 if (shared_network -> subnets) 839 subnet_dereference (&shared_network -> subnets, file, line); 840 if (shared_network -> interface) 841 interface_dereference (&shared_network -> interface, 842 file, line); 843 if (shared_network -> pools) 844 omapi_object_dereference ((omapi_object_t **) 845 &shared_network -> pools, file, line); 846 if (shared_network -> group) 847 group_dereference (&shared_network -> group, file, line); 848#if defined (FAILOVER_PROTOCOL) 849 if (shared_network -> failover_peer) 850 omapi_object_dereference ((omapi_object_t **) 851 &shared_network -> failover_peer, 852 file, line); 853#endif 854#endif /* DEBUG_MEMORY_LEAKAGE */ 855 856 return ISC_R_SUCCESS; 857} 858 859isc_result_t dhcp_shared_network_signal_handler (omapi_object_t *h, 860 const char *name, 861 va_list ap) 862{ 863 struct shared_network *shared_network; 864 isc_result_t status; 865 int updatep = 0; 866 867 if (h -> type != dhcp_type_shared_network) 868 return ISC_R_INVALIDARG; 869 shared_network = (struct shared_network *)h; 870 871 /* Can't write shared_networks yet. */ 872 873 /* Try to find some inner object that can take the value. */ 874 if (h -> inner && h -> inner -> type -> get_value) { 875 status = ((*(h -> inner -> type -> signal_handler)) 876 (h -> inner, name, ap)); 877 if (status == ISC_R_SUCCESS) 878 return status; 879 } 880 if (updatep) 881 return ISC_R_SUCCESS; 882 return ISC_R_NOTFOUND; 883} 884 885isc_result_t dhcp_shared_network_stuff_values (omapi_object_t *c, 886 omapi_object_t *id, 887 omapi_object_t *h) 888{ 889 struct shared_network *shared_network; 890 isc_result_t status; 891 892 if (h -> type != dhcp_type_shared_network) 893 return ISC_R_INVALIDARG; 894 shared_network = (struct shared_network *)h; 895 896 /* Can't stuff shared_network values yet. */ 897 898 /* Write out the inner object, if any. */ 899 if (h -> inner && h -> inner -> type -> stuff_values) { 900 status = ((*(h -> inner -> type -> stuff_values)) 901 (c, id, h -> inner)); 902 if (status == ISC_R_SUCCESS) 903 return status; 904 } 905 906 return ISC_R_SUCCESS; 907} 908 909isc_result_t dhcp_shared_network_lookup (omapi_object_t **lp, 910 omapi_object_t *id, 911 omapi_object_t *ref) 912{ 913 914 /* Can't look up shared_networks yet. */ 915 916 /* If we get to here without finding a shared_network, no valid key was 917 specified. */ 918 if (!*lp) 919 return ISC_R_NOKEYS; 920 return ISC_R_SUCCESS; 921} 922 923isc_result_t dhcp_shared_network_create (omapi_object_t **lp, 924 omapi_object_t *id) 925{ 926 return ISC_R_NOTIMPLEMENTED; 927} 928 929isc_result_t dhcp_shared_network_remove (omapi_object_t *lp, 930 omapi_object_t *id) 931{ 932 return ISC_R_NOTIMPLEMENTED; 933} 934 935