mirror of
https://github.com/FreeRTOS/FreeRTOS.git
synced 2025-06-20 07:13:55 +08:00
Sync with +TCP amazon-FreeRTOS (#158)
* DNS.c commit * IP.c commit * Add various source & header files
This commit is contained in:

committed by
GitHub

parent
8e36bee30e
commit
e0d62163b0
@ -112,6 +112,9 @@ type. */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
/* Define the ASCII value of '.' (Period/Full-stop). */
|
||||
#define ASCII_BASELINE_DOT 46U
|
||||
|
||||
/*
|
||||
* Create a socket and bind it to the standard DNS port number. Return the
|
||||
* the created socket - or NULL if the socket could not be created or bound.
|
||||
@ -217,8 +220,7 @@ static uint32_t prvGetHostByName( const char *pcHostName,
|
||||
|
||||
static DNSCacheRow_t xDNSCache[ ipconfigDNS_CACHE_ENTRIES ];
|
||||
|
||||
/* MISRA c 2012 rule 8.7: Below function may be used by
|
||||
external callees as well */
|
||||
/* Utility function: Clear DNS cache by calling this function. */
|
||||
void FreeRTOS_dnsclear( void )
|
||||
{
|
||||
( void ) memset( xDNSCache, 0x0, sizeof( xDNSCache ) );
|
||||
@ -327,9 +329,6 @@ typedef struct xDNSAnswerRecord DNSAnswerRecord_t;
|
||||
/*-----------------------------------------------------------*/
|
||||
|
||||
#if( ipconfigUSE_DNS_CACHE == 1 )
|
||||
|
||||
/* MISRA c 2012 rule 8.7: Below function may be used by
|
||||
external callees as well */
|
||||
uint32_t FreeRTOS_dnslookup( const char *pcHostName )
|
||||
{
|
||||
uint32_t ulIPAddress = 0UL;
|
||||
@ -501,8 +500,6 @@ typedef struct xDNSAnswerRecord DNSAnswerRecord_t;
|
||||
/*-----------------------------------------------------------*/
|
||||
|
||||
#if( ipconfigDNS_USE_CALLBACKS == 0 )
|
||||
/* MISRA c 2012 rule 8.7 ralxed since this function can
|
||||
be called from external sources as well */
|
||||
uint32_t FreeRTOS_gethostbyname( const char *pcHostName )
|
||||
{
|
||||
return prvPrepareLookup( pcHostName );
|
||||
@ -532,8 +529,33 @@ TickType_t uxReadTimeOut_ticks = ipconfigDNS_RECEIVE_BLOCK_TIME_TICKS;
|
||||
as gethostbyname() may be called from different threads */
|
||||
BaseType_t xHasRandom = pdFALSE;
|
||||
TickType_t uxIdentifier = 0U;
|
||||
#if( ipconfigUSE_DNS_CACHE != 0 )
|
||||
BaseType_t xLengthOk = pdFALSE;
|
||||
#endif
|
||||
|
||||
#if( ipconfigUSE_DNS_CACHE != 0 )
|
||||
{
|
||||
if( pcHostName != NULL )
|
||||
{
|
||||
size_t xLength = strlen( pcHostName ) + 1;
|
||||
|
||||
if( xLength <= ipconfigDNS_CACHE_NAME_LENGTH )
|
||||
{
|
||||
/* The name is not too long. */
|
||||
xLengthOk = pdTRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
FreeRTOS_printf( ( "prvPrepareLookup: name is too long ( %lu > %lu )\n",
|
||||
( unsigned long ) xLength,
|
||||
( unsigned long ) ipconfigDNS_CACHE_NAME_LENGTH ) );
|
||||
}
|
||||
}
|
||||
}
|
||||
if( ( pcHostName != NULL ) && ( xLengthOk != pdFALSE ) )
|
||||
#else
|
||||
if( pcHostName != NULL )
|
||||
#endif /* ( ipconfigUSE_DNS_CACHE != 0 ) */
|
||||
{
|
||||
/* If the supplied hostname is IP address, convert it to uint32_t
|
||||
and return. */
|
||||
@ -647,7 +669,7 @@ TickType_t uxWriteTimeOut_ticks = ipconfigDNS_SEND_BLOCK_TIME_TICKS;
|
||||
if( xDNSSocket != NULL )
|
||||
{
|
||||
/* Ideally we should check for the return value. But since we are passing
|
||||
correect parameters, and xDNSSocket is != NULL, the return value is
|
||||
correct parameters, and xDNSSocket is != NULL, the return value is
|
||||
going to be '0' i.e. success. Thus, return value is discarded */
|
||||
( void ) FreeRTOS_setsockopt( xDNSSocket, 0, FREERTOS_SO_SNDTIMEO, &( uxWriteTimeOut_ticks ), sizeof( TickType_t ) );
|
||||
( void ) FreeRTOS_setsockopt( xDNSSocket, 0, FREERTOS_SO_RCVTIMEO, &( uxReadTimeOut_ticks ), sizeof( TickType_t ) );
|
||||
@ -785,10 +807,12 @@ static const DNSMessage_t xDefaultPartDNSHeader =
|
||||
0 /* No additional authorities. */
|
||||
};
|
||||
|
||||
/* Copy in the const part of the header. */
|
||||
/* Copy in the const part of the header. Intentionally using different
|
||||
* pointers with memcpy() to put the information in to correct place. */
|
||||
( void ) memcpy( pucUDPPayloadBuffer, &( xDefaultPartDNSHeader ), sizeof( xDefaultPartDNSHeader ) );
|
||||
|
||||
/* Write in a unique identifier. */
|
||||
/* Write in a unique identifier. Cast the Payload Buffer to DNSMessage_t
|
||||
* to easily access fields of the DNS Message. */
|
||||
pxDNSMessageHeader = ipPOINTER_CAST( DNSMessage_t *, pucUDPPayloadBuffer );
|
||||
pxDNSMessageHeader->usIdentifier = ( uint16_t ) uxIdentifier;
|
||||
|
||||
@ -815,9 +839,7 @@ static const DNSMessage_t xDefaultPartDNSHeader =
|
||||
{
|
||||
pucByte++;
|
||||
|
||||
/* MISRA c 2012 rule 10.4 relaxed for increased readability.
|
||||
Not writing 46U instead of '.' */
|
||||
while( ( *pucByte != ( uint8_t ) 0U ) && ( *pucByte != ( uint8_t ) '.' ) )
|
||||
while( ( *pucByte != ( uint8_t ) 0U ) && ( *pucByte != ( uint8_t ) ASCII_BASELINE_DOT ) )
|
||||
{
|
||||
pucByte++;
|
||||
}
|
||||
@ -830,7 +852,8 @@ static const DNSMessage_t xDefaultPartDNSHeader =
|
||||
pucStart = pucByte;
|
||||
} while( *pucByte != ( uint8_t ) 0U );
|
||||
|
||||
/* Finish off the record. */
|
||||
/* Finish off the record. Cast the record onto DNSTail_t stucture to easily
|
||||
* access the fields of the DNS Message. */
|
||||
pxTail = ipPOINTER_CAST(DNSTail_t *, &( pucByte[ 1 ] ) );
|
||||
|
||||
#if defined( _lint ) || defined( __COVERITY__ )
|
||||
@ -1012,9 +1035,6 @@ when ipconfigDNS_USE_CALLBACKS == 1
|
||||
when ipconfigUSE_LLMNR == 1
|
||||
for testing purposes, by the module iot_test_freertos_tcp.c
|
||||
*/
|
||||
|
||||
/* MISRA c 2012 rule 8.7: Function below may be used by external
|
||||
callees as well. */
|
||||
uint32_t ulDNSHandlePacket( const NetworkBufferDescriptor_t *pxNetworkBuffer )
|
||||
{
|
||||
DNSMessage_t *pxDNSMessageHeader;
|
||||
@ -1076,6 +1096,8 @@ uint8_t *pucByte;
|
||||
size_t uxSourceBytesRemaining;
|
||||
uint16_t x, usDataLength, usQuestions;
|
||||
uint16_t usType = 0U;
|
||||
BaseType_t xReturn = pdTRUE;
|
||||
|
||||
#if( ipconfigUSE_LLMNR == 1 )
|
||||
uint16_t usClass = 0U;
|
||||
#endif
|
||||
@ -1087,13 +1109,14 @@ uint16_t usType = 0U;
|
||||
/* Ensure that the buffer is of at least minimal DNS message length. */
|
||||
if( uxBufferLength < sizeof( DNSMessage_t ) )
|
||||
{
|
||||
return dnsPARSE_ERROR;
|
||||
xReturn = pdFALSE;
|
||||
}
|
||||
|
||||
else
|
||||
{
|
||||
uxSourceBytesRemaining = uxBufferLength;
|
||||
|
||||
/* Parse the DNS message header.
|
||||
MISRA c 2012 rule 11.3 relaxed to make byte by byte traversal easier */
|
||||
/* Parse the DNS message header. Map the byte stream onto a structure
|
||||
* for easier access. */
|
||||
pxDNSMessageHeader = ipPOINTER_CAST( DNSMessage_t *, pucUDPPayloadBuffer );
|
||||
|
||||
/* Introduce a do {} while (0) to allow the use of breaks. */
|
||||
@ -1131,7 +1154,8 @@ uint16_t usType = 0U;
|
||||
/* Check for a malformed response. */
|
||||
if( uxResult == 0U )
|
||||
{
|
||||
return dnsPARSE_ERROR;
|
||||
xReturn = pdFALSE;
|
||||
break;
|
||||
}
|
||||
uxBytesRead += uxResult;
|
||||
pucByte = &( pucByte[ uxResult ] );
|
||||
@ -1147,7 +1171,8 @@ uint16_t usType = 0U;
|
||||
/* Check for a malformed response. */
|
||||
if( uxResult == 0U )
|
||||
{
|
||||
return dnsPARSE_ERROR;
|
||||
xReturn = pdFALSE;
|
||||
break;
|
||||
}
|
||||
uxBytesRead += uxResult;
|
||||
pucByte = &( pucByte[ uxResult ] );
|
||||
@ -1171,18 +1196,26 @@ uint16_t usType = 0U;
|
||||
}
|
||||
else
|
||||
{
|
||||
return dnsPARSE_ERROR;
|
||||
xReturn = pdFALSE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if( xReturn == pdFALSE )
|
||||
{
|
||||
/* No need to proceed. Break out of the do-while loop. */
|
||||
break;
|
||||
}
|
||||
|
||||
/* Search through the answer records. */
|
||||
pxDNSMessageHeader->usAnswers = FreeRTOS_ntohs( pxDNSMessageHeader->usAnswers );
|
||||
|
||||
if( ( pxDNSMessageHeader->usFlags & dnsRX_FLAGS_MASK ) == dnsEXPECTED_RX_FLAGS )
|
||||
{
|
||||
const uint16_t usCount = ( uint16_t ) ipconfigDNS_CACHE_ADDRESSES_PER_ENTRY;
|
||||
uint16_t usNumARecordsStored = 0;
|
||||
|
||||
for( x = 0U; ( x < pxDNSMessageHeader->usAnswers ) && ( x < usCount ); x++ )
|
||||
for( x = 0U; ( x < pxDNSMessageHeader->usAnswers ) && ( usNumARecordsStored < usCount ); x++ )
|
||||
{
|
||||
BaseType_t xDoAccept;
|
||||
|
||||
@ -1192,7 +1225,8 @@ uint16_t usType = 0U;
|
||||
/* Check for a malformed response. */
|
||||
if( uxResult == 0U )
|
||||
{
|
||||
return dnsPARSE_ERROR;
|
||||
xReturn = pdFALSE;
|
||||
break;
|
||||
}
|
||||
|
||||
uxBytesRead += uxResult;
|
||||
@ -1203,7 +1237,8 @@ uint16_t usType = 0U;
|
||||
is this an A record? */
|
||||
if( uxSourceBytesRemaining < sizeof( uint16_t ) )
|
||||
{
|
||||
return dnsPARSE_ERROR;
|
||||
xReturn = pdFALSE;
|
||||
break;
|
||||
}
|
||||
usType = usChar2u16( pucByte );
|
||||
|
||||
@ -1223,20 +1258,19 @@ uint16_t usType = 0U;
|
||||
/* Unknown host type. */
|
||||
xDoAccept = pdFALSE;
|
||||
}
|
||||
|
||||
if( xDoAccept != pdFALSE )
|
||||
{
|
||||
/* This is the required record type and is of sufficient size. */
|
||||
/* MISRA c 2012 rule 11.3 relaxed. pucByte is used for byte-by-byte
|
||||
traversal. */
|
||||
/* Mapping pucByte to a DNSAnswerRecord allows easy access of the
|
||||
* fields of the structure. */
|
||||
pxDNSAnswerRecord = ipPOINTER_CAST( DNSAnswerRecord_t *, pucByte );
|
||||
|
||||
/* Sanity check the data length of an IPv4 answer. */
|
||||
if( FreeRTOS_ntohs( pxDNSAnswerRecord->usDataLength ) == ( uint16_t ) sizeof( uint32_t ) )
|
||||
{
|
||||
/* Copy the IP address out of the record. */
|
||||
/* MISRA c 2012 rule 21.15 relaxed here since this seems
|
||||
to be the least cumbersome way to get the IP address
|
||||
from the record. */
|
||||
/* Copy the IP address out of the record. Using different pointers
|
||||
* to copy only the portion we want is intentional here. */
|
||||
( void ) memcpy( &( ulIPAddress ),
|
||||
&( pucByte[ sizeof( DNSAnswerRecord_t ) ] ),
|
||||
sizeof( uint32_t ) );
|
||||
@ -1254,18 +1288,22 @@ uint16_t usType = 0U;
|
||||
#endif /* ipconfigDNS_USE_CALLBACKS == 1 */
|
||||
#if( ipconfigUSE_DNS_CACHE == 1 )
|
||||
{
|
||||
char cBuffer[ 16 ];
|
||||
|
||||
/* The reply will only be stored in the DNS cache when the
|
||||
request was issued by this device. */
|
||||
if( xDoStore != pdFALSE )
|
||||
{
|
||||
( void ) prvProcessDNSCache( pcName, &ulIPAddress, pxDNSAnswerRecord->ulTTL, pdFALSE );
|
||||
usNumARecordsStored++; /* Track # of A records stored */
|
||||
}
|
||||
|
||||
FreeRTOS_inet_ntop( FREERTOS_AF_INET, ( const void * ) &( ulIPAddress ), cBuffer, sizeof( cBuffer ) );
|
||||
/* Show what has happened. */
|
||||
FreeRTOS_printf( ( "DNS[0x%04lX]: The answer to '%s' (%lxip) will%s be stored\n",
|
||||
FreeRTOS_printf( ( "DNS[0x%04lX]: The answer to '%s' (%s) will%s be stored\n",
|
||||
( UBaseType_t ) pxDNSMessageHeader->usIdentifier,
|
||||
pcName,
|
||||
( UBaseType_t ) FreeRTOS_ntohl( ulIPAddress ),
|
||||
cBuffer,
|
||||
( xDoStore != 0 ) ? "" : " NOT" ) );
|
||||
}
|
||||
#endif /* ipconfigUSE_DNS_CACHE */
|
||||
@ -1278,9 +1316,7 @@ uint16_t usType = 0U;
|
||||
{
|
||||
/* It's not an A record, so skip it. Get the header location
|
||||
and then jump over the header. */
|
||||
|
||||
/* MISRA c 2012 rule 11.3 relaxed as pucByte is being used in
|
||||
various places to point to various parts of the DNS records */
|
||||
/* Cast the response to DNSAnswerRecord for easy access to fields of the DNS response. */
|
||||
pxDNSAnswerRecord = ipPOINTER_CAST( DNSAnswerRecord_t *, pucByte );
|
||||
|
||||
pucByte = &( pucByte[ sizeof( DNSAnswerRecord_t ) ] );
|
||||
@ -1298,7 +1334,8 @@ uint16_t usType = 0U;
|
||||
else
|
||||
{
|
||||
/* Malformed response. */
|
||||
return dnsPARSE_ERROR;
|
||||
xReturn = pdFALSE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
@ -1391,12 +1428,23 @@ uint16_t usType = 0U;
|
||||
#endif /* ipconfigUSE_LLMNR == 1 */
|
||||
( void ) uxBytesRead;
|
||||
} while( ipFALSE_BOOL );
|
||||
}
|
||||
|
||||
if( xExpected == pdFALSE )
|
||||
if( xReturn == pdFALSE )
|
||||
{
|
||||
/* There was an error while parsing the DNS response. Return error code. */
|
||||
ulIPAddress = dnsPARSE_ERROR;
|
||||
}
|
||||
else if( xExpected == pdFALSE )
|
||||
{
|
||||
/* Do not return a valid IP-address in case the reply was not expected. */
|
||||
ulIPAddress = 0UL;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* The IP-address found will be returned. */
|
||||
}
|
||||
|
||||
#if( ipconfigUSE_DNS_CACHE == 1 ) || ( ipconfigDNS_USE_CALLBACKS == 1 )
|
||||
( void ) xDoStore;
|
||||
#endif
|
||||
@ -1567,9 +1615,11 @@ BaseType_t xReturn;
|
||||
xSocket = FreeRTOS_socket( FREERTOS_AF_INET, FREERTOS_SOCK_DGRAM, FREERTOS_IPPROTO_UDP );
|
||||
if( ( xSocket == FREERTOS_INVALID_SOCKET ) || ( xSocket == NULL ) )
|
||||
{
|
||||
return NULL;
|
||||
/* There was an error, return NULL. */
|
||||
xSocket = NULL;
|
||||
}
|
||||
|
||||
else
|
||||
{
|
||||
/* Auto bind the port. */
|
||||
xAddress.sin_port = 0U;
|
||||
xReturn = FreeRTOS_bind( xSocket, &xAddress, sizeof( xAddress ) );
|
||||
@ -1584,6 +1634,7 @@ BaseType_t xReturn;
|
||||
{
|
||||
/* The send and receive timeouts will be set later on. */
|
||||
}
|
||||
}
|
||||
|
||||
return xSocket;
|
||||
}
|
||||
@ -1651,9 +1702,6 @@ BaseType_t xReturn;
|
||||
uint32_t ulIPAddressIndex = 0;
|
||||
static BaseType_t xFreeEntry = 0;
|
||||
|
||||
/* MISRA advisory rule 1.2 Relaxed in case of
|
||||
configASSERT as using __FUNCTION__ makes
|
||||
debugging easier */
|
||||
configASSERT( ( pcName != NULL ) );
|
||||
|
||||
/* For each entry in the DNS cache table. */
|
||||
@ -1736,7 +1784,7 @@ BaseType_t xReturn;
|
||||
xDNSCache[ xFreeEntry ].ucCurrentIPAddress = 0;
|
||||
|
||||
/* Initialize all remaining IP addresses in this entry to 0 */
|
||||
memset( &xDNSCache[ xFreeEntry ].ulIPAddresses[ 1 ],
|
||||
( void ) memset( &xDNSCache[ xFreeEntry ].ulIPAddresses[ 1 ],
|
||||
0,
|
||||
sizeof( xDNSCache[ xFreeEntry ].ulIPAddresses[ 1 ] ) *
|
||||
( ( uint32_t ) ipconfigDNS_CACHE_ADDRESSES_PER_ENTRY - 1U ) );
|
||||
|
@ -798,7 +798,7 @@ const TickType_t xDontBlock = ( TickType_t ) 0;
|
||||
iptraceNETWORK_DOWN();
|
||||
}
|
||||
/*-----------------------------------------------------------*/
|
||||
|
||||
/* Utility function. Process Network Down event from ISR. */
|
||||
BaseType_t FreeRTOS_NetworkDownFromISR( void )
|
||||
{
|
||||
static const IPStackEvent_t xNetworkDownEvent = { eNetworkDownEvent, NULL };
|
||||
@ -1288,6 +1288,7 @@ eFrameProcessingResult_t eConsiderFrameForProcessing( const uint8_t * const pucE
|
||||
eFrameProcessingResult_t eReturn;
|
||||
const EthernetHeader_t *pxEthernetHeader;
|
||||
|
||||
/* Map the buffer onto Ethernet Header struct for easy access to fields. */
|
||||
pxEthernetHeader = ipPOINTER_CAST( const EthernetHeader_t *, pucEthernetBuffer );
|
||||
|
||||
if( memcmp( ipLOCAL_MAC_ADDRESS, pxEthernetHeader->xDestinationAddress.ucBytes, sizeof( MACAddress_t ) ) == 0 )
|
||||
@ -1427,6 +1428,8 @@ eFrameProcessingResult_t eReturned = eReleaseBuffer;
|
||||
if( pxNetworkBuffer->xDataLength >= sizeof( EthernetHeader_t ) )
|
||||
{
|
||||
eReturned = ipCONSIDER_FRAME_FOR_PROCESSING( pxNetworkBuffer->pucEthernetBuffer );
|
||||
|
||||
/* Map the buffer onto the Ethernet Header struct for easy access to the fields. */
|
||||
pxEthernetHeader = ipPOINTER_CAST( const EthernetHeader_t *, pxNetworkBuffer->pucEthernetBuffer );
|
||||
|
||||
/* The condition "eReturned == eProcessBuffer" must be true. */
|
||||
@ -1688,9 +1691,10 @@ uint8_t ucProtocol;
|
||||
if( ( uxHeaderLength > ( pxNetworkBuffer->xDataLength - ipSIZE_OF_ETH_HEADER ) ) ||
|
||||
( uxHeaderLength < ipSIZE_OF_IPv4_HEADER ) )
|
||||
{
|
||||
return eReleaseBuffer;
|
||||
eReturn = eReleaseBuffer;
|
||||
}
|
||||
|
||||
else
|
||||
{
|
||||
ucProtocol = pxIPPacket->xIPHeader.ucProtocol;
|
||||
/* Check if the IP headers are acceptable and if it has our destination. */
|
||||
eReturn = prvAllowIPPacket( pxIPPacket, pxNetworkBuffer, uxHeaderLength );
|
||||
@ -1725,11 +1729,13 @@ uint8_t ucProtocol;
|
||||
{
|
||||
/* 'ipconfigIP_PASS_PACKETS_WITH_IP_OPTIONS' is not set, so packets carrying
|
||||
IP-options will be dropped. */
|
||||
return eReleaseBuffer;
|
||||
eReturn = eReleaseBuffer;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if( eReturn != eReleaseBuffer )
|
||||
{
|
||||
/* Add the IP and MAC addresses to the ARP table if they are not
|
||||
already there - otherwise refresh the age of the existing
|
||||
entry. */
|
||||
@ -1754,6 +1760,8 @@ uint8_t ucProtocol;
|
||||
{
|
||||
if( pxNetworkBuffer->xDataLength >= sizeof( ICMPPacket_t ) )
|
||||
{
|
||||
/* Map the buffer onto a ICMP-Packet struct to easily access the
|
||||
* fields of ICMP packet. */
|
||||
ICMPPacket_t *pxICMPPacket = ipPOINTER_CAST( ICMPPacket_t *, pxNetworkBuffer->pucEthernetBuffer );
|
||||
if( pxIPHeader->ulDestinationIPAddress == *ipLOCAL_IP_ADDRESS_POINTER )
|
||||
{
|
||||
@ -1771,6 +1779,9 @@ uint8_t ucProtocol;
|
||||
case ipPROTOCOL_UDP :
|
||||
{
|
||||
/* The IP packet contained a UDP frame. */
|
||||
|
||||
/* Map the buffer onto a UDP-Packet struct to easily access the
|
||||
* fields of UDP packet. */
|
||||
const UDPPacket_t *pxUDPPacket = ipPOINTER_CAST( const UDPPacket_t *, pxNetworkBuffer->pucEthernetBuffer );
|
||||
uint16_t usLength;
|
||||
|
||||
@ -1840,6 +1851,8 @@ uint8_t ucProtocol;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return eReturn;
|
||||
}
|
||||
@ -1995,7 +2008,8 @@ uint8_t ucProtocol;
|
||||
break;
|
||||
}
|
||||
|
||||
/* Parse the packet length. */
|
||||
/* Map the buffer onto a IP-Packet struct to easily access the
|
||||
* fields of the IP packet. */
|
||||
pxIPPacket = ipPOINTER_CAST( const IPPacket_t *, pucEthernetBuffer );
|
||||
|
||||
ucVersionHeaderLength = pxIPPacket->xIPHeader.ucVersionHeaderLength;
|
||||
@ -2028,11 +2042,13 @@ uint8_t ucProtocol;
|
||||
/* Identify the next protocol. */
|
||||
ucProtocol = pxIPPacket->xIPHeader.ucProtocol;
|
||||
|
||||
/* N.B., if this IP packet header includes Options, then the following
|
||||
/* If this IP packet header includes Options, then the following
|
||||
assignment results in a pointer into the protocol packet with the Ethernet
|
||||
and IP headers incorrectly aligned. However, either way, the "third"
|
||||
protocol (Layer 3 or 4) header will be aligned, which is the convenience
|
||||
of this calculation. */
|
||||
/* Map the Buffer onto the Protocol Packet struct for easy access to the
|
||||
* struct fields. */
|
||||
pxProtPack = ipPOINTER_CAST( ProtocolPacket_t *, &( pucEthernetBuffer[ uxIPHeaderLength - ipSIZE_OF_IPv4_HEADER ] ) );
|
||||
|
||||
/* Switch on the Layer 3/4 protocol. */
|
||||
@ -2104,12 +2120,16 @@ uint16_t ucVersionHeaderLength;
|
||||
|
||||
BaseType_t location = 0;
|
||||
|
||||
/* Introduce a do-while loop to allow use of break statements.
|
||||
* Note: MISRA prohibits use of 'goto', thus replaced with breaks. */
|
||||
do
|
||||
{
|
||||
/* Check for minimum packet size. */
|
||||
if( uxBufferLength < sizeof( IPPacket_t ) )
|
||||
{
|
||||
usChecksum = ipINVALID_LENGTH;
|
||||
location = 1;
|
||||
goto error_exit;
|
||||
break;
|
||||
}
|
||||
|
||||
/* Parse the packet length. */
|
||||
@ -2126,7 +2146,7 @@ BaseType_t location = 0;
|
||||
{
|
||||
usChecksum = ipINVALID_LENGTH;
|
||||
location = 2;
|
||||
goto error_exit;
|
||||
break;
|
||||
}
|
||||
usLength = pxIPPacket->xIPHeader.usLength;
|
||||
usLength = FreeRTOS_ntohs( usLength );
|
||||
@ -2134,7 +2154,7 @@ BaseType_t location = 0;
|
||||
{
|
||||
usChecksum = ipINVALID_LENGTH;
|
||||
location = 3;
|
||||
goto error_exit;
|
||||
break;
|
||||
}
|
||||
|
||||
/* Identify the next protocol. */
|
||||
@ -2154,7 +2174,7 @@ BaseType_t location = 0;
|
||||
{
|
||||
usChecksum = ipINVALID_LENGTH;
|
||||
location = 4;
|
||||
goto error_exit;
|
||||
break;
|
||||
}
|
||||
|
||||
pusChecksum = ( uint16_t * ) ( &( pxProtPack->xUDPPacket.xUDPHeader.usChecksum ) );
|
||||
@ -2170,7 +2190,7 @@ BaseType_t location = 0;
|
||||
{
|
||||
usChecksum = ipINVALID_LENGTH;
|
||||
location = 5;
|
||||
goto error_exit;
|
||||
break;
|
||||
}
|
||||
|
||||
pusChecksum = ( uint16_t * ) ( &( pxProtPack->xTCPPacket.xTCPHeader.usChecksum ) );
|
||||
@ -2187,7 +2207,7 @@ BaseType_t location = 0;
|
||||
{
|
||||
usChecksum = ipINVALID_LENGTH;
|
||||
location = 6;
|
||||
goto error_exit;
|
||||
break;
|
||||
}
|
||||
|
||||
pusChecksum = ( uint16_t * ) ( &( pxProtPack->xICMPPacket.xICMPHeader.usChecksum ) );
|
||||
@ -2209,7 +2229,7 @@ BaseType_t location = 0;
|
||||
/* Unhandled protocol, other than ICMP, IGMP, UDP, or TCP. */
|
||||
usChecksum = ipUNHANDLED_PROTOCOL;
|
||||
location = 7;
|
||||
goto error_exit;
|
||||
break;
|
||||
}
|
||||
|
||||
/* The protocol and checksum field have been identified. Check the direction
|
||||
@ -2247,7 +2267,7 @@ BaseType_t location = 0;
|
||||
}
|
||||
#endif
|
||||
location = 8;
|
||||
goto error_exit;
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -2274,7 +2294,7 @@ BaseType_t location = 0;
|
||||
format/length */
|
||||
usChecksum = ipINVALID_LENGTH;
|
||||
location = 9;
|
||||
goto error_exit;
|
||||
break;
|
||||
}
|
||||
if( ucProtocol <= ( uint8_t ) ipPROTOCOL_IGMP )
|
||||
{
|
||||
@ -2344,8 +2364,7 @@ BaseType_t location = 0;
|
||||
/* Nothing. */
|
||||
}
|
||||
#endif /* ipconfigHAS_DEBUG_PRINTF != 0 */
|
||||
|
||||
error_exit:
|
||||
} while( ipFALSE_BOOL );
|
||||
|
||||
if( ( usChecksum == ipUNHANDLED_PROTOCOL ) ||
|
||||
( usChecksum == ipINVALID_LENGTH ) )
|
||||
@ -2482,7 +2501,9 @@ size_t uxDataLengthBytes = uxByteCount;
|
||||
xLastSource.u8ptr = ( uint8_t * ) ( xSource.u8ptr + ( uxDataLengthBytes & ~( ( size_t ) 1 ) ) );
|
||||
|
||||
/* Half-word aligned. */
|
||||
/* The operator "<" is being applied to the pointers "xSource.u16ptr" and "xLastSource.u16ptr", which do not point into the same object. */
|
||||
/* Coverity does not like Unions. Warning issued here: "The operator "<"
|
||||
* is being applied to the pointers "xSource.u16ptr" and "xLastSource.u16ptr",
|
||||
* which do not point into the same object." */
|
||||
while( xSource.u16ptr < xLastSource.u16ptr )
|
||||
{
|
||||
/* At least one more short. */
|
||||
@ -2516,6 +2537,8 @@ size_t uxDataLengthBytes = uxByteCount;
|
||||
}
|
||||
/*-----------------------------------------------------------*/
|
||||
|
||||
/* This function is used in other files, has external linkage e.g. in
|
||||
* FreeRTOS_DNS.c. Not to be made static. */
|
||||
void vReturnEthernetFrame( NetworkBufferDescriptor_t * pxNetworkBuffer, BaseType_t xReleaseAfterSend )
|
||||
{
|
||||
EthernetHeader_t *pxEthernetHeader;
|
||||
@ -2554,6 +2577,7 @@ EthernetHeader_t *pxEthernetHeader;
|
||||
if( pxNetworkBuffer != NULL )
|
||||
#endif
|
||||
{
|
||||
/* Map the Buffer to Ethernet Header struct for easy access to fields. */
|
||||
pxEthernetHeader = ipPOINTER_CAST( EthernetHeader_t *, pxNetworkBuffer->pucEthernetBuffer );
|
||||
|
||||
/* Swap source and destination MAC addresses. */
|
||||
@ -2769,7 +2793,8 @@ BaseType_t FreeRTOS_IsNetworkUp( void )
|
||||
}
|
||||
#endif
|
||||
/*-----------------------------------------------------------*/
|
||||
|
||||
/* Utility function: Convert error number to a human readable
|
||||
* string. Decalartion in FreeRTOS_errno_TCP.h. */
|
||||
const char *FreeRTOS_strerror_r( BaseType_t xErrnum, char *pcBuffer, size_t uxLength )
|
||||
{
|
||||
const char *pcName;
|
||||
|
@ -874,6 +874,9 @@ NetworkBufferDescriptor_t xTempBuffer;
|
||||
usPacketIdentifier++;
|
||||
pxIPHeader->usFragmentOffset = 0U;
|
||||
|
||||
/* Important: tell NIC driver how many bytes must be sent. */
|
||||
pxNetworkBuffer->xDataLength = ulLen + ipSIZE_OF_ETH_HEADER;
|
||||
|
||||
#if( ipconfigDRIVER_INCLUDED_TX_IP_CHECKSUM == 0 )
|
||||
{
|
||||
/* calculate the IP header checksum, in case the driver won't do that. */
|
||||
@ -899,9 +902,6 @@ NetworkBufferDescriptor_t xTempBuffer;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Important: tell NIC driver how many bytes must be sent. */
|
||||
pxNetworkBuffer->xDataLength = ulLen + ipSIZE_OF_ETH_HEADER;
|
||||
|
||||
/* Fill in the destination MAC addresses. */
|
||||
( void ) memcpy( &( pxEthernetHeader->xDestinationAddress ),
|
||||
&( pxEthernetHeader->xSourceAddress ),
|
||||
@ -2000,6 +2000,7 @@ int32_t lCount, lLength;
|
||||
|
||||
/* A txStream has been created already, see if the socket has new data for
|
||||
the sliding window.
|
||||
|
||||
uxStreamBufferMidSpace() returns the distance between rxHead and rxMid. It
|
||||
contains new Tx data which has not been passed to the sliding window yet.
|
||||
The oldest data not-yet-confirmed can be found at rxTail. */
|
||||
@ -2009,6 +2010,7 @@ int32_t lCount, lLength;
|
||||
{
|
||||
/* All data between txMid and rxHead will now be passed to the sliding
|
||||
window manager, so it can start transmitting them.
|
||||
|
||||
Hand over the new data to the sliding window handler. It will be
|
||||
split-up in chunks of 1460 bytes each (or less, depending on
|
||||
ipconfigTCP_MSS). */
|
||||
@ -2141,6 +2143,7 @@ uint16_t usLength;
|
||||
|
||||
/* Determine the length and the offset of the user-data sent to this
|
||||
node.
|
||||
|
||||
The size of the TCP header is given in a multiple of 4-byte words (single
|
||||
byte, needs no ntoh() translation). A shift-right 2: is the same as
|
||||
(offset >> 4) * 4. */
|
||||
@ -2216,6 +2219,7 @@ BaseType_t xResult = 0;
|
||||
{
|
||||
/* See if way may accept the data contents and forward it to the socket
|
||||
owner.
|
||||
|
||||
If it can't be "accept"ed it may have to be stored and send a selective
|
||||
ack (SACK) option to confirm it. In that case, lTCPAddRxdata() will be
|
||||
called later to store an out-of-order packet (in case lOffset is
|
||||
@ -3504,3 +3508,4 @@ const ListItem_t *pxEndTCP = ipPOINTER_CAST( const ListItem_t *, listGET_END_MAR
|
||||
#ifdef FREERTOS_TCP_ENABLE_VERIFICATION
|
||||
#include "aws_freertos_tcp_verification_access_tcp_define.h"
|
||||
#endif
|
||||
|
||||
|
@ -1910,8 +1910,8 @@ const int32_t l500ms = 500;
|
||||
|
||||
#if( ipconfigUSE_TCP_WIN == 0 )
|
||||
|
||||
static BaseType_t prvTCPWindowTxHasSpace( TCPWindow_t *pxWindow, uint32_t ulWindowSize );
|
||||
static BaseType_t prvTCPWindowTxHasSpace( TCPWindow_t *pxWindow, uint32_t ulWindowSize )
|
||||
static BaseType_t prvTCPWindowTxHasSpace( TCPWindow_t const * pxWindow, uint32_t ulWindowSize );
|
||||
static BaseType_t prvTCPWindowTxHasSpace( TCPWindow_t const * pxWindow, uint32_t ulWindowSize )
|
||||
{
|
||||
BaseType_t xReturn;
|
||||
|
||||
@ -1934,7 +1934,7 @@ const int32_t l500ms = 500;
|
||||
|
||||
BaseType_t xTCPWindowTxHasData( TCPWindow_t const *pxWindow, uint32_t ulWindowSize, TickType_t *pulDelay )
|
||||
{
|
||||
TCPSegment_t *pxSegment = &( pxWindow->xTxSegment );
|
||||
TCPSegment_t const *pxSegment = &( pxWindow->xTxSegment );
|
||||
BaseType_t xReturn;
|
||||
TickType_t ulAge, ulMaxAge;
|
||||
|
||||
|
@ -317,20 +317,25 @@ from the FreeRTOSIPConfig.h configuration header file. */
|
||||
#define ipconfigALLOW_SOCKET_SEND_WITHOUT_BIND 1
|
||||
#endif
|
||||
|
||||
|
||||
#ifndef ipconfigIP_PASS_PACKETS_WITH_IP_OPTIONS
|
||||
#define ipconfigIP_PASS_PACKETS_WITH_IP_OPTIONS 1
|
||||
#endif
|
||||
|
||||
#ifndef ipconfigUDP_PASS_ZERO_CHECKSUM_PACKETS
|
||||
#define ipconfigUDP_PASS_ZERO_CHECKSUM_PACKETS 0
|
||||
#endif
|
||||
|
||||
|
||||
/* Configuration to control whether packets with IP options,
|
||||
* received over the network, should be passed up to the
|
||||
* software stack OR should be dropped.
|
||||
* If set to 1, the stack accepts IP packets that contain IP options, but does
|
||||
* not process the options (IP options are not supported).
|
||||
* If set to 0, the stack will drop IP packets that contain IP options.
|
||||
*/
|
||||
#ifndef ipconfigIP_PASS_PACKETS_WITH_IP_OPTIONS
|
||||
#define ipconfigIP_PASS_PACKETS_WITH_IP_OPTIONS 1
|
||||
#endif
|
||||
|
||||
/* Configuration to control whether UDP packets with
|
||||
* checksum value of zero should be passed up the software
|
||||
* stack OR should be dropped.
|
||||
* If set to 1, the stack will accept UDP packets that have their checksum
|
||||
* value set to 0.
|
||||
* If set to 0, the stack will drop UDP packets that have their checksum value
|
||||
* set to 0.
|
||||
*/
|
||||
#ifndef ipconfigUDP_PASS_ZERO_CHECKSUM_PACKETS
|
||||
#define ipconfigUDP_PASS_ZERO_CHECKSUM_PACKETS 0
|
||||
#endif
|
||||
|
@ -304,6 +304,12 @@ BaseType_t FreeRTOS_IsNetworkUp( void );
|
||||
UBaseType_t uxGetMinimumIPQueueSpace( void );
|
||||
#endif
|
||||
|
||||
#if ( ipconfigHAS_PRINTF != 0 )
|
||||
extern void vPrintResourceStats( void );
|
||||
#else
|
||||
#define vPrintResourceStats() do {} while( ipFALSE_BOOL )
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Defined in FreeRTOS_Sockets.c
|
||||
* //_RB_ Don't think this comment is correct. If this is for internal use only it should appear after all the public API functions and not start with FreeRTOS_.
|
||||
|
@ -1,3 +1,28 @@
|
||||
/*
|
||||
* FreeRTOS+TCP V2.2.1
|
||||
* Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||
* this software and associated documentation files (the "Software"), to deal in
|
||||
* the Software without restriction, including without limitation the rights to
|
||||
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
|
||||
* the Software, and to permit persons to whom the Software is furnished to do so,
|
||||
* subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in all
|
||||
* copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
|
||||
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
||||
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
|
||||
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
|
||||
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
*
|
||||
* http://aws.amazon.com/freertos
|
||||
* http://www.FreeRTOS.org
|
||||
*/
|
||||
|
||||
/*
|
||||
* dump_packets.c
|
||||
* Used in the PC/Win project to dump Ethernet packets, along with some description.
|
||||
|
@ -1,3 +1,28 @@
|
||||
/*
|
||||
* FreeRTOS+TCP V2.2.1
|
||||
* Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||
* this software and associated documentation files (the "Software"), to deal in
|
||||
* the Software without restriction, including without limitation the rights to
|
||||
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
|
||||
* the Software, and to permit persons to whom the Software is furnished to do so,
|
||||
* subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in all
|
||||
* copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
|
||||
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
||||
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
|
||||
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
|
||||
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
*
|
||||
* http://aws.amazon.com/freertos
|
||||
* http://www.FreeRTOS.org
|
||||
*/
|
||||
|
||||
/*
|
||||
* tcp_mem_stats.h
|
||||
*/
|
||||
|
Reference in New Issue
Block a user