adopt.c revision d04ccbb3f3163ae5962a8b7465d9796bff6ca434
/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License (the "License").
* You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/*
* Copyright 2007 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*
* ADOPTING state of the client state machine. This is used only during
* diskless boot with IPv4.
*/
#pragma ident "%Z%%M% %I% %E% SMI"
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include <signal.h>
#include <sys/systeminfo.h>
#include <netinet/inetutil.h>
#include <dhcpmsg.h>
#include <libdevinfo.h>
#include "agent.h"
#include "async.h"
#include "util.h"
#include "packet.h"
#include "interface.h"
#include "states.h"
typedef struct {
char dk_if_name[IFNAMSIZ];
char dk_ack[1];
uint_t *);
/*
* dhcp_adopt(): adopts the interface managed by the kernel for diskless boot
*
* input: void
* output: boolean_t: B_TRUE success, B_FALSE on failure
*/
dhcp_adopt(void)
{
int retval;
goto failure;
}
/*
* convert the kernel's ACK into binary
*/
goto failure;
goto failure;
}
goto failure;
}
/*
* make an interface to represent the "cached interface" in
* the kernel, hook up the ACK packet we made, and send out
* the extend request (to attempt to renew the lease).
*
* we do a send_extend() instead of doing a dhcp_init_reboot()
* because although dhcp_init_reboot() is more correct from a
* protocol perspective, it introduces a window where a
* diskless client has no IP address but may need to page in
* more of this program. we could mlockall(), but that's
* going to be a mess, especially with handling malloc() and
* stack growth, so it's easier to just renew(). the only
* catch here is that if we are not granted a renewal, we're
* totally hosed and can only bail out.
*/
goto failure;
}
goto failure;
}
/*
* If the agent is adopting a lease, then OBP is initially
* searched for a client-id.
*/
client_id_len = 0;
&client_id_len)) {
/*
* a failure occurred trying to acquire the client-id
*/
"dhcp_adopt: cannot allocate client id for %s",
goto failure;
/*
* when the interface is infiniband and the agent
* is adopting the lease there must be an OBP
* client-id.
*/
goto failure;
}
goto failure;
goto failure;
/*
* move to BOUND and use the information in our ACK packet.
* adoption will continue after DAD via dhcp_adopt_complete.
*/
goto failure;
}
return (B_TRUE);
/* Note: no need to free lif; dsmp holds reference */
return (B_FALSE);
}
/*
* dhcp_adopt_complete(): completes interface adoption process after kernel
* duplicate address detection (DAD) is done.
*
* input: dhcp_smach_t *: the state machine on which a lease is being adopted
* output: none
*/
void
{
return;
}
if (dhcp_extending(dsmp) == 0) {
"dhcp_adopt_complete: cannot send renew request");
return;
}
if (grandparent != (pid_t)0) {
" to exit.", grandparent);
}
}
/*
* get_dhcp_kcache(): fetches the DHCP ACK and interface name from the kernel
*
* input: dhcp_kcache_t **: a dynamically-allocated cache packet
* size_t *: the length of that packet (on return)
* output: int: nonzero on success, zero on failure
*/
static int
{
char dummy;
long size;
if (size == -1)
return (0);
*kcache_size = size;
if (*kernel_cachep == NULL)
return (0);
return (1);
}
/*
* get_prom_prop(): get the value of the named property on the named node in
* devinfo root.
*
* input: const char *: The name of the node containing the property.
* const char *: The name of the property.
* uchar_t **: The property value, modified iff B_TRUE is returned.
* If no value is found the value is set to NULL.
* uint_t *: The length of the property value
* output: boolean_t: Returns B_TRUE if successful (no problems),
* otherwise B_FALSE.
* note: The memory allocated by this function must be freed by
* the caller. This code is derived from
*/
static boolean_t
{
unsigned int len = 0;
/*
* locate root node
*/
"not found");
goto get_prom_prop_cleanup;
}
/*
* locate nodename within '/'
*/
node != DI_NODE_NIL;
break;
}
}
if (node == DI_NODE_NIL) {
goto get_prom_prop_cleanup;
}
/*
* scan all properties of /nodename for the 'propname' property
*/
pp != DI_PROM_PROP_NIL;
break;
}
}
if (pp == DI_PROM_PROP_NIL) {
goto get_prom_prop_cleanup;
}
/*
* get the property; allocate some memory copy it out
*/
/*
* property data read problems
*/
goto get_prom_prop_cleanup;
}
if (propvaluep != NULL) {
/*
* allocate somewhere to copy the property value to
*/
if (*propvaluep == NULL) {
/*
* allocation problems
*/
"memory for property value");
goto get_prom_prop_cleanup;
}
/*
* copy data out
*/
/*
* copy out the length if a suitable pointer has
* been supplied
*/
}
"length = %d", len);
}
if (phdl != DI_PROM_HANDLE_NIL) {
}
if (root_node != DI_NODE_NIL) {
}
return (success);
}