mirror of
https://git.savannah.nongnu.org/git/lwip.git
synced 2026-08-10 09:33:44 +08:00
Merge branch 'master' into ppp-new
This commit is contained in:
@@ -74,9 +74,6 @@
|
||||
#if (!LWIP_UDP && LWIP_UDPLITE)
|
||||
#error "If you want to use UDP Lite, you have to define LWIP_UDP=1 in your lwipopts.h"
|
||||
#endif
|
||||
#if (!LWIP_UDP && LWIP_SNMP)
|
||||
#error "If you want to use SNMP, you have to define LWIP_UDP=1 in your lwipopts.h"
|
||||
#endif
|
||||
#if (!LWIP_UDP && LWIP_DHCP)
|
||||
#error "If you want to use DHCP, you have to define LWIP_UDP=1 in your lwipopts.h"
|
||||
#endif
|
||||
@@ -143,7 +140,7 @@
|
||||
#if (LWIP_TCP && ((TCP_MAXRTX > 12) || (TCP_SYNMAXRTX > 12)))
|
||||
#error "If you want to use TCP, TCP_MAXRTX and TCP_SYNMAXRTX must less or equal to 12 (due to tcp_backoff table), so, you have to reduce them in your lwipopts.h"
|
||||
#endif
|
||||
#if (LWIP_TCP && TCP_LISTEN_BACKLOG && (TCP_DEFAULT_LISTEN_BACKLOG < 0) || (TCP_DEFAULT_LISTEN_BACKLOG > 0xff))
|
||||
#if (LWIP_TCP && TCP_LISTEN_BACKLOG && ((TCP_DEFAULT_LISTEN_BACKLOG < 0) || (TCP_DEFAULT_LISTEN_BACKLOG > 0xff)))
|
||||
#error "If you want to use TCP backlog, TCP_DEFAULT_LISTEN_BACKLOG must fit into an u8_t"
|
||||
#endif
|
||||
#if (LWIP_NETIF_API && (NO_SYS==1))
|
||||
@@ -185,7 +182,7 @@
|
||||
#if (DNS_LOCAL_HOSTLIST && !DNS_LOCAL_HOSTLIST_IS_DYNAMIC && !(defined(DNS_LOCAL_HOSTLIST_INIT)))
|
||||
#error "you have to define define DNS_LOCAL_HOSTLIST_INIT {{'host1', 0x123}, {'host2', 0x234}} to initialize DNS_LOCAL_HOSTLIST"
|
||||
#endif
|
||||
#if PPP_SUPPORT && !PPPOS_SUPPORT & !PPPOE_SUPPORT
|
||||
#if PPP_SUPPORT && !PPPOS_SUPPORT && !PPPOE_SUPPORT
|
||||
#error "PPP_SUPPORT needs either PPPOS_SUPPORT or PPPOE_SUPPORT turned on"
|
||||
#endif
|
||||
#if !LWIP_ETHERNET && (LWIP_ARP || PPPOE_SUPPORT)
|
||||
@@ -236,9 +233,6 @@
|
||||
#ifdef MEMP_NUM_TCPIP_MSG
|
||||
#error "MEMP_NUM_TCPIP_MSG option is deprecated. Remove it from your lwipopts.h."
|
||||
#endif
|
||||
#ifdef MEMP_NUM_API_MSG
|
||||
#error "MEMP_NUM_API_MSG option is deprecated. Remove it from your lwipopts.h."
|
||||
#endif
|
||||
#ifdef TCP_REXMIT_DEBUG
|
||||
#error "TCP_REXMIT_DEBUG option is deprecated. Remove it from your lwipopts.h."
|
||||
#endif
|
||||
|
||||
@@ -696,12 +696,18 @@ static void
|
||||
igmp_start_timer(struct igmp_group *group, u8_t max_time)
|
||||
{
|
||||
/* ensure the input value is > 0 */
|
||||
#ifdef LWIP_RAND
|
||||
if (max_time == 0) {
|
||||
max_time = 1;
|
||||
}
|
||||
#ifdef LWIP_RAND
|
||||
/* ensure the random value is > 0 */
|
||||
group->timer = (LWIP_RAND() % max_time);
|
||||
#else /* LWIP_RAND */
|
||||
/* ATTENTION: use this only if absolutely necessary! */
|
||||
group->timer = max_time / 2;
|
||||
if (group->timer == 0) {
|
||||
group->timer = 1;
|
||||
}
|
||||
#endif /* LWIP_RAND */
|
||||
}
|
||||
|
||||
|
||||
@@ -48,6 +48,7 @@
|
||||
#include "lwip/igmp.h"
|
||||
#include "lwip/api.h"
|
||||
#include "lwip/api_msg.h"
|
||||
#include "lwip/sockets.h"
|
||||
#include "lwip/tcpip.h"
|
||||
#include "lwip/sys.h"
|
||||
#include "lwip/timers.h"
|
||||
|
||||
@@ -890,12 +890,12 @@ pbuf_copy(struct pbuf *p_to, struct pbuf *p_from)
|
||||
|
||||
if((p_from != NULL) && (p_from->len == p_from->tot_len)) {
|
||||
/* don't copy more than one packet! */
|
||||
LWIP_ERROR("pbuf_copy() does not allow packet queues!\n",
|
||||
LWIP_ERROR("pbuf_copy() does not allow packet queues!",
|
||||
(p_from->next == NULL), return ERR_VAL;);
|
||||
}
|
||||
if((p_to != NULL) && (p_to->len == p_to->tot_len)) {
|
||||
/* don't copy more than one packet! */
|
||||
LWIP_ERROR("pbuf_copy() does not allow packet queues!\n",
|
||||
LWIP_ERROR("pbuf_copy() does not allow packet queues!",
|
||||
(p_to->next == NULL), return ERR_VAL;);
|
||||
}
|
||||
} while (p_from);
|
||||
@@ -952,6 +952,56 @@ pbuf_copy_partial(struct pbuf *buf, void *dataptr, u16_t len, u16_t offset)
|
||||
return copied_total;
|
||||
}
|
||||
|
||||
#if LWIP_TCP && TCP_QUEUE_OOSEQ && LWIP_WND_SCALE
|
||||
/**
|
||||
* This method modifies a 'pbuf chain', so that its total length is
|
||||
* smaller than 64K. The remainder of the original pbuf chain is stored
|
||||
* in *rest.
|
||||
* This function never creates new pbufs, but splits an existing chain
|
||||
* in two parts. The tot_len of the modified packet queue will likely be
|
||||
* smaller than 64K.
|
||||
* 'packet queues' are not supported by this function.
|
||||
*
|
||||
* @param p the pbuf queue to be splitted
|
||||
* @param rest pointer to store the remainder (after the first 64K)
|
||||
*/
|
||||
void pbuf_split_64k(struct pbuf *p, struct pbuf **rest)
|
||||
{
|
||||
*rest = NULL;
|
||||
if ((p != NULL) && (p->next != NULL)) {
|
||||
u16_t tot_len_front = p->len;
|
||||
struct pbuf *i = p;
|
||||
struct pbuf *r = p->next;
|
||||
|
||||
/* continue until the total length (summed up as u16_t) overflows */
|
||||
while ((r != NULL) && ((u16_t)(tot_len_front + r->len) > tot_len_front)) {
|
||||
tot_len_front += r->len;
|
||||
i = r;
|
||||
r = r->next;
|
||||
}
|
||||
/* i now points to last packet of the first segment. Set next
|
||||
pointer to NULL */
|
||||
i->next = NULL;
|
||||
|
||||
if (r != NULL) {
|
||||
/* Update the tot_len field in the first part */
|
||||
for (i = p; i != NULL; i = i->next) {
|
||||
i->tot_len -= r->tot_len;
|
||||
LWIP_ASSERT("tot_len/len mismatch in last pbuf",
|
||||
(i->next != NULL) || (i->tot_len == i->len));
|
||||
}
|
||||
if (p->flags & PBUF_FLAG_TCP_FIN) {
|
||||
r->flags |= PBUF_FLAG_TCP_FIN;
|
||||
}
|
||||
|
||||
/* tot_len field in rest does not need modifications */
|
||||
/* reference counters do not need modifications */
|
||||
*rest = r;
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif /* LWIP_TCP && TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
|
||||
/**
|
||||
* Copy application supplied data into a pbuf.
|
||||
* This function can only be used to copy the equivalent of buf->tot_len data.
|
||||
|
||||
@@ -51,6 +51,7 @@
|
||||
#include "arch/perf.h"
|
||||
#include "lwip/ip6.h"
|
||||
#include "lwip/ip6_addr.h"
|
||||
#include "lwip/inet_chksum.h"
|
||||
|
||||
#include <string.h>
|
||||
|
||||
@@ -313,6 +314,16 @@ raw_sendto(struct raw_pcb *pcb, struct pbuf *p, ip_addr_t *ipaddr)
|
||||
src_ip = &pcb->local_ip;
|
||||
}
|
||||
|
||||
#if LWIP_IPV6
|
||||
/* If requested, based on the IPV6_CHECKSUM socket option per RFC3542,
|
||||
compute the checksum and update the checksum in the payload. */
|
||||
if (PCB_ISIPV6(pcb) && pcb->chksum_reqd) {
|
||||
u16_t chksum;
|
||||
chksum = ip6_chksum_pseudo(q, pcb->protocol, q->tot_len, ipX_2_ip6(src_ip), ipX_2_ip6(dst_ip));
|
||||
*(u16_t *)(((u8_t *)q->payload) + pcb->chksum_offset) = chksum;
|
||||
}
|
||||
#endif
|
||||
|
||||
NETIF_SET_HWADDRHINT(netif, &pcb->addr_hint);
|
||||
err = ipX_output_if(PCB_ISIPV6(pcb), q, ipX_2_ip(src_ip), ipX_2_ip(dst_ip), pcb->ttl, pcb->tos, pcb->protocol, netif);
|
||||
NETIF_SET_HWADDRHINT(netif, NULL);
|
||||
|
||||
@@ -51,6 +51,8 @@
|
||||
#include "lwip/sys.h"
|
||||
#include "netif/etharp.h"
|
||||
|
||||
#include <string.h>
|
||||
|
||||
/**
|
||||
* IANA assigned enterprise ID for lwIP is 26381
|
||||
* @see http://www.iana.org/assignments/enterprise-numbers
|
||||
@@ -763,7 +765,8 @@ const struct mib_array_node internet = {
|
||||
#endif
|
||||
|
||||
/** mib-2.system.sysObjectID */
|
||||
static struct snmp_obj_id sysobjid = {SNMP_SYSOBJID_LEN, SNMP_SYSOBJID};
|
||||
static const struct snmp_obj_id sysobjid_default = {SNMP_SYSOBJID_LEN, SNMP_SYSOBJID};
|
||||
static const struct snmp_obj_id* sysobjid_ptr = &sysobjid_default;
|
||||
/** enterprise ID for generic TRAPs, .iso.org.dod.internet.mgmt.mib-2.snmp */
|
||||
static struct snmp_obj_id snmpgrp_id = {7,{1,3,6,1,2,1,11}};
|
||||
/** mib-2.system.sysServices */
|
||||
@@ -893,40 +896,6 @@ static u32_t snmpinpkts = 0,
|
||||
snmpouttraps = 0;
|
||||
|
||||
|
||||
|
||||
/* prototypes of the following functions are in lwip/src/include/lwip/snmp.h */
|
||||
/**
|
||||
* Copy octet string.
|
||||
*
|
||||
* @param dst points to destination
|
||||
* @param src points to source
|
||||
* @param n number of octets to copy.
|
||||
*/
|
||||
static void ocstrncpy(u8_t *dst, const u8_t *src, u16_t n)
|
||||
{
|
||||
u16_t i = n;
|
||||
while (i > 0) {
|
||||
i--;
|
||||
*dst++ = *src++;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Copy object identifier (s32_t) array.
|
||||
*
|
||||
* @param dst points to destination
|
||||
* @param src points to source
|
||||
* @param n number of sub identifiers to copy.
|
||||
*/
|
||||
void objectidncpy(s32_t *dst, const s32_t *src, u8_t n)
|
||||
{
|
||||
u8_t i = n;
|
||||
while(i > 0) {
|
||||
i--;
|
||||
*dst++ = *src++;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Initializes sysDescr pointers.
|
||||
*
|
||||
@@ -942,9 +911,9 @@ void snmp_set_sysdescr(const u8_t *str, const u8_t *len)
|
||||
}
|
||||
}
|
||||
|
||||
void snmp_get_sysobjid_ptr(struct snmp_obj_id **oid)
|
||||
void snmp_get_sysobjid_ptr(const struct snmp_obj_id **oid)
|
||||
{
|
||||
*oid = &sysobjid;
|
||||
*oid = sysobjid_ptr;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -952,9 +921,9 @@ void snmp_get_sysobjid_ptr(struct snmp_obj_id **oid)
|
||||
*
|
||||
* @param oid points to stuct snmp_obj_id to copy
|
||||
*/
|
||||
void snmp_set_sysobjid(struct snmp_obj_id *oid)
|
||||
void snmp_set_sysobjid(const struct snmp_obj_id *oid)
|
||||
{
|
||||
sysobjid = *oid;
|
||||
sysobjid_ptr = oid;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -2141,7 +2110,7 @@ system_get_object_def(u8_t ident_len, s32_t *ident, struct obj_def *od)
|
||||
od->instance = MIB_OBJECT_SCALAR;
|
||||
od->access = MIB_OBJECT_READ_ONLY;
|
||||
od->asn_type = (SNMP_ASN1_UNIV | SNMP_ASN1_PRIMIT | SNMP_ASN1_OBJ_ID);
|
||||
od->v_len = sysobjid.len * sizeof(s32_t);
|
||||
od->v_len = sysobjid_ptr->len * sizeof(s32_t);
|
||||
break;
|
||||
case 3: /* sysUpTime */
|
||||
od->instance = MIB_OBJECT_SCALAR;
|
||||
@@ -2204,10 +2173,10 @@ system_get_value(struct obj_def *od, u16_t len, void *value)
|
||||
switch (id)
|
||||
{
|
||||
case 1: /* sysDescr */
|
||||
ocstrncpy((u8_t*)value, sysdescr_ptr, len);
|
||||
MEMCPY(value, sysdescr_ptr, len);
|
||||
break;
|
||||
case 2: /* sysObjectID */
|
||||
objectidncpy((s32_t*)value, (s32_t*)sysobjid.id, (u8_t)(len / sizeof(s32_t)));
|
||||
MEMCPY(value, sysobjid_ptr->id, len);
|
||||
break;
|
||||
case 3: /* sysUpTime */
|
||||
{
|
||||
@@ -2215,13 +2184,13 @@ system_get_value(struct obj_def *od, u16_t len, void *value)
|
||||
}
|
||||
break;
|
||||
case 4: /* sysContact */
|
||||
ocstrncpy((u8_t*)value, syscontact_ptr, len);
|
||||
MEMCPY(value, syscontact_ptr, len);
|
||||
break;
|
||||
case 5: /* sysName */
|
||||
ocstrncpy((u8_t*)value, sysname_ptr, len);
|
||||
MEMCPY(value, sysname_ptr, len);
|
||||
break;
|
||||
case 6: /* sysLocation */
|
||||
ocstrncpy((u8_t*)value, syslocation_ptr, len);
|
||||
MEMCPY(value, syslocation_ptr, len);
|
||||
break;
|
||||
case 7: /* sysServices */
|
||||
{
|
||||
@@ -2279,15 +2248,15 @@ system_set_value(struct obj_def *od, u16_t len, void *value)
|
||||
switch (id)
|
||||
{
|
||||
case 4: /* sysContact */
|
||||
ocstrncpy(syscontact_ptr, (u8_t*)value, len);
|
||||
MEMCPY(syscontact_ptr, value, len);
|
||||
*syscontact_len_ptr = (u8_t)len;
|
||||
break;
|
||||
case 5: /* sysName */
|
||||
ocstrncpy(sysname_ptr, (u8_t*)value, len);
|
||||
MEMCPY(sysname_ptr, value, len);
|
||||
*sysname_len_ptr = (u8_t)len;
|
||||
break;
|
||||
case 6: /* sysLocation */
|
||||
ocstrncpy(syslocation_ptr, (u8_t*)value, len);
|
||||
MEMCPY(syslocation_ptr, value, len);
|
||||
*syslocation_len_ptr = (u8_t)len;
|
||||
break;
|
||||
};
|
||||
@@ -2475,7 +2444,7 @@ ifentry_get_value(struct obj_def *od, u16_t len, void *value)
|
||||
}
|
||||
break;
|
||||
case 2: /* ifDescr */
|
||||
ocstrncpy((u8_t*)value, (u8_t*)netif->name, len);
|
||||
MEMCPY(value, netif->name, len);
|
||||
break;
|
||||
case 3: /* ifType */
|
||||
{
|
||||
@@ -2496,7 +2465,7 @@ ifentry_get_value(struct obj_def *od, u16_t len, void *value)
|
||||
}
|
||||
break;
|
||||
case 6: /* ifPhysAddress */
|
||||
ocstrncpy((u8_t*)value, netif->hwaddr, len);
|
||||
MEMCPY(value, netif->hwaddr, len);
|
||||
break;
|
||||
case 7: /* ifAdminStatus */
|
||||
{
|
||||
@@ -2608,7 +2577,7 @@ ifentry_get_value(struct obj_def *od, u16_t len, void *value)
|
||||
}
|
||||
break;
|
||||
case 22: /* ifSpecific */
|
||||
objectidncpy((s32_t*)value, (s32_t*)ifspecific.id, (u8_t)(len / sizeof(s32_t)));
|
||||
MEMCPY(value, ifspecific.id, len);
|
||||
break;
|
||||
};
|
||||
}
|
||||
@@ -3352,7 +3321,7 @@ ip_rteentry_get_value(struct obj_def *od, u16_t len, void *value)
|
||||
}
|
||||
break;
|
||||
case 13: /* ipRouteInfo */
|
||||
objectidncpy((s32_t*)value, (s32_t*)iprouteinfo.id, (u8_t)(len / sizeof(s32_t)));
|
||||
MEMCPY(value, iprouteinfo.id, len);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -737,13 +737,13 @@ snmp_expand_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct snm
|
||||
}
|
||||
else
|
||||
{
|
||||
u8_t j;
|
||||
u16_t j;
|
||||
struct nse cur_node;
|
||||
|
||||
LWIP_DEBUGF(SNMP_MIB_DEBUG,("non-leaf node\n"));
|
||||
/* non-leaf, store right child ptr and id */
|
||||
LWIP_ASSERT("i < 0xff", i < 0xff);
|
||||
j = (u8_t)i + 1;
|
||||
j = i + 1;
|
||||
while ((j < an->maxlength) && (empty_table(an->nptr[j])))
|
||||
{
|
||||
j++;
|
||||
@@ -781,7 +781,7 @@ snmp_expand_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct snm
|
||||
}
|
||||
else
|
||||
{
|
||||
u8_t j;
|
||||
u16_t j;
|
||||
/* ident_len == 0, complete with leftmost '.thing' */
|
||||
j = 0;
|
||||
while ((j < an->maxlength) && empty_table(an->nptr[j]))
|
||||
@@ -980,13 +980,13 @@ snmp_expand_tree(struct mib_node *node, u8_t ident_len, s32_t *ident, struct snm
|
||||
}
|
||||
else
|
||||
{
|
||||
u8_t j;
|
||||
u16_t j;
|
||||
struct nse cur_node;
|
||||
|
||||
LWIP_DEBUGF(SNMP_MIB_DEBUG,("non-leaf node\n"));
|
||||
/* non-leaf, store right child ptr and id */
|
||||
LWIP_ASSERT("i < 0xff", i < 0xff);
|
||||
j = (u8_t)i + 1;
|
||||
j = i + 1;
|
||||
if (j < len)
|
||||
{
|
||||
/* right node is the current external node */
|
||||
|
||||
@@ -1124,37 +1124,58 @@ tcp_fasttmr_start:
|
||||
err_t
|
||||
tcp_process_refused_data(struct tcp_pcb *pcb)
|
||||
{
|
||||
err_t err;
|
||||
u8_t refused_flags = pcb->refused_data->flags;
|
||||
/* set pcb->refused_data to NULL in case the callback frees it and then
|
||||
closes the pcb */
|
||||
struct pbuf *refused_data = pcb->refused_data;
|
||||
pcb->refused_data = NULL;
|
||||
/* Notify again application with data previously received. */
|
||||
LWIP_DEBUGF(TCP_INPUT_DEBUG, ("tcp_input: notify kept packet\n"));
|
||||
TCP_EVENT_RECV(pcb, refused_data, ERR_OK, err);
|
||||
if (err == ERR_OK) {
|
||||
/* did refused_data include a FIN? */
|
||||
if (refused_flags & PBUF_FLAG_TCP_FIN) {
|
||||
/* correct rcv_wnd as the application won't call tcp_recved()
|
||||
for the FIN's seqno */
|
||||
if (pcb->rcv_wnd != TCP_WND) {
|
||||
pcb->rcv_wnd++;
|
||||
#if TCP_QUEUE_OOSEQ && LWIP_WND_SCALE
|
||||
struct pbuf *rest;
|
||||
while (pcb->refused_data != NULL)
|
||||
#endif /* TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
{
|
||||
err_t err;
|
||||
u8_t refused_flags = pcb->refused_data->flags;
|
||||
/* set pcb->refused_data to NULL in case the callback frees it and then
|
||||
closes the pcb */
|
||||
struct pbuf *refused_data = pcb->refused_data;
|
||||
#if TCP_QUEUE_OOSEQ && LWIP_WND_SCALE
|
||||
pbuf_split_64k(refused_data, &rest);
|
||||
pcb->refused_data = rest;
|
||||
#else /* TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
pcb->refused_data = NULL;
|
||||
#endif /* TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
/* Notify again application with data previously received. */
|
||||
LWIP_DEBUGF(TCP_INPUT_DEBUG, ("tcp_input: notify kept packet\n"));
|
||||
TCP_EVENT_RECV(pcb, refused_data, ERR_OK, err);
|
||||
if (err == ERR_OK) {
|
||||
/* did refused_data include a FIN? */
|
||||
if (refused_flags & PBUF_FLAG_TCP_FIN
|
||||
#if TCP_QUEUE_OOSEQ && LWIP_WND_SCALE
|
||||
&& (rest == NULL)
|
||||
#endif /* TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
) {
|
||||
/* correct rcv_wnd as the application won't call tcp_recved()
|
||||
for the FIN's seqno */
|
||||
if (pcb->rcv_wnd != TCP_WND) {
|
||||
pcb->rcv_wnd++;
|
||||
}
|
||||
TCP_EVENT_CLOSED(pcb, err);
|
||||
if (err == ERR_ABRT) {
|
||||
return ERR_ABRT;
|
||||
}
|
||||
}
|
||||
TCP_EVENT_CLOSED(pcb, err);
|
||||
if (err == ERR_ABRT) {
|
||||
return ERR_ABRT;
|
||||
} else if (err == ERR_ABRT) {
|
||||
/* if err == ERR_ABRT, 'pcb' is already deallocated */
|
||||
/* Drop incoming packets because pcb is "full" (only if the incoming
|
||||
segment contains data). */
|
||||
LWIP_DEBUGF(TCP_INPUT_DEBUG, ("tcp_input: drop incoming packets, because pcb is \"full\"\n"));
|
||||
return ERR_ABRT;
|
||||
} else {
|
||||
/* data is still refused, pbuf is still valid (go on for ACK-only packets) */
|
||||
#if TCP_QUEUE_OOSEQ && LWIP_WND_SCALE
|
||||
if (rest != NULL) {
|
||||
pbuf_cat(refused_data, rest);
|
||||
}
|
||||
#endif /* TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
pcb->refused_data = refused_data;
|
||||
return ERR_INPROGRESS;
|
||||
}
|
||||
} else if (err == ERR_ABRT) {
|
||||
/* if err == ERR_ABRT, 'pcb' is already deallocated */
|
||||
/* Drop incoming packets because pcb is "full" (only if the incoming
|
||||
segment contains data). */
|
||||
LWIP_DEBUGF(TCP_INPUT_DEBUG, ("tcp_input: drop incoming packets, because pcb is \"full\"\n"));
|
||||
return ERR_ABRT;
|
||||
} else {
|
||||
/* data is still refused, pbuf is still valid (go on for ACK-only packets) */
|
||||
pcb->refused_data = refused_data;
|
||||
}
|
||||
return ERR_OK;
|
||||
}
|
||||
|
||||
@@ -348,7 +348,7 @@ tcp_input(struct pbuf *p, struct netif *inp)
|
||||
u16_t acked;
|
||||
#if LWIP_WND_SCALE
|
||||
/* pcb->acked is u32_t but the sent callback only takes a u16_t,
|
||||
so we might have to call it multiple timess. */
|
||||
so we might have to call it multiple times. */
|
||||
u32_t pcb_acked = pcb->acked;
|
||||
while(pcb_acked > 0) {
|
||||
acked = (u16_t)LWIP_MIN(pcb_acked, 0xffffu);
|
||||
@@ -364,12 +364,24 @@ tcp_input(struct pbuf *p, struct netif *inp)
|
||||
}
|
||||
}
|
||||
|
||||
#if TCP_QUEUE_OOSEQ && LWIP_WND_SCALE
|
||||
while (recv_data != NULL) {
|
||||
struct pbuf *rest = NULL;
|
||||
pbuf_split_64k(recv_data, &rest);
|
||||
#else /* TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
if (recv_data != NULL) {
|
||||
#endif /* TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
|
||||
LWIP_ASSERT("pcb->refused_data == NULL", pcb->refused_data == NULL);
|
||||
if (pcb->flags & TF_RXCLOSED) {
|
||||
/* received data although already closed -> abort (send RST) to
|
||||
notify the remote host that not all data has been processed */
|
||||
pbuf_free(recv_data);
|
||||
#if TCP_QUEUE_OOSEQ && LWIP_WND_SCALE
|
||||
if (rest != NULL) {
|
||||
pbuf_free(rest);
|
||||
}
|
||||
#endif /* TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
tcp_abort(pcb);
|
||||
goto aborted;
|
||||
}
|
||||
@@ -377,13 +389,29 @@ tcp_input(struct pbuf *p, struct netif *inp)
|
||||
/* Notify application that data has been received. */
|
||||
TCP_EVENT_RECV(pcb, recv_data, ERR_OK, err);
|
||||
if (err == ERR_ABRT) {
|
||||
#if TCP_QUEUE_OOSEQ && LWIP_WND_SCALE
|
||||
if (rest != NULL) {
|
||||
pbuf_free(rest);
|
||||
}
|
||||
#endif /* TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
goto aborted;
|
||||
}
|
||||
|
||||
/* If the upper layer can't receive this data, store it */
|
||||
if (err != ERR_OK) {
|
||||
#if TCP_QUEUE_OOSEQ && LWIP_WND_SCALE
|
||||
if (rest != NULL) {
|
||||
pbuf_cat(recv_data, rest);
|
||||
}
|
||||
#endif /* TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
pcb->refused_data = recv_data;
|
||||
LWIP_DEBUGF(TCP_INPUT_DEBUG, ("tcp_input: keep incoming packet, because pcb is \"full\"\n"));
|
||||
#if TCP_QUEUE_OOSEQ && LWIP_WND_SCALE
|
||||
break;
|
||||
} else {
|
||||
/* Upper layer received the data, go on with the rest if > 64K */
|
||||
recv_data = rest;
|
||||
#endif /* TCP_QUEUE_OOSEQ && LWIP_WND_SCALE */
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1382,6 +1410,9 @@ tcp_receive(struct tcp_pcb *pcb)
|
||||
if (cseg->p->tot_len > 0) {
|
||||
/* Chain this pbuf onto the pbuf that we will pass to
|
||||
the application. */
|
||||
/* With window scaling, this can overflow recv_data->tot_len, but
|
||||
that's not a problem since we explicitly fix that before passing
|
||||
recv_data to the application. */
|
||||
if (recv_data) {
|
||||
pbuf_cat(recv_data, cseg->p);
|
||||
} else {
|
||||
|
||||
@@ -789,7 +789,7 @@ tcp_enqueue_flags(struct tcp_pcb *pcb, u8_t flags)
|
||||
TCP_STATS_INC(tcp.memerr);
|
||||
return ERR_MEM;
|
||||
}
|
||||
LWIP_ASSERT("seg->tcphdr not aligned", ((mem_ptr_t)seg->tcphdr % MEM_ALIGNMENT) == 0);
|
||||
LWIP_ASSERT("seg->tcphdr not aligned", ((mem_ptr_t)seg->tcphdr % 4) == 0);
|
||||
LWIP_ASSERT("tcp_enqueue_flags: invalid segment length", seg->len == 0);
|
||||
|
||||
LWIP_DEBUGF(TCP_OUTPUT_DEBUG | LWIP_DBG_TRACE,
|
||||
|
||||
Reference in New Issue
Block a user