Annotation of embedaddon/dhcp/common/comapi.c, revision 1.1

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

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>