📄 ipraw.c
字号:
/* Set the data pointer to the correct location. */
buf_ptr->data_ptr = (buf_ptr->mem_parent_packet +
NET_MAX_IP_HEADER_SIZE);
/* Move the data into the output buffer. This will depend on the size of
the data. The data may need to be copied into the multiple buffers
in the buffer chain. */
/* Get the total number of bytes that must be copied. */
bytes_left = nbytes;
/* Will it all fit into one buffer? */
if (bytes_left <= (NET_PARENT_BUFFER_SIZE - NET_MAX_IP_HEADER_SIZE))
{
/* Store the number of bytes held by this buffer, this includes the
protocol headers. */
buf_ptr->data_len = buf_ptr->mem_total_data_len;
NU_BLOCK_COPY (buf_ptr->data_ptr, buffer, (unsigned int)nbytes);
}
else
{
/* Fill the parent buffer in the chain. This one is slightly smaller than
the rest in the chain. */
NU_BLOCK_COPY (buf_ptr->data_ptr, buffer, NET_PARENT_BUFFER_SIZE -
NET_MAX_IP_HEADER_SIZE);
/* Take off the bytes just copied from the total bytes left. */
bytes_left -= (NET_PARENT_BUFFER_SIZE - NET_MAX_IP_HEADER_SIZE);
/* Store the number of bytes in this buffer. */
buf_ptr->data_len = ((NET_PARENT_BUFFER_SIZE - NET_MAX_IP_HEADER_SIZE));
/* Get a work pointer and bump it the number of bytes just copied. */
work_ptr = (buffer + (NET_PARENT_BUFFER_SIZE - NET_MAX_IP_HEADER_SIZE));
/* Get a work buffer pointer to the buffer chain */
work_buf = buf_ptr;
/* Break the rest up into the multiple buffers in the chain. */
do
{
/* Move to the next buffer in the chain */
work_buf = work_buf->next_buffer;
/* If the bytes left will fit into one buffer then copy them over */
if (bytes_left <= NET_MAX_BUFFER_SIZE)
{
/* Copy the rest of the data. */
NU_BLOCK_COPY (work_buf->mem_packet, work_ptr, (INT)bytes_left);
/* Set the data ptr */
work_buf->data_ptr = work_buf->mem_packet;
/* Store the number of bytes in this buffer. */
work_buf->data_len = bytes_left;
}
else
{
/* Copy all that will fit into a single buffer */
NU_BLOCK_COPY (work_buf->mem_packet, work_ptr, NET_MAX_BUFFER_SIZE);
/* Update the buffer pointer */
work_ptr += NET_MAX_BUFFER_SIZE;
/* Set the data ptr */
work_buf->data_ptr = work_buf->mem_packet;
/* Store the number of bytes in this buffer. */
work_buf->data_len = NET_MAX_BUFFER_SIZE;
}
/* Update the data bytes left to copy. */
bytes_left -= NET_MAX_BUFFER_SIZE;
} while (bytes_left > 0);
} /* end if it will fit into one buffer */
/* Send this packet. */
/* If the application created the header - socket option HDRINCL */
if (sock_ptr->s_flags & IP_RAWOUTPUT)
{
stat = IP_Send( (NET_BUFFER *)buf_ptr, &iptr->ip_route,
iptr->ip_route.rt_ip_dest.sck_addr, iptr->ip_laddr,
IP_RAWOUTPUT, IP_TIME_TO_LIVE, (INT)iptr->ip_protocol,
IP_TYPE_OF_SERVICE, sock_ptr->s_moptions);
}
else
{
stat = IP_Send( (NET_BUFFER *)buf_ptr, &iptr->ip_route,
iptr->ip_route.rt_ip_dest.sck_addr, iptr->ip_laddr,
IP_ALLOWBROADCAST, IP_TIME_TO_LIVE, (INT)iptr->ip_protocol,
IP_TYPE_OF_SERVICE, sock_ptr->s_moptions);
}
if(stat != NU_SUCCESS)
{
/* The packet was not sent. Dealocate the buffer. If the packet was
transmitted it will be deallocated later by the apropriate MAC layer
TX routine. */
MEM_One_Buffer_Chain_Free (buf_ptr, &MEM_Buffer_Freelist);
return -1;
}
/* If the send went ok, then return the number of bytes sent. */
return((INT16)nbytes);
}
/***********************************************************************
*
*
* IPRaw_Interpret
*
* DESCRIPTION
*
* Process received IP Raw datagrams.
*
* INPUTS
*
* buf_ptr
* device
*
* OUTPUTS
*
* NU_SUCCESS
* -1
*
*************************************************************************/
STATUS IPRaw_Interpret (NET_BUFFER *buf_ptr, DV_DEVICE_ENTRY *device)
{
INT i;
NET_BUFFER *new_buf_ptr;
IPLAYER *ip_ptr;
/* Remove compiler warning. */
UNUSED_PARAMETER(device);
/* Pull the current buffer chain off of the
receive list. */
MEM_Buffer_Dequeue (&MEM_Buffer_List);
/* The data pointer was advanced past the IP header prior to entering
this funtion, move it back to point at the IP header so that
we can peek into it and pass it up to the application if a matching
process is found. */
buf_ptr->data_ptr -= sizeof(IPLAYER);
buf_ptr->data_len += sizeof(IPLAYER);
buf_ptr->mem_total_data_len += sizeof(IPLAYER);
/* Grab a pointer into the IP layer. */
ip_ptr = (IPLAYER *)buf_ptr->data_ptr;
/*
* did we want this data ? If not, then let it go, no comment
* If we want it, copy the relevent information into our structure
*/
for (i = 0; i < IPR_MAX_PORTS; i++)
{
/* Check to make sure this entry in the iportlist actually points to a
port structure, and check to see if the destination protocol
matches the local protocol. Short circuit evaluation will cause
the test to fail immediately if the pointer to the port structure is NULL.
*/
if ( (IPR_Ports[i]) &&
((GET8(ip_ptr, IP_PROTOCOL_OFFSET) == IPR_Ports[i]->ip_protocol) ||
(IPR_Ports[i]->ip_protocol == 0) ))
{
/* Compare local address with destination address */
if( (IPR_Ports[i]->ip_laddr == IP_ADDR_ANY) ||
(GET32(ip_ptr, IP_DEST_OFFSET) == IPR_Ports[i]->ip_laddr) )
{
/* Compare foreign address with source address */
if( (IPR_Ports[i]->ip_faddr == IP_ADDR_ANY) ||
(GET32(ip_ptr, IP_SRC_OFFSET) == IPR_Ports[i]->ip_faddr) )
{
/* When a match is found our search is over. */
/* Make sure there is room to add the received
packet. */
if (SCK_Sockets[IPR_Ports[i]->ip_socketd]->s_recvpackets
< IMAX_DGRAMS)
{
/* Since this packet could be passed to
multiple sockets we need to make a copy
for each socket that might RX it. So,
allocate buffers for it and copy it. */
new_buf_ptr = MEM_Buffer_Chain_Dequeue (&MEM_Buffer_Freelist,
(INT32)buf_ptr->mem_total_data_len);
/* Make sure we got the buffers. */
if (new_buf_ptr)
{
/* Init the header fields for this new buffer. */
new_buf_ptr->data_ptr = new_buf_ptr->mem_packet;
new_buf_ptr->mem_buf_device = buf_ptr->mem_buf_device;
/* Copy the data from the original packet. */
MEM_Chain_Copy (new_buf_ptr, buf_ptr, 0,
(INT32)buf_ptr->mem_total_data_len);
/* Set the total length for this new packet. */
new_buf_ptr->mem_total_data_len = buf_ptr->mem_total_data_len;
/* Append the new buffer to datagram queue */
IPRaw_Append(i, new_buf_ptr);
}
}
}
}
}
} /* end for i =0 to IPR_MAX_PORTS */
/* Free the original buffers held by this packet. */
MEM_One_Buffer_Chain_Free (buf_ptr, &MEM_Buffer_Freelist);
return (NU_SUCCESS);
} /* IPRaw_Interpret */
/***********************************************************************
*
* FUNCTION
*
* IPRaw_Append
*
* DESCRIPTION
*
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -