📄 bootp.c
字号:
*
* DESCRIPTION
*
* This routine will handle the parseing of the incomming bootp
* packets.
*
* INPUTS
*
* socketd Socket Descriptor to retrieve data from.
* bp Pointer to the bootp packet that we are
* to process.
* timeout Timeout value used for NU_Select.
*
*
* OUTPUTS
*
* NU_NO_SOCK_MEMORY Unable to allocate memory.
* NU_BOOTP_FAILED No data to process.
* NU_BOOTP_SELECT_FAILED No bootp packet to process.
* NU_BOOTP_RECV_FAILED Error retrieving data.
* NU_TRUE Packet was processed.
* 0 Packet was not found.
*
****************************************************************************/
STATUS BOOTP_Process_Packets(INT socketd, BOOTP_STRUCT *bp, UINT16 timeout)
{
STATUS ret;
INT x, items, len;
INT16 flen;
CHAR *inbuf;
INT16 found = 0;
UINT8 bootp_cookie[4] = BOOTP_COOKIE;
UINT32 vend_cookie;
UINT32 local_xid;
BOOTPLAYER *bootp_ptr; /* Bootp struct pointer*/
FD_SET readfs, writefs, exceptfs;
STATUS status;
struct addr_struct fromaddr;
UINT8 *ptr;
UINT8 message[80];
STATUS retval = 0;
/* Allocate Memory for input Buffer */
status = NU_Allocate_Memory(&System_Memory, (VOID **)&inbuf, IOSIZE,
(UNSIGNED)NU_NO_SUSPEND);
/* Check if an error occured during NU_Allocate_Memory */
if (status != NU_SUCCESS)
{
NERRS_Log_Error(NERR_FATAL, __FILE__, __LINE__);
return (NU_NO_SOCK_MEMORY);
}
/* Do While to process received data */
do
{ /* do while */
NU_FD_Init(&readfs);
NU_FD_Set(socketd, &readfs);
ret = NU_Select(NSOCKETS, &readfs, &writefs, &exceptfs,
(timeout * SCK_Ticks_Per_Second));
if (ret == NU_NO_DATA)
{
retval = NU_BOOTP_FAILED;
break;
}
if (NU_FD_Check(socketd, &readfs) == NU_FALSE)
{
retval = NU_BOOTP_SELECT_FAILED;
break;
}
fromaddr.family = NU_FAMILY_IP;
fromaddr.port = 0;
ret = (INT)NU_Recv_From(socketd, inbuf, IOSIZE, 0, &fromaddr, &flen);
if (ret < 0)
{
NERRS_Log_Error(NERR_FATAL, __FILE__, __LINE__);
retval = NU_BOOTP_RECV_FAILED;
break;
}
/* get pointer to BOOTP packet. */
bootp_ptr = (BOOTPLAYER *)inbuf;
/* Retrieve the unique ID from the packet */
memcpy(&local_xid, &bootp_ptr->bp_xid, sizeof(UINT32) );
/* see if packet is the returning response to the packet I sent */
if ( local_xid != bootp_xid )
continue;
/* Accept the very first packet */
/* Get the Server address */
bp->bp_siaddr[0] = bootp_ptr->bp_siaddr.is_ip_addrs[0];
bp->bp_siaddr[1] = bootp_ptr->bp_siaddr.is_ip_addrs[1];
bp->bp_siaddr[2] = bootp_ptr->bp_siaddr.is_ip_addrs[2];
bp->bp_siaddr[3] = bootp_ptr->bp_siaddr.is_ip_addrs[3];
/* Get the gateway address */
bp->bp_giaddr[0] = bootp_ptr->bp_giaddr.is_ip_addrs[0];
bp->bp_giaddr[1] = bootp_ptr->bp_giaddr.is_ip_addrs[1];
bp->bp_giaddr[2] = bootp_ptr->bp_giaddr.is_ip_addrs[2];
bp->bp_giaddr[3] = bootp_ptr->bp_giaddr.is_ip_addrs[3];
/* Get my IP address */
bp->bp_yiaddr[0] = bootp_ptr->bp_yiaddr.is_ip_addrs[0];
bp->bp_yiaddr[1] = bootp_ptr->bp_yiaddr.is_ip_addrs[1];
bp->bp_yiaddr[2] = bootp_ptr->bp_yiaddr.is_ip_addrs[2];
bp->bp_yiaddr[3] = bootp_ptr->bp_yiaddr.is_ip_addrs[3];
/* Get the Server Name */
memcpy(bp->bp_sname, bootp_ptr->bp_sname, sizeof(bp->bp_sname) );
/* Get the Bootp file name. */
memcpy(bp->bp_file, bootp_ptr->bp_file, sizeof(bp->bp_file) );
/* Get the Vnedor specific cookie. */
memcpy( &vend_cookie, bootp_ptr->bp_vend, 4);
/* test to see if cookie is a vendor cookie */
if (TLS_Comparen (bootp_ptr->bp_vend, VM_RFC1048,4))
{
if (vend_cookie == *(UINT32 *)bootp_cookie)
{
/* Now loop thur vendor options, passing them to user */
/* callback function. */
ptr = bootp_ptr->bp_vend + 4;
found = NU_TRUE;
while ((*ptr != 255) && ((ptr - bootp_ptr->bp_vend) < 64))
{
switch (*ptr)
{
case BOOTP_PAD: /* nop padding, used to align fields to word */
ptr++; /* boundries. */
break;
case BOOTP_SUBNET: /* subnet mask */
len = (*(ptr + 1));
ptr += 2;
bp->bp_net_mask[0] = (*ptr);
bp->bp_net_mask[1] = (*(ptr + 1));
bp->bp_net_mask[2] = (*(ptr + 2));
bp->bp_net_mask[3] = (*(ptr + 3));
ptr += len;
break;
case BOOTP_TIMEOFF: /* time offset */
ptr += 3;
break;
case BOOTP_GATEWAY: /* gateways */
len = (*(ptr + 1));
items = len/4;
ptr += 2;
for (x = 0; x < items; x++)
{
ptr += 4;
}
break;
case BOOTP_TIMESERV: /* time servers */
case BOOTP_NAMESERV: /* IEN = 116 name server */
ptr += 3;
break;
case BOOTP_DOMNAME: /* domain name server */
len = (*(ptr + 1));
items = len / 4;
ptr += 2;
for (x = 0; x < items; x++)
{
ptr += 4;
}
break;
case BOOTP_LOGSERV: /* log server */
/* Place your code here. */
case BOOTP_COOKSRV: /* cookie server */
/* Place your code here. */
case BOOTP_LPRSRV: /* lpr server */
/* Place your code here. */
case BOOTP_IMPRSRV: /* impress server */
/* Place your code here. */
case BOOTP_RLPSRV: /* rlp server */
/* Place your code here. */
ptr += 3;
break;
case BOOTP_HOSTNAME: /* client host name */
len = (*(ptr + 1));
strncpy ((INT8 *)message, (const INT8 *)ptr + 2, len);
message[len] = 0;
ptr += len+2;
break;
case BOOTP_BFILSZ: /* Bootp File Size */
ptr += 2;
break;
case BOOTP_END:
break;
default:
ptr += 3;
break;
} /* end switch */
} /* end while */
}
}
} while (found == 0);
NU_Deallocate_Memory(inbuf);
if (retval == 0)
{
if (found == 0)
retval = NU_BOOTP_RECV_FAILED;
else
retval = found;
}
return (retval);
} /* end BOOTP_Process_Packets */
#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -