Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Menu
Open sidebar
ruanhaishen
Nodemcu Firmware
Commits
5d5be356
Commit
5d5be356
authored
Oct 12, 2015
by
Johny Mattsson
Browse files
Upgraded LWIP to 1.4.0 released from Espressif.
Plus directly provided patch for user_interface.h.
parent
711d464a
Changes
27
Hide whitespace changes
Inline
Side-by-side
app/include/lwip/app/dhcpserver.h
View file @
5d5be356
...
...
@@ -24,6 +24,7 @@ typedef struct dhcps_msg {
#ifndef LWIP_OPEN_SRC
struct
dhcps_lease
{
bool
enable
;
struct
ip_addr
start_ip
;
struct
ip_addr
end_ip
;
};
...
...
@@ -46,7 +47,8 @@ typedef struct _list_node{
struct
_list_node
*
pnext
;
}
list_node
;
#define DHCPS_LEASE_TIMER 0x05A0
extern
uint32
dhcps_lease_time
;
#define DHCPS_LEASE_TIMER dhcps_lease_time //0x05A0
#define DHCPS_MAX_LEASE 0x64
#define BOOTP_BROADCAST 0x8000
...
...
@@ -89,6 +91,7 @@ typedef struct _list_node{
#define DHCPS_STATE_ACK 3
#define DHCPS_STATE_NAK 4
#define DHCPS_STATE_IDLE 5
#define DHCPS_STATE_RELEASE 6
#define dhcps_router_enabled(offer) ((offer & OFFER_ROUTER) != 0)
...
...
app/include/lwip/app/espconn.h
View file @
5d5be356
...
...
@@ -30,6 +30,7 @@ typedef void (* espconn_reconnect_callback)(void *arg, sint8 err);
#define ESPCONN_CONN -11
/* Not connected. */
#define ESPCONN_ARG -12
/* Illegal argument. */
#define ESPCONN_IF -14
/* Low_level error */
#define ESPCONN_ISCONN -15
/* Already connected. */
#define ESPCONN_HANDSHAKE -28
/* ssl handshake failed */
...
...
@@ -168,7 +169,7 @@ typedef struct _espconn_msg{
struct
espconn
*
pespconn
;
comon_pkt
pcommon
;
uint8
count_opt
;
s
int16_t
hs_status
;
//the status of the handshake
int16_t
hs_status
;
//the status of the handshake
void
*
preverse
;
void
*
pssl
;
struct
_espconn_msg
*
pnext
;
...
...
app/include/lwip/app/espconn_udp.h
View file @
5d5be356
...
...
@@ -45,6 +45,19 @@ extern sint8 espconn_udp_server(struct espconn *espconn);
extern
err_t
espconn_udp_sent
(
void
*
arg
,
uint8
*
psent
,
uint16
length
);
/******************************************************************************
* FunctionName : espconn_udp_sendto
* Description : sent data for UDP
* Parameters : void *arg -- UDP to send
* uint8* psent -- Data to send
* uint16 length -- Length of data to send
* Returns : return espconn error code.
* - ESPCONN_OK. Successful. No error occured.
* - ESPCONN_MEM. Out of memory.
* - ESPCONN_RTE. Could not find route to destination address.
* - More errors could be returned by lower protocol layers.
*******************************************************************************/
extern
err_t
espconn_udp_sendto
(
void
*
arg
,
uint8
*
psent
,
uint16
length
);
#endif
/* __ESPCONN_UDP_H__ */
...
...
app/include/lwip/mem.h
View file @
5d5be356
...
...
@@ -33,7 +33,7 @@
#define __LWIP_MEM_H__
#include "lwip/opt.h"
#include "mem_manager.h"
//
#include "mem_manager.h"
#ifdef __cplusplus
extern
"C"
{
...
...
@@ -50,6 +50,7 @@ typedef size_t mem_size_t;
/* in case C library malloc() needs extra protection,
* allow these defines to be overridden.
*/
#ifndef MEMLEAK_DEBUG
#ifndef mem_free
#define mem_free vPortFree
#endif
...
...
@@ -64,6 +65,28 @@ typedef size_t mem_size_t;
#endif
#ifndef mem_zalloc
#define mem_zalloc pvPortZalloc
#endif
#else
#ifndef mem_free
#define mem_free(s) \
do{\
const char *file = mem_debug_file;\
vPortFree(s, file, __LINE__);\
}while(0)
#endif
#ifndef mem_malloc
#define mem_malloc(s) ({const char *file = mem_debug_file; pvPortMalloc(s, file, __LINE__);})
#endif
#ifndef mem_calloc
#define mem_calloc(s) ({const char *file = mem_debug_file; pvPortCalloc(s, file, __LINE__);})
#endif
#ifndef mem_realloc
#define mem_realloc(p, s) ({const char *file = mem_debug_file; pvPortRealloc(p, s, file, __LINE__);})
#endif
#ifndef mem_zalloc
#define mem_zalloc(s) ({const char *file = mem_debug_file; pvPortZalloc(s, file, __LINE__);})
#endif
#endif
#ifndef os_malloc
...
...
app/include/lwip/netif.h
View file @
5d5be356
...
...
@@ -130,6 +130,9 @@ typedef void (*netif_status_callback_fn)(struct netif *netif);
typedef
err_t
(
*
netif_igmp_mac_filter_fn
)(
struct
netif
*
netif
,
ip_addr_t
*
group
,
u8_t
action
);
/*add DHCP event processing by LiuHan*/
typedef
void
(
*
dhcp_event_fn
)(
void
);
/** Generic data structure used for all lwIP network interfaces.
* The following fields should be filled in by the initialization
* function for the device driver: hwaddr_len, hwaddr[], mtu, flags */
...
...
@@ -170,7 +173,7 @@ struct netif {
/** the DHCP client state information for this netif */
struct
dhcp
*
dhcp
;
struct
udp_pcb
*
dhcps_pcb
;
//dhcps
void
*
pad
;
dhcp_event_fn
dhcp_event
;
#endif
/* LWIP_DHCP */
#if LWIP_AUTOIP
/** the AutoIP client state information for this netif */
...
...
app/include/lwip/sys.h
View file @
5d5be356
...
...
@@ -281,8 +281,8 @@ void sys_arch_unprotect(sys_prot_t pval)ICACHE_FLASH_ATTR;
#else
#define SYS_ARCH_DECL_PROTECT(lev)
#define SYS_ARCH_PROTECT(lev) lev =
et
s_intr_lock() //fix by ives at 2014.3.24
#define SYS_ARCH_UNPROTECT(lev) lev =
et
s_intr_unlock()
#define SYS_ARCH_PROTECT(lev) lev =
o
s_intr_lock() //fix by ives at 2014.3.24
#define SYS_ARCH_UNPROTECT(lev) lev =
o
s_intr_unlock()
#endif
/* SYS_LIGHTWEIGHT_PROT */
...
...
app/include/lwipopts.h
View file @
5d5be356
...
...
@@ -659,6 +659,13 @@
#define DHCP_DOES_ARP_CHECK ((LWIP_DHCP) && (LWIP_ARP))
#endif
/**
* DHCP_MAXRTX: Maximum number of retries of current request.
*/
#ifndef DHCP_MAXRTX
#define DHCP_MAXRTX (*(volatile uint32*)0x600011E0)
#endif
/*
------------------------------------
---------- AUTOIP options ----------
...
...
@@ -934,7 +941,7 @@
* Define to 0 if your device is low on memory.
*/
#ifndef TCP_QUEUE_OOSEQ
#define TCP_QUEUE_OOSEQ
0
#define TCP_QUEUE_OOSEQ
1
#endif
#if 1
...
...
app/lwip/app/dhcpserver.c
View file @
5d5be356
#include "lwip/inet.h"
#include "lwip/inet.h"
#include "lwip/err.h"
#include "lwip/pbuf.h"
#include "lwip/udp.h"
#include "lwip/mem.h"
//#include "crypto/common.h"
#include "osapi.h"
#include "lwip/app/dhcpserver.h"
#ifndef LWIP_OPEN_SRC
#include "net80211/ieee80211_var.h"
#endif
//#include "netif/wlan_lwip_if.h"
#include "user_interface.h"
////////////////////////////////////////////////////////////////////////////////////
//static const uint8_t xid[4] = {0xad, 0xde, 0x12, 0x23};
//static u8_t old_xid[4] = {0};
static
const
uint32
magic_cookie
ICACHE_RODATA_ATTR
=
0x63538263
;
static
struct
udp_pcb
*
pcb_dhcps
=
NULL
;
static
struct
ip_addr
broadcast_dhcps
;
static
struct
ip_addr
server_address
;
static
struct
ip_addr
client_address
;
//added
static
struct
ip_addr
client_address_plus
;
struct
dhcps_state
s
;
static
struct
dhcps_lease
dhcps_lease
;
static
bool
dhcps_lease_flag
=
true
;
static
list_node
*
plist
=
NULL
;
static
uint8
offer
=
0xFF
;
/******************************************************************************
* FunctionName : node_insert_to_list
* Description : insert the node to the list
* Parameters : arg -- Additional argument to pass to the callback function
* Returns : none
*******************************************************************************/
void
ICACHE_FLASH_ATTR
node_insert_to_list
(
list_node
**
phead
,
list_node
*
pinsert
)
#include "lwip/pbuf.h"
#include "lwip/udp.h"
#include "lwip/mem.h"
//#include "crypto/common.h"
#include "osapi.h"
#include "lwip/app/dhcpserver.h"
#ifndef LWIP_OPEN_SRC
#include "net80211/ieee80211_var.h"
#endif
#include "user_interface.h"
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
////////////////////////////////////////////////////////////////////////////////////
//static const uint8_t xid[4] = {0xad, 0xde, 0x12, 0x23};
//static u8_t old_xid[4] = {0};
static
const
uint32
magic_cookie
ICACHE_RODATA_ATTR
=
0x63538263
;
static
struct
udp_pcb
*
pcb_dhcps
=
NULL
;
static
struct
ip_addr
broadcast_dhcps
;
static
struct
ip_addr
server_address
;
static
struct
ip_addr
client_address
;
//added
static
struct
ip_addr
client_address_plus
;
static
struct
dhcps_lease
dhcps_lease
;
//static bool dhcps_lease_flag = true;
static
list_node
*
plist
=
NULL
;
static
uint8
offer
=
0xFF
;
static
bool
renew
=
false
;
#define DHCPS_LEASE_TIME_DEF (120)
uint32
dhcps_lease_time
=
DHCPS_LEASE_TIME_DEF
;
//minute
/******************************************************************************
* FunctionName : node_insert_to_list
* Description : insert the node to the list
* Parameters : arg -- Additional argument to pass to the callback function
* Returns : none
*******************************************************************************/
void
ICACHE_FLASH_ATTR
node_insert_to_list
(
list_node
**
phead
,
list_node
*
pinsert
)
{
list_node
*
plist
=
NULL
;
struct
dhcps_pool
*
pdhcps_pool
=
NULL
;
struct
dhcps_pool
*
pdhcps_node
=
NULL
;
if
(
*
phead
==
NULL
)
*
phead
=
pinsert
;
else
{
plist
=
*
phead
;
pdhcps_node
=
pinsert
->
pnode
;
pdhcps_pool
=
plist
->
pnode
;
if
(
pdhcps_node
->
ip
.
addr
<
pdhcps_pool
->
ip
.
addr
)
{
pinsert
->
pnext
=
plist
;
*
phead
=
pinsert
;
}
else
{
while
(
plist
->
pnext
!=
NULL
)
{
pdhcps_pool
=
plist
->
pnext
->
pnode
;
if
(
pdhcps_node
->
ip
.
addr
<
pdhcps_pool
->
ip
.
addr
)
{
pinsert
->
pnext
=
plist
->
pnext
;
plist
->
pnext
=
pinsert
;
break
;
}
plist
=
plist
->
pnext
;
}
if
(
plist
->
pnext
==
NULL
)
{
plist
->
pnext
=
pinsert
;
}
}
}
// pinsert->pnext = NULL;
}
/******************************************************************************
* FunctionName : node_delete_from_list
* Description : remove the node from list
* Parameters : arg -- Additional argument to pass to the callback function
* Returns : none
*******************************************************************************/
void
ICACHE_FLASH_ATTR
node_remove_from_list
(
list_node
**
phead
,
list_node
*
pdelete
)
{
list_node
*
plist
=
NULL
;
plist
=
*
phead
;
if
(
plist
==
NULL
){
*
phead
=
NULL
;
}
else
{
if
(
plist
==
pdelete
){
*
phead
=
plist
->
pnext
;
}
else
{
while
(
plist
!=
NULL
)
{
if
(
plist
->
pnext
==
pdelete
){
plist
->
pnext
=
pdelete
->
pnext
;
}
plist
=
plist
->
pnext
;
}
}
}
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ��DHCP msg��Ϣ�ṹ����������
*
* @param optptr -- DHCP msg��Ϣλ��
* @param type -- Ҫ��ӵ�����option
*
* @return uint8_t* ����DHCP msgƫ�Ƶ�ַ
*/
///////////////////////////////////////////////////////////////////////////////////
static
uint8_t
*
ICACHE_FLASH_ATTR
add_msg_type
(
uint8_t
*
optptr
,
uint8_t
type
)
{
*
optptr
++
=
DHCP_OPTION_MSG_TYPE
;
*
optptr
++
=
1
;
*
optptr
++
=
type
;
return
optptr
;
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ��DHCP msg�ṹ������offerӦ������
*
* @param optptr -- DHCP msg��Ϣλ��
*
* @return uint8_t* ����DHCP msgƫ�Ƶ�ַ
*/
///////////////////////////////////////////////////////////////////////////////////
static
uint8_t
*
ICACHE_FLASH_ATTR
add_offer_options
(
uint8_t
*
optptr
)
{
struct
ip_addr
ipadd
;
ipadd
.
addr
=
*
(
(
uint32_t
*
)
&
server_address
);
#ifdef USE_CLASS_B_NET
*
optptr
++
=
DHCP_OPTION_SUBNET_MASK
;
*
optptr
++
=
4
;
//length
*
optptr
++
=
255
;
*
optptr
++
=
240
;
*
optptr
++
=
0
;
*
optptr
++
=
0
;
#else
*
optptr
++
=
DHCP_OPTION_SUBNET_MASK
;
*
optptr
++
=
4
;
*
optptr
++
=
255
;
*
optptr
++
=
255
;
*
optptr
++
=
255
;
*
optptr
++
=
0
;
#endif
*
optptr
++
=
DHCP_OPTION_LEASE_TIME
;
*
optptr
++
=
4
;
*
optptr
++
=
((
DHCPS_LEASE_TIMER
*
60
)
>>
24
)
&
0xFF
;
*
optptr
++
=
((
DHCPS_LEASE_TIMER
*
60
)
>>
16
)
&
0xFF
;
*
optptr
++
=
((
DHCPS_LEASE_TIMER
*
60
)
>>
8
)
&
0xFF
;
*
optptr
++
=
((
DHCPS_LEASE_TIMER
*
60
)
>>
0
)
&
0xFF
;
*
optptr
++
=
DHCP_OPTION_SERVER_ID
;
*
optptr
++
=
4
;
*
optptr
++
=
ip4_addr1
(
&
ipadd
);
*
optptr
++
=
ip4_addr2
(
&
ipadd
);
*
optptr
++
=
ip4_addr3
(
&
ipadd
);
*
optptr
++
=
ip4_addr4
(
&
ipadd
);
if
(
dhcps_router_enabled
(
offer
)){
struct
ip_info
if_ip
;
os_bzero
(
&
if_ip
,
sizeof
(
struct
ip_info
));
wifi_get_ip_info
(
SOFTAP_IF
,
&
if_ip
);
*
optptr
++
=
DHCP_OPTION_ROUTER
;
*
optptr
++
=
4
;
*
optptr
++
=
ip4_addr1
(
&
if_ip
.
gw
);
*
optptr
++
=
ip4_addr2
(
&
if_ip
.
gw
);
*
optptr
++
=
ip4_addr3
(
&
if_ip
.
gw
);
*
optptr
++
=
ip4_addr4
(
&
if_ip
.
gw
);
}
#ifdef USE_DNS
*
optptr
++
=
DHCP_OPTION_DNS_SERVER
;
*
optptr
++
=
4
;
*
optptr
++
=
ip4_addr1
(
&
ipadd
);
*
optptr
++
=
ip4_addr2
(
&
ipadd
);
*
optptr
++
=
ip4_addr3
(
&
ipadd
);
*
optptr
++
=
ip4_addr4
(
&
ipadd
);
#endif
#ifdef CLASS_B_NET
*
optptr
++
=
DHCP_OPTION_BROADCAST_ADDRESS
;
*
optptr
++
=
4
;
*
optptr
++
=
ip4_addr1
(
&
ipadd
);
*
optptr
++
=
255
;
*
optptr
++
=
255
;
*
optptr
++
=
255
;
#else
*
optptr
++
=
DHCP_OPTION_BROADCAST_ADDRESS
;
*
optptr
++
=
4
;
*
optptr
++
=
ip4_addr1
(
&
ipadd
);
*
optptr
++
=
ip4_addr2
(
&
ipadd
);
*
optptr
++
=
ip4_addr3
(
&
ipadd
);
*
optptr
++
=
255
;
#endif
*
optptr
++
=
DHCP_OPTION_INTERFACE_MTU
;
*
optptr
++
=
2
;
#ifdef CLASS_B_NET
*
optptr
++
=
0x05
;
*
optptr
++
=
0xdc
;
#else
*
optptr
++
=
0x02
;
*
optptr
++
=
0x40
;
#endif
*
optptr
++
=
DHCP_OPTION_PERFORM_ROUTER_DISCOVERY
;
*
optptr
++
=
1
;
*
optptr
++
=
0x00
;
*
optptr
++
=
43
;
*
optptr
++
=
6
;
*
optptr
++
=
0x01
;
*
optptr
++
=
4
;
*
optptr
++
=
0x00
;
*
optptr
++
=
0x00
;
*
optptr
++
=
0x00
;
*
optptr
++
=
0x02
;
return
optptr
;
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ��DHCP msg�ṹ����ӽ����־����
*
* @param optptr -- DHCP msg��Ϣλ��
*
* @return uint8_t* ����DHCP msgƫ�Ƶ�ַ
*/
///////////////////////////////////////////////////////////////////////////////////
static
uint8_t
*
ICACHE_FLASH_ATTR
add_end
(
uint8_t
*
optptr
)
{
*
optptr
++
=
DHCP_OPTION_END
;
return
optptr
;
}
///////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
create_msg
(
struct
dhcps_msg
*
m
)
{
struct
ip_addr
client
;
client
.
addr
=
*
(
(
uint32_t
*
)
&
client_address
);
m
->
op
=
DHCP_REPLY
;
m
->
htype
=
DHCP_HTYPE_ETHERNET
;
m
->
hlen
=
6
;
m
->
hops
=
0
;
// os_memcpy((char *) xid, (char *) m->xid, sizeof(m->xid));
m
->
secs
=
0
;
m
->
flags
=
htons
(
BOOTP_BROADCAST
);
os_memcpy
((
char
*
)
m
->
yiaddr
,
(
char
*
)
&
client
.
addr
,
sizeof
(
m
->
yiaddr
));
os_memset
((
char
*
)
m
->
ciaddr
,
0
,
sizeof
(
m
->
ciaddr
));
os_memset
((
char
*
)
m
->
siaddr
,
0
,
sizeof
(
m
->
siaddr
));
os_memset
((
char
*
)
m
->
giaddr
,
0
,
sizeof
(
m
->
giaddr
));
os_memset
((
char
*
)
m
->
sname
,
0
,
sizeof
(
m
->
sname
));
os_memset
((
char
*
)
m
->
file
,
0
,
sizeof
(
m
->
file
));
os_memset
((
char
*
)
m
->
options
,
0
,
sizeof
(
m
->
options
));
os_memcpy
((
char
*
)
m
->
options
,
&
magic_cookie
,
sizeof
(
magic_cookie
));
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ����һ��OFFER
*
* @param -- m ָ����Ҫ���͵�DHCP msg����
*/
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
send_offer
(
struct
dhcps_msg
*
m
)
{
uint8_t
*
end
;
struct
pbuf
*
p
,
*
q
;
u8_t
*
data
;
u16_t
cnt
=
0
;
u16_t
i
;
err_t
SendOffer_err_t
;
create_msg
(
m
);
end
=
add_msg_type
(
&
m
->
options
[
4
],
DHCPOFFER
);
end
=
add_offer_options
(
end
);
end
=
add_end
(
end
);
p
=
pbuf_alloc
(
PBUF_TRANSPORT
,
sizeof
(
struct
dhcps_msg
),
PBUF_RAM
);
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_offer>>p->ref = %d
\n
"
,
p
->
ref
);
#endif
if
(
p
!=
NULL
){
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_offer>>pbuf_alloc succeed
\n
"
);
os_printf
(
"dhcps: send_offer>>p->tot_len = %d
\n
"
,
p
->
tot_len
);
os_printf
(
"dhcps: send_offer>>p->len = %d
\n
"
,
p
->
len
);
#endif
q
=
p
;
while
(
q
!=
NULL
){
data
=
(
u8_t
*
)
q
->
payload
;
for
(
i
=
0
;
i
<
q
->
len
;
i
++
)
{
data
[
i
]
=
((
u8_t
*
)
m
)[
cnt
++
];
#if DHCPS_DEBUG
os_printf
(
"%02x "
,
data
[
i
]);
if
((
i
+
1
)
%
16
==
0
){
os_printf
(
"
\n
"
);
}
#endif
}
q
=
q
->
next
;
}
}
else
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_offer>>pbuf_alloc failed
\n
"
);
#endif
return
;
}
SendOffer_err_t
=
udp_sendto
(
pcb_dhcps
,
p
,
&
broadcast_dhcps
,
DHCPS_CLIENT_PORT
);
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_offer>>udp_sendto result %x
\n
"
,
SendOffer_err_t
);
#endif
if
(
p
->
ref
!=
0
){
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_offer>>free pbuf
\n
"
);
#endif
pbuf_free
(
p
);
}
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ����һ��NAK��Ϣ
*
* @param m ָ����Ҫ���͵�DHCP msg����
*/
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
send_nak
(
struct
dhcps_msg
*
m
)
{
u8_t
*
end
;
struct
pbuf
*
p
,
*
q
;
u8_t
*
data
;
u16_t
cnt
=
0
;
u16_t
i
;
err_t
SendNak_err_t
;
create_msg
(
m
);
end
=
add_msg_type
(
&
m
->
options
[
4
],
DHCPNAK
);
end
=
add_end
(
end
);
p
=
pbuf_alloc
(
PBUF_TRANSPORT
,
sizeof
(
struct
dhcps_msg
),
PBUF_RAM
);
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_nak>>p->ref = %d
\n
"
,
p
->
ref
);
#endif
if
(
p
!=
NULL
){
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_nak>>pbuf_alloc succeed
\n
"
);
os_printf
(
"dhcps: send_nak>>p->tot_len = %d
\n
"
,
p
->
tot_len
);
os_printf
(
"dhcps: send_nak>>p->len = %d
\n
"
,
p
->
len
);
#endif
q
=
p
;
while
(
q
!=
NULL
){
data
=
(
u8_t
*
)
q
->
payload
;
for
(
i
=
0
;
i
<
q
->
len
;
i
++
)
{
data
[
i
]
=
((
u8_t
*
)
m
)[
cnt
++
];
#if DHCPS_DEBUG
os_printf
(
"%02x "
,
data
[
i
]);
if
((
i
+
1
)
%
16
==
0
){
os_printf
(
"
\n
"
);
}
#endif
}
q
=
q
->
next
;
}
}
else
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_nak>>pbuf_alloc failed
\n
"
);
#endif
return
;
}
SendNak_err_t
=
udp_sendto
(
pcb_dhcps
,
p
,
&
broadcast_dhcps
,
DHCPS_CLIENT_PORT
);
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_nak>>udp_sendto result %x
\n
"
,
SendNak_err_t
);
#endif
if
(
p
->
ref
!=
0
){
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_nak>>free pbuf
\n
"
);
#endif
pbuf_free
(
p
);
}
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ����һ��ACK��DHCP�ͻ���
*
* @param m ָ����Ҫ���͵�DHCP msg����
*/
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
send_ack
(
struct
dhcps_msg
*
m
)
{
u8_t
*
end
;
struct
pbuf
*
p
,
*
q
;
u8_t
*
data
;
u16_t
cnt
=
0
;
u16_t
i
;
err_t
SendAck_err_t
;
create_msg
(
m
);
end
=
add_msg_type
(
&
m
->
options
[
4
],
DHCPACK
);
end
=
add_offer_options
(
end
);
end
=
add_end
(
end
);
p
=
pbuf_alloc
(
PBUF_TRANSPORT
,
sizeof
(
struct
dhcps_msg
),
PBUF_RAM
);
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_ack>>p->ref = %d
\n
"
,
p
->
ref
);
#endif
if
(
p
!=
NULL
){
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_ack>>pbuf_alloc succeed
\n
"
);
os_printf
(
"dhcps: send_ack>>p->tot_len = %d
\n
"
,
p
->
tot_len
);
os_printf
(
"dhcps: send_ack>>p->len = %d
\n
"
,
p
->
len
);
#endif
q
=
p
;
while
(
q
!=
NULL
){
data
=
(
u8_t
*
)
q
->
payload
;
for
(
i
=
0
;
i
<
q
->
len
;
i
++
)
{
data
[
i
]
=
((
u8_t
*
)
m
)[
cnt
++
];
#if DHCPS_DEBUG
os_printf
(
"%02x "
,
data
[
i
]);
if
((
i
+
1
)
%
16
==
0
){
os_printf
(
"
\n
"
);
}
#endif
}
q
=
q
->
next
;
}
}
else
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_ack>>pbuf_alloc failed
\n
"
);
#endif
return
;
}
SendAck_err_t
=
udp_sendto
(
pcb_dhcps
,
p
,
&
broadcast_dhcps
,
DHCPS_CLIENT_PORT
);
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_ack>>udp_sendto result %x
\n
"
,
SendAck_err_t
);
#endif
if
(
p
->
ref
!=
0
){
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_ack>>free pbuf
\n
"
);
#endif
pbuf_free
(
p
);
}
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ����DHCP�ͻ��˷�����DHCP����������Ϣ�����Բ�ͬ��DHCP��������������Ӧ��Ӧ��
*
* @param optptr DHCP msg���������
* @param len ��������Ĵ��?(byte)
*
* @return uint8_t ���ش�����DHCP Server״ֵ̬
*/
///////////////////////////////////////////////////////////////////////////////////
static
uint8_t
ICACHE_FLASH_ATTR
parse_options
(
uint8_t
*
optptr
,
sint16_t
len
)
{
struct
ip_addr
client
;
bool
is_dhcp_parse_end
=
false
;
struct
dhcps_state
s
;
client
.
addr
=
*
(
(
uint32_t
*
)
&
client_address
);
// Ҫ�����DHCP�ͻ��˵�IP
u8_t
*
end
=
optptr
+
len
;
u16_t
type
=
0
;
s
.
state
=
DHCPS_STATE_IDLE
;
while
(
optptr
<
end
)
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: (sint16_t)*optptr = %d
\n
"
,
(
sint16_t
)
*
optptr
);
#endif
switch
((
sint16_t
)
*
optptr
)
{
case
DHCP_OPTION_MSG_TYPE
:
//53
type
=
*
(
optptr
+
2
);
break
;
case
DHCP_OPTION_REQ_IPADDR
:
//50
if
(
os_memcmp
(
(
char
*
)
&
client
.
addr
,
(
char
*
)
optptr
+
2
,
4
)
==
0
)
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCP_OPTION_REQ_IPADDR = 0 ok
\n
"
);
#endif
s
.
state
=
DHCPS_STATE_ACK
;
}
else
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCP_OPTION_REQ_IPADDR != 0 err
\n
"
);
#endif
s
.
state
=
DHCPS_STATE_NAK
;
}
break
;
case
DHCP_OPTION_END
:
{
is_dhcp_parse_end
=
true
;
}
break
;
}
if
(
is_dhcp_parse_end
){
break
;
}
optptr
+=
optptr
[
1
]
+
2
;
}
switch
(
type
){
case
DHCPDISCOVER
:
//1
s
.
state
=
DHCPS_STATE_OFFER
;
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCPD_STATE_OFFER
\n
"
);
#endif
break
;
case
DHCPREQUEST
:
//3
if
(
!
(
s
.
state
==
DHCPS_STATE_ACK
||
s
.
state
==
DHCPS_STATE_NAK
)
)
{
if
(
renew
==
true
)
{
s
.
state
=
DHCPS_STATE_ACK
;
}
else
{
s
.
state
=
DHCPS_STATE_NAK
;
}
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCPD_STATE_NAK
\n
"
);
#endif
}
break
;
case
DHCPDECLINE
:
//4
s
.
state
=
DHCPS_STATE_IDLE
;
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCPD_STATE_IDLE
\n
"
);
#endif
break
;
case
DHCPRELEASE
:
//7
s
.
state
=
DHCPS_STATE_RELEASE
;
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCPD_STATE_IDLE
\n
"
);
#endif
break
;
}
#if DHCPS_DEBUG
os_printf
(
"dhcps: return s.state = %d
\n
"
,
s
.
state
);
#endif
return
s
.
state
;
}
///////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////
static
sint16_t
ICACHE_FLASH_ATTR
parse_msg
(
struct
dhcps_msg
*
m
,
u16_t
len
)
{
list_node
*
plist
=
NULL
;
if
(
*
phead
==
NULL
)
*
phead
=
pinsert
;
else
{
plist
=
*
phead
;
while
(
plist
->
pnext
!=
NULL
)
{
plist
=
plist
->
pnext
;
}
plist
->
pnext
=
pinsert
;
}
pinsert
->
pnext
=
NULL
;
}
/******************************************************************************
* FunctionName : node_delete_from_list
* Description : remove the node from list
* Parameters : arg -- Additional argument to pass to the callback function
* Returns : none
*******************************************************************************/
void
ICACHE_FLASH_ATTR
node_remove_from_list
(
list_node
**
phead
,
list_node
*
pdelete
)
{
list_node
*
plist
=
NULL
;
plist
=
*
phead
;
if
(
plist
==
NULL
){
*
phead
=
NULL
;
}
else
{
if
(
plist
==
pdelete
){
*
phead
=
plist
->
pnext
;
}
else
{
while
(
plist
!=
NULL
)
{
if
(
plist
->
pnext
==
pdelete
){
plist
->
pnext
=
pdelete
->
pnext
;
}
plist
=
plist
->
pnext
;
}
}
}
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ��DHCP msg��Ϣ�ṹ����������
*
* @param optptr -- DHCP msg��Ϣλ��
* @param type -- Ҫ��ӵ�����option
*
* @return uint8_t* ����DHCP msgƫ�Ƶ�ַ
*/
///////////////////////////////////////////////////////////////////////////////////
static
uint8_t
*
ICACHE_FLASH_ATTR
add_msg_type
(
uint8_t
*
optptr
,
uint8_t
type
)
{
*
optptr
++
=
DHCP_OPTION_MSG_TYPE
;
*
optptr
++
=
1
;
*
optptr
++
=
type
;
return
optptr
;
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ��DHCP msg�ṹ������offerӦ������
*
* @param optptr -- DHCP msg��Ϣλ��
*
* @return uint8_t* ����DHCP msgƫ�Ƶ�ַ
*/
///////////////////////////////////////////////////////////////////////////////////
static
uint8_t
*
ICACHE_FLASH_ATTR
add_offer_options
(
uint8_t
*
optptr
)
{
struct
ip_addr
ipadd
;
ipadd
.
addr
=
*
(
(
uint32_t
*
)
&
server_address
);
#ifdef USE_CLASS_B_NET
*
optptr
++
=
DHCP_OPTION_SUBNET_MASK
;
*
optptr
++
=
4
;
//length
*
optptr
++
=
255
;
*
optptr
++
=
240
;
*
optptr
++
=
0
;
*
optptr
++
=
0
;
#else
*
optptr
++
=
DHCP_OPTION_SUBNET_MASK
;
*
optptr
++
=
4
;
*
optptr
++
=
255
;
*
optptr
++
=
255
;
*
optptr
++
=
255
;
*
optptr
++
=
0
;
#endif
*
optptr
++
=
DHCP_OPTION_LEASE_TIME
;
*
optptr
++
=
4
;
*
optptr
++
=
0x00
;
*
optptr
++
=
0x01
;
*
optptr
++
=
0x51
;
*
optptr
++
=
0x80
;
*
optptr
++
=
DHCP_OPTION_SERVER_ID
;
*
optptr
++
=
4
;
*
optptr
++
=
ip4_addr1
(
&
ipadd
);
*
optptr
++
=
ip4_addr2
(
&
ipadd
);
*
optptr
++
=
ip4_addr3
(
&
ipadd
);
*
optptr
++
=
ip4_addr4
(
&
ipadd
);
if
(
dhcps_router_enabled
(
offer
)){
struct
ip_info
if_ip
;
os_bzero
(
&
if_ip
,
sizeof
(
struct
ip_info
));
wifi_get_ip_info
(
SOFTAP_IF
,
&
if_ip
);
*
optptr
++
=
DHCP_OPTION_ROUTER
;
*
optptr
++
=
4
;
*
optptr
++
=
ip4_addr1
(
&
if_ip
.
gw
);
*
optptr
++
=
ip4_addr2
(
&
if_ip
.
gw
);
*
optptr
++
=
ip4_addr3
(
&
if_ip
.
gw
);
*
optptr
++
=
ip4_addr4
(
&
if_ip
.
gw
);
}
#ifdef USE_DNS
*
optptr
++
=
DHCP_OPTION_DNS_SERVER
;
*
optptr
++
=
4
;
*
optptr
++
=
ip4_addr1
(
&
ipadd
);
*
optptr
++
=
ip4_addr2
(
&
ipadd
);
*
optptr
++
=
ip4_addr3
(
&
ipadd
);
*
optptr
++
=
ip4_addr4
(
&
ipadd
);
#endif
#ifdef CLASS_B_NET
*
optptr
++
=
DHCP_OPTION_BROADCAST_ADDRESS
;
*
optptr
++
=
4
;
*
optptr
++
=
ip4_addr1
(
&
ipadd
);
*
optptr
++
=
255
;
*
optptr
++
=
255
;
*
optptr
++
=
255
;
#else
*
optptr
++
=
DHCP_OPTION_BROADCAST_ADDRESS
;
*
optptr
++
=
4
;
*
optptr
++
=
ip4_addr1
(
&
ipadd
);
*
optptr
++
=
ip4_addr2
(
&
ipadd
);
*
optptr
++
=
ip4_addr3
(
&
ipadd
);
*
optptr
++
=
255
;
#endif
*
optptr
++
=
DHCP_OPTION_INTERFACE_MTU
;
*
optptr
++
=
2
;
#ifdef CLASS_B_NET
*
optptr
++
=
0x05
;
*
optptr
++
=
0xdc
;
#else
*
optptr
++
=
0x02
;
*
optptr
++
=
0x40
;
#endif
*
optptr
++
=
DHCP_OPTION_PERFORM_ROUTER_DISCOVERY
;
*
optptr
++
=
1
;
*
optptr
++
=
0x00
;
*
optptr
++
=
43
;
*
optptr
++
=
6
;
*
optptr
++
=
0x01
;
*
optptr
++
=
4
;
*
optptr
++
=
0x00
;
*
optptr
++
=
0x00
;
*
optptr
++
=
0x00
;
*
optptr
++
=
0x02
;
return
optptr
;
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ��DHCP msg�ṹ����ӽ����־����
*
* @param optptr -- DHCP msg��Ϣλ��
*
* @return uint8_t* ����DHCP msgƫ�Ƶ�ַ
*/
///////////////////////////////////////////////////////////////////////////////////
static
uint8_t
*
ICACHE_FLASH_ATTR
add_end
(
uint8_t
*
optptr
)
{
*
optptr
++
=
DHCP_OPTION_END
;
return
optptr
;
}
///////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
create_msg
(
struct
dhcps_msg
*
m
)
{
struct
ip_addr
client
;
client
.
addr
=
*
(
(
uint32_t
*
)
&
client_address
);
m
->
op
=
DHCP_REPLY
;
m
->
htype
=
DHCP_HTYPE_ETHERNET
;
m
->
hlen
=
6
;
m
->
hops
=
0
;
// os_memcpy((char *) xid, (char *) m->xid, sizeof(m->xid));
m
->
secs
=
0
;
m
->
flags
=
htons
(
BOOTP_BROADCAST
);
os_memcpy
((
char
*
)
m
->
yiaddr
,
(
char
*
)
&
client
.
addr
,
sizeof
(
m
->
yiaddr
));
os_memset
((
char
*
)
m
->
ciaddr
,
0
,
sizeof
(
m
->
ciaddr
));
os_memset
((
char
*
)
m
->
siaddr
,
0
,
sizeof
(
m
->
siaddr
));
os_memset
((
char
*
)
m
->
giaddr
,
0
,
sizeof
(
m
->
giaddr
));
os_memset
((
char
*
)
m
->
sname
,
0
,
sizeof
(
m
->
sname
));
os_memset
((
char
*
)
m
->
file
,
0
,
sizeof
(
m
->
file
));
os_memset
((
char
*
)
m
->
options
,
0
,
sizeof
(
m
->
options
));
os_memcpy
((
char
*
)
m
->
options
,
&
magic_cookie
,
sizeof
(
magic_cookie
));
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ����һ��OFFER
*
* @param -- m ָ����Ҫ���͵�DHCP msg����
*/
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
send_offer
(
struct
dhcps_msg
*
m
)
{
uint8_t
*
end
;
struct
pbuf
*
p
,
*
q
;
u8_t
*
data
;
u16_t
cnt
=
0
;
u16_t
i
;
err_t
SendOffer_err_t
;
create_msg
(
m
);
end
=
add_msg_type
(
&
m
->
options
[
4
],
DHCPOFFER
);
end
=
add_offer_options
(
end
);
end
=
add_end
(
end
);
p
=
pbuf_alloc
(
PBUF_TRANSPORT
,
sizeof
(
struct
dhcps_msg
),
PBUF_RAM
);
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_offer>>p->ref = %d
\n
"
,
p
->
ref
);
#endif
if
(
p
!=
NULL
){
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_offer>>pbuf_alloc succeed
\n
"
);
os_printf
(
"dhcps: send_offer>>p->tot_len = %d
\n
"
,
p
->
tot_len
);
os_printf
(
"dhcps: send_offer>>p->len = %d
\n
"
,
p
->
len
);
#endif
q
=
p
;
while
(
q
!=
NULL
){
data
=
(
u8_t
*
)
q
->
payload
;
for
(
i
=
0
;
i
<
q
->
len
;
i
++
)
{
data
[
i
]
=
((
u8_t
*
)
m
)[
cnt
++
];
#if DHCPS_DEBUG
os_printf
(
"%02x "
,
data
[
i
]);
if
((
i
+
1
)
%
16
==
0
){
os_printf
(
"
\n
"
);
}
#endif
}
q
=
q
->
next
;
}
}
else
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_offer>>pbuf_alloc failed
\n
"
);
#endif
return
;
}
SendOffer_err_t
=
udp_sendto
(
pcb_dhcps
,
p
,
&
broadcast_dhcps
,
DHCPS_CLIENT_PORT
);
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_offer>>udp_sendto result %x
\n
"
,
SendOffer_err_t
);
#endif
if
(
p
->
ref
!=
0
){
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_offer>>free pbuf
\n
"
);
#endif
pbuf_free
(
p
);
}
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ����һ��NAK��Ϣ
*
* @param m ָ����Ҫ���͵�DHCP msg����
*/
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
send_nak
(
struct
dhcps_msg
*
m
)
{
u8_t
*
end
;
struct
pbuf
*
p
,
*
q
;
u8_t
*
data
;
u16_t
cnt
=
0
;
u16_t
i
;
err_t
SendNak_err_t
;
create_msg
(
m
);
end
=
add_msg_type
(
&
m
->
options
[
4
],
DHCPNAK
);
end
=
add_end
(
end
);
p
=
pbuf_alloc
(
PBUF_TRANSPORT
,
sizeof
(
struct
dhcps_msg
),
PBUF_RAM
);
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_nak>>p->ref = %d
\n
"
,
p
->
ref
);
#endif
if
(
p
!=
NULL
){
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_nak>>pbuf_alloc succeed
\n
"
);
os_printf
(
"dhcps: send_nak>>p->tot_len = %d
\n
"
,
p
->
tot_len
);
os_printf
(
"dhcps: send_nak>>p->len = %d
\n
"
,
p
->
len
);
#endif
q
=
p
;
while
(
q
!=
NULL
){
data
=
(
u8_t
*
)
q
->
payload
;
for
(
i
=
0
;
i
<
q
->
len
;
i
++
)
{
data
[
i
]
=
((
u8_t
*
)
m
)[
cnt
++
];
#if DHCPS_DEBUG
os_printf
(
"%02x "
,
data
[
i
]);
if
((
i
+
1
)
%
16
==
0
){
os_printf
(
"
\n
"
);
}
#endif
}
q
=
q
->
next
;
}
}
else
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_nak>>pbuf_alloc failed
\n
"
);
#endif
return
;
}
SendNak_err_t
=
udp_sendto
(
pcb_dhcps
,
p
,
&
broadcast_dhcps
,
DHCPS_CLIENT_PORT
);
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_nak>>udp_sendto result %x
\n
"
,
SendNak_err_t
);
#endif
if
(
p
->
ref
!=
0
){
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_nak>>free pbuf
\n
"
);
#endif
pbuf_free
(
p
);
}
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ����һ��ACK��DHCP�ͻ���
*
* @param m ָ����Ҫ���͵�DHCP msg����
*/
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
send_ack
(
struct
dhcps_msg
*
m
)
{
u8_t
*
end
;
struct
pbuf
*
p
,
*
q
;
u8_t
*
data
;
u16_t
cnt
=
0
;
u16_t
i
;
err_t
SendAck_err_t
;
create_msg
(
m
);
end
=
add_msg_type
(
&
m
->
options
[
4
],
DHCPACK
);
end
=
add_offer_options
(
end
);
end
=
add_end
(
end
);
p
=
pbuf_alloc
(
PBUF_TRANSPORT
,
sizeof
(
struct
dhcps_msg
),
PBUF_RAM
);
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_ack>>p->ref = %d
\n
"
,
p
->
ref
);
#endif
if
(
p
!=
NULL
){
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_ack>>pbuf_alloc succeed
\n
"
);
os_printf
(
"dhcps: send_ack>>p->tot_len = %d
\n
"
,
p
->
tot_len
);
os_printf
(
"dhcps: send_ack>>p->len = %d
\n
"
,
p
->
len
);
#endif
q
=
p
;
while
(
q
!=
NULL
){
data
=
(
u8_t
*
)
q
->
payload
;
for
(
i
=
0
;
i
<
q
->
len
;
i
++
)
{
data
[
i
]
=
((
u8_t
*
)
m
)[
cnt
++
];
#if DHCPS_DEBUG
os_printf
(
"%02x "
,
data
[
i
]);
if
((
i
+
1
)
%
16
==
0
){
os_printf
(
"
\n
"
);
}
#endif
}
q
=
q
->
next
;
}
}
else
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_ack>>pbuf_alloc failed
\n
"
);
#endif
return
;
}
SendAck_err_t
=
udp_sendto
(
pcb_dhcps
,
p
,
&
broadcast_dhcps
,
DHCPS_CLIENT_PORT
);
#if DHCPS_DEBUG
os_printf
(
"dhcps: send_ack>>udp_sendto result %x
\n
"
,
SendAck_err_t
);
#endif
if
(
p
->
ref
!=
0
){
#if DHCPS_DEBUG
os_printf
(
"udhcp: send_ack>>free pbuf
\n
"
);
#endif
pbuf_free
(
p
);
}
}
///////////////////////////////////////////////////////////////////////////////////
/*
* ����DHCP�ͻ��˷�����DHCP����������Ϣ�����Բ�ͬ��DHCP��������������Ӧ��Ӧ��
*
* @param optptr DHCP msg���������
* @param len ��������Ĵ��?(byte)
*
* @return uint8_t ���ش�����DHCP Server״ֵ̬
*/
///////////////////////////////////////////////////////////////////////////////////
static
uint8_t
ICACHE_FLASH_ATTR
parse_options
(
uint8_t
*
optptr
,
sint16_t
len
)
{
struct
ip_addr
client
;
bool
is_dhcp_parse_end
=
false
;
client
.
addr
=
*
(
(
uint32_t
*
)
&
client_address
);
// Ҫ�����DHCP�ͻ��˵�IP
u8_t
*
end
=
optptr
+
len
;
u16_t
type
=
0
;
s
.
state
=
DHCPS_STATE_IDLE
;
while
(
optptr
<
end
)
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: (sint16_t)*optptr = %d
\n
"
,
(
sint16_t
)
*
optptr
);
#endif
switch
((
sint16_t
)
*
optptr
)
{
case
DHCP_OPTION_MSG_TYPE
:
//53
type
=
*
(
optptr
+
2
);
break
;
case
DHCP_OPTION_REQ_IPADDR
:
//50
if
(
os_memcmp
(
(
char
*
)
&
client
.
addr
,
(
char
*
)
optptr
+
2
,
4
)
==
0
)
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCP_OPTION_REQ_IPADDR = 0 ok
\n
"
);
#endif
s
.
state
=
DHCPS_STATE_ACK
;
}
else
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCP_OPTION_REQ_IPADDR != 0 err
\n
"
);
#endif
s
.
state
=
DHCPS_STATE_NAK
;
}
break
;
case
DHCP_OPTION_END
:
{
is_dhcp_parse_end
=
true
;
}
break
;
}
if
(
is_dhcp_parse_end
){
break
;
}
optptr
+=
optptr
[
1
]
+
2
;
}
switch
(
type
){
case
DHCPDISCOVER
:
//1
s
.
state
=
DHCPS_STATE_OFFER
;
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCPD_STATE_OFFER
\n
"
);
#endif
break
;
case
DHCPREQUEST
:
//3
if
(
!
(
s
.
state
==
DHCPS_STATE_ACK
||
s
.
state
==
DHCPS_STATE_NAK
)
)
{
s
.
state
=
DHCPS_STATE_NAK
;
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCPD_STATE_NAK
\n
"
);
#endif
}
break
;
case
DHCPDECLINE
:
//4
s
.
state
=
DHCPS_STATE_IDLE
;
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCPD_STATE_IDLE
\n
"
);
#endif
break
;
case
DHCPRELEASE
:
//7
s
.
state
=
DHCPS_STATE_IDLE
;
#if DHCPS_DEBUG
os_printf
(
"dhcps: DHCPD_STATE_IDLE
\n
"
);
#endif
break
;
}
#if DHCPS_DEBUG
os_printf
(
"dhcps: return s.state = %d
\n
"
,
s
.
state
);
#endif
return
s
.
state
;
}
///////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////
static
sint16_t
ICACHE_FLASH_ATTR
parse_msg
(
struct
dhcps_msg
*
m
,
u16_t
len
)
{
if
(
os_memcmp
((
char
*
)
m
->
options
,
&
magic_cookie
,
sizeof
(
magic_cookie
))
==
0
){
#if DHCPS_DEBUG
os_printf
(
"dhcps: len = %d
\n
"
,
len
);
#endif
/*
* ��¼��ǰ��xid���ﴦ���?
* �˺�ΪDHCP�ͻ����������û�ͳһ��ȡIPʱ��
*/
// if((old_xid[0] == 0) &&
// (old_xid[1] == 0) &&
// (old_xid[2] == 0) &&
// (old_xid[3] == 0)){
// /*
// * old_xidδ��¼�κ����?
// * �϶��ǵ�һ��ʹ��
// */
// os_memcpy((char *)old_xid, (char *)m->xid, sizeof(m->xid));
// }else{
// /*
// * ���δ����DHCP msg��Я���xid���ϴμ�¼�IJ�ͬ��
// * �϶�Ϊ��ͬ��DHCP�ͻ��˷��ͣ���ʱ����Ҫ����Ŀͻ���IP
// * ���� 192.168.4.100(0x6404A8C0) <--> 192.168.4.200(0xC804A8C0)
// *
// */
// if(os_memcmp((char *)old_xid, (char *)m->xid, sizeof(m->xid)) != 0){
/*
* ��¼���ε�xid�ţ�ͬʱ�����IP����
*/
struct
ip_addr
addr_tmp
;
// os_memcpy((char *)old_xid, (char *)m->xid, sizeof(m->xid));
{
struct
dhcps_pool
*
pdhcps_pool
=
NULL
;
list_node
*
pnode
=
NULL
;
list_node
*
pback_node
=
NULL
;
POOL_START:
client_address
.
addr
=
client_address_plus
.
addr
;
// addr_tmp.addr = htonl(client_address_plus.addr);
// addr_tmp.addr++;
// client_address_plus.addr = htonl(addr_tmp.addr);
for
(
pback_node
=
plist
;
pback_node
!=
NULL
;
pback_node
=
pback_node
->
pnext
)
{
pdhcps_pool
=
pback_node
->
pnode
;
if
(
os_memcmp
(
pdhcps_pool
->
mac
,
m
->
chaddr
,
sizeof
(
pdhcps_pool
->
mac
))
==
0
){
// os_printf("the same device request ip\n");
client_address
.
addr
=
pdhcps_pool
->
ip
.
addr
;
pdhcps_pool
->
lease_timer
=
DHCPS_LEASE_TIMER
;
goto
POOL_CHECK
;
}
else
if
(
pdhcps_pool
->
ip
.
addr
==
client_address_plus
.
addr
){
// client_address.addr = client_address_plus.addr;
// os_printf("the ip addr has been request\n");
addr_tmp
.
addr
=
htonl
(
client_address_plus
.
addr
);
addr_tmp
.
addr
++
;
client_address_plus
.
addr
=
htonl
(
addr_tmp
.
addr
);
client_address
.
addr
=
client_address_plus
.
addr
;
}
}
pdhcps_pool
=
(
struct
dhcps_pool
*
)
os_zalloc
(
sizeof
(
struct
dhcps_pool
));
pdhcps_pool
->
ip
.
addr
=
client_address
.
addr
;
os_memcpy
(
pdhcps_pool
->
mac
,
m
->
chaddr
,
sizeof
(
pdhcps_pool
->
mac
));
pdhcps_pool
->
lease_timer
=
DHCPS_LEASE_TIMER
;
pnode
=
(
list_node
*
)
os_zalloc
(
sizeof
(
list_node
));
pnode
->
pnode
=
pdhcps_pool
;
node_insert_to_list
(
&
plist
,
pnode
);
POOL_CHECK:
if
((
client_address_plus
.
addr
>
dhcps_lease
.
end_ip
.
addr
)
||
(
ip_addr_isany
(
&
client_address
))){
os_printf
(
"client_address_plus.addr %x %d
\n
"
,
client_address_plus
.
addr
,
system_get_free_heap_size
());
node_remove_from_list
(
&
plist
,
pnode
);
os_free
(
pdhcps_pool
);
pdhcps_pool
=
NULL
;
os_free
(
pnode
);
pnode
=
NULL
;
// client_address_plus.addr = dhcps_lease.start_ip.addr;
return
4
;
}
if
(
wifi_softap_set_station_info
(
m
->
chaddr
,
&
client_address
)
==
false
)
{
return
0
;
}
}
#if DHCPS_DEBUG
os_printf
(
"dhcps: xid changed
\n
"
);
os_printf
(
"dhcps: client_address.addr = %x
\n
"
,
client_address
.
addr
);
#endif
// }
// }
return
parse_options
(
&
m
->
options
[
4
],
len
);
}
return
0
;
}
///////////////////////////////////////////////////////////////////////////////////
/*
* DHCP ��������ݰ���մ���ص�����˺�����LWIP UDPģ������ʱ������
* ��Ҫ����udp_recv()������LWIP����ע��.
*
* @param arg
* @param pcb ���յ�UDP��Ŀ��ƿ�?
* @param p ���յ���UDP�е��������?
* @param addr ���ʹ�UDP���Դ�����IP��ַ
* @param port ���ʹ�UDP���Դ�����UDPͨ���˿ں�
*/
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
handle_dhcp
(
void
*
arg
,
struct
udp_pcb
*
pcb
,
struct
pbuf
*
p
,
struct
ip_addr
*
addr
,
uint16_t
port
)
{
struct
dhcps_msg
*
pmsg_dhcps
=
NULL
;
sint16_t
tlen
=
0
;
u16_t
i
=
0
;
u16_t
dhcps_msg_cnt
=
0
;
u8_t
*
p_dhcps_msg
=
NULL
;
u8_t
*
data
=
NULL
;
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> receive a packet
\n
"
);
#endif
if
(
p
==
NULL
)
return
;
pmsg_dhcps
=
(
struct
dhcps_msg
*
)
os_zalloc
(
sizeof
(
struct
dhcps_msg
));
if
(
NULL
==
pmsg_dhcps
){
pbuf_free
(
p
);
return
;
}
p_dhcps_msg
=
(
u8_t
*
)
pmsg_dhcps
;
tlen
=
p
->
tot_len
;
data
=
p
->
payload
;
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> p->tot_len = %d
\n
"
,
tlen
);
os_printf
(
"dhcps: handle_dhcp-> p->len = %d
\n
"
,
p
->
len
);
#endif
for
(
i
=
0
;
i
<
p
->
len
;
i
++
){
p_dhcps_msg
[
dhcps_msg_cnt
++
]
=
data
[
i
];
#if DHCPS_DEBUG
os_printf
(
"%02x "
,
data
[
i
]);
if
((
i
+
1
)
%
16
==
0
){
os_printf
(
"
\n
"
);
}
#endif
}
if
(
p
->
next
!=
NULL
)
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> p->next != NULL
\n
"
);
os_printf
(
"dhcps: handle_dhcp-> p->next->tot_len = %d
\n
"
,
p
->
next
->
tot_len
);
os_printf
(
"dhcps: handle_dhcp-> p->next->len = %d
\n
"
,
p
->
next
->
len
);
#endif
data
=
p
->
next
->
payload
;
for
(
i
=
0
;
i
<
p
->
next
->
len
;
i
++
){
p_dhcps_msg
[
dhcps_msg_cnt
++
]
=
data
[
i
];
#if DHCPS_DEBUG
os_printf
(
"%02x "
,
data
[
i
]);
if
((
i
+
1
)
%
16
==
0
){
os_printf
(
"
\n
"
);
}
#endif
}
}
/*
* DHCP �ͻ���������Ϣ����
*/
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> parse_msg(p)
\n
"
);
#endif
switch
(
parse_msg
(
pmsg_dhcps
,
tlen
-
240
))
{
case
DHCPS_STATE_OFFER
:
//1
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> DHCPD_STATE_OFFER
\n
"
);
#endif
send_offer
(
pmsg_dhcps
);
break
;
case
DHCPS_STATE_ACK
:
//3
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> DHCPD_STATE_ACK
\n
"
);
#endif
send_ack
(
pmsg_dhcps
);
break
;
case
DHCPS_STATE_NAK
:
//4
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> DHCPD_STATE_NAK
\n
"
);
#endif
send_nak
(
pmsg_dhcps
);
break
;
default
:
break
;
}
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> pbuf_free(p)
\n
"
);
#endif
pbuf_free
(
p
);
os_free
(
pmsg_dhcps
);
pmsg_dhcps
=
NULL
;
}
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
wifi_softap_init_dhcps_lease
(
uint32
ip
)
{
uint32
softap_ip
=
0
,
local_ip
=
0
;
if
(
dhcps_lease_flag
)
{
local_ip
=
softap_ip
=
htonl
(
ip
);
softap_ip
&=
0xFFFFFF00
;
local_ip
&=
0xFF
;
if
(
local_ip
>=
0x80
)
local_ip
-=
DHCPS_MAX_LEASE
;
else
local_ip
++
;
os_bzero
(
&
dhcps_lease
,
sizeof
(
dhcps_lease
));
dhcps_lease
.
start_ip
.
addr
=
softap_ip
|
local_ip
;
dhcps_lease
.
end_ip
.
addr
=
softap_ip
|
(
local_ip
+
DHCPS_MAX_LEASE
);
}
dhcps_lease
.
start_ip
.
addr
=
htonl
(
dhcps_lease
.
start_ip
.
addr
);
dhcps_lease
.
end_ip
.
addr
=
htonl
(
dhcps_lease
.
end_ip
.
addr
);
// os_printf("start_ip = 0x%x, end_ip = 0x%x\n",dhcps_lease.start_ip, dhcps_lease.end_ip);
}
///////////////////////////////////////////////////////////////////////////////////
void
ICACHE_FLASH_ATTR
dhcps_start
(
struct
ip_info
*
info
)
{
struct
netif
*
apnetif
=
(
struct
netif
*
)
eagle_lwip_getif
(
0x01
);
if
(
apnetif
->
dhcps_pcb
!=
NULL
)
{
udp_remove
(
apnetif
->
dhcps_pcb
);
}
pcb_dhcps
=
udp_new
();
if
(
pcb_dhcps
==
NULL
||
info
==
NULL
)
{
os_printf
(
"dhcps_start(): could not obtain pcb
\n
"
);
}
apnetif
->
dhcps_pcb
=
pcb_dhcps
;
IP4_ADDR
(
&
broadcast_dhcps
,
255
,
255
,
255
,
255
);
server_address
=
info
->
ip
;
wifi_softap_init_dhcps_lease
(
server_address
.
addr
);
client_address_plus
.
addr
=
dhcps_lease
.
start_ip
.
addr
;
udp_bind
(
pcb_dhcps
,
IP_ADDR_ANY
,
DHCPS_SERVER_PORT
);
udp_recv
(
pcb_dhcps
,
handle_dhcp
,
NULL
);
#if DHCPS_DEBUG
os_printf
(
"dhcps:dhcps_start->udp_recv function Set a receive callback handle_dhcp for UDP_PCB pcb_dhcps
\n
"
);
#endif
}
void
ICACHE_FLASH_ATTR
dhcps_stop
(
void
)
{
struct
netif
*
apnetif
=
(
struct
netif
*
)
eagle_lwip_getif
(
0x01
);
udp_disconnect
(
pcb_dhcps
);
dhcps_lease_flag
=
true
;
if
(
apnetif
->
dhcps_pcb
!=
NULL
)
{
udp_remove
(
apnetif
->
dhcps_pcb
);
apnetif
->
dhcps_pcb
=
NULL
;
}
//udp_remove(pcb_dhcps);
list_node
*
pnode
=
NULL
;
list_node
*
pback_node
=
NULL
;
pnode
=
plist
;
while
(
pnode
!=
NULL
)
{
pback_node
=
pnode
;
pnode
=
pback_node
->
pnext
;
node_remove_from_list
(
&
plist
,
pback_node
);
os_free
(
pback_node
->
pnode
);
pback_node
->
pnode
=
NULL
;
os_free
(
pback_node
);
pback_node
=
NULL
;
}
}
/******************************************************************************
* FunctionName : wifi_softap_set_dhcps_lease
* Description : set the lease information of DHCP server
* Parameters : please -- Additional argument to set the lease information,
* Little-Endian.
* Returns : true or false
*******************************************************************************/
bool
ICACHE_FLASH_ATTR
wifi_softap_set_dhcps_lease
(
struct
dhcps_lease
*
please
)
{
struct
ip_info
info
;
uint32
softap_ip
=
0
;
uint32
start_ip
=
0
;
uint32
end_ip
=
0
;
uint8
opmode
=
wifi_get_opmode
();
if
(
opmode
==
STATION_MODE
||
opmode
==
NULL_MODE
)
{
return
false
;
}
if
(
please
==
NULL
||
wifi_softap_dhcps_status
()
==
DHCP_STARTED
)
return
false
;
os_bzero
(
&
info
,
sizeof
(
struct
ip_info
));
wifi_get_ip_info
(
SOFTAP_IF
,
&
info
);
softap_ip
=
htonl
(
info
.
ip
.
addr
);
start_ip
=
htonl
(
please
->
start_ip
.
addr
);
end_ip
=
htonl
(
please
->
end_ip
.
addr
);
/*config ip information can't contain local ip*/
if
((
start_ip
<=
softap_ip
)
&&
(
softap_ip
<=
end_ip
))
return
false
;
/*config ip information must be in the same segment as the local ip*/
softap_ip
>>=
8
;
if
((
start_ip
>>
8
!=
softap_ip
)
||
(
end_ip
>>
8
!=
softap_ip
))
{
return
false
;
}
if
(
end_ip
-
start_ip
>
DHCPS_MAX_LEASE
)
return
false
;
os_bzero
(
&
dhcps_lease
,
sizeof
(
dhcps_lease
));
dhcps_lease
.
start_ip
.
addr
=
start_ip
;
dhcps_lease
.
end_ip
.
addr
=
end_ip
;
dhcps_lease_flag
=
false
;
return
true
;
}
/******************************************************************************
* FunctionName : wifi_softap_get_dhcps_lease
* Description : get the lease information of DHCP server
* Parameters : please -- Additional argument to get the lease information,
* Little-Endian.
* Returns : true or false
*******************************************************************************/
bool
ICACHE_FLASH_ATTR
wifi_softap_get_dhcps_lease
(
struct
dhcps_lease
*
please
)
{
uint8
opmode
=
wifi_get_opmode
();
if
(
opmode
==
STATION_MODE
||
opmode
==
NULL_MODE
)
{
return
false
;
}
if
(
NULL
==
please
)
return
false
;
if
(
dhcps_lease_flag
){
if
(
wifi_softap_dhcps_status
()
==
DHCP_STOPPED
)
return
false
;
}
else
{
os_bzero
(
please
,
sizeof
(
dhcps_lease
));
if
(
wifi_softap_dhcps_status
()
==
DHCP_STOPPED
){
please
->
start_ip
.
addr
=
htonl
(
dhcps_lease
.
start_ip
.
addr
);
please
->
end_ip
.
addr
=
htonl
(
dhcps_lease
.
end_ip
.
addr
);
}
}
if
(
wifi_softap_dhcps_status
()
==
DHCP_STARTED
){
os_bzero
(
please
,
sizeof
(
dhcps_lease
));
please
->
start_ip
.
addr
=
dhcps_lease
.
start_ip
.
addr
;
please
->
end_ip
.
addr
=
dhcps_lease
.
end_ip
.
addr
;
}
return
true
;
}
static
void
ICACHE_FLASH_ATTR
kill_oldest_dhcps_pool
(
void
)
{
list_node
*
pre
=
NULL
,
*
p
=
NULL
;
list_node
*
minpre
=
NULL
,
*
minp
=
NULL
;
struct
dhcps_pool
*
pdhcps_pool
=
NULL
,
*
pmin_pool
=
NULL
;
pre
=
plist
;
p
=
pre
->
pnext
;
minpre
=
pre
;
minp
=
p
;
while
(
p
!=
NULL
){
pdhcps_pool
=
p
->
pnode
;
pmin_pool
=
minp
->
pnode
;
if
(
pdhcps_pool
->
lease_timer
<
pmin_pool
->
lease_timer
){
minp
=
p
;
minpre
=
pre
;
}
pre
=
p
;
p
=
p
->
pnext
;
}
minpre
->
pnext
=
minp
->
pnext
;
os_free
(
minp
->
pnode
);
minp
->
pnode
=
NULL
;
os_free
(
minp
);
minp
=
NULL
;
}
void
ICACHE_FLASH_ATTR
dhcps_coarse_tmr
(
void
)
{
uint8
num_dhcps_pool
=
0
;
list_node
*
pback_node
=
NULL
;
list_node
*
pnode
=
NULL
;
struct
dhcps_pool
*
pdhcps_pool
=
NULL
;
pnode
=
plist
;
while
(
pnode
!=
NULL
)
{
pdhcps_pool
=
pnode
->
pnode
;
pdhcps_pool
->
lease_timer
--
;
if
(
pdhcps_pool
->
lease_timer
==
0
){
pback_node
=
pnode
;
pnode
=
pback_node
->
pnext
;
node_remove_from_list
(
&
plist
,
pback_node
);
os_free
(
pback_node
->
pnode
);
pback_node
->
pnode
=
NULL
;
os_free
(
pback_node
);
pback_node
=
NULL
;
}
else
{
pnode
=
pnode
->
pnext
;
num_dhcps_pool
++
;
}
}
if
(
num_dhcps_pool
>=
MAX_STATION_NUM
)
kill_oldest_dhcps_pool
();
}
bool
ICACHE_FLASH_ATTR
wifi_softap_set_dhcps_offer_option
(
uint8
level
,
void
*
optarg
)
{
bool
offer_flag
=
true
;
uint8
option
=
0
;
if
(
optarg
==
NULL
&&
wifi_softap_dhcps_status
()
==
false
)
return
false
;
if
(
level
<=
OFFER_START
||
level
>=
OFFER_END
)
return
false
;
switch
(
level
){
case
OFFER_ROUTER
:
offer
=
(
*
(
uint8
*
)
optarg
)
&
0x01
;
offer_flag
=
true
;
break
;
default
:
offer_flag
=
false
;
break
;
}
return
offer_flag
;
}
if
(
os_memcmp
((
char
*
)
m
->
options
,
&
magic_cookie
,
sizeof
(
magic_cookie
))
==
0
){
#if DHCPS_DEBUG
os_printf
(
"dhcps: len = %d
\n
"
,
len
);
#endif
/*
* ��¼��ǰ��xid���ﴦ���?
* �˺�ΪDHCP�ͻ����������û�ͳһ��ȡIPʱ��
*/
// if((old_xid[0] == 0) &&
// (old_xid[1] == 0) &&
// (old_xid[2] == 0) &&
// (old_xid[3] == 0)){
// /*
// * old_xidδ��¼�κ����?
// * �϶��ǵ�һ��ʹ��
// */
// os_memcpy((char *)old_xid, (char *)m->xid, sizeof(m->xid));
// }else{
// /*
// * ���δ����DHCP msg��Я���xid���ϴμ�¼�IJ�ͬ��
// * �϶�Ϊ��ͬ��DHCP�ͻ��˷��ͣ���ʱ����Ҫ����Ŀͻ���IP
// * ���� 192.168.4.100(0x6404A8C0) <--> 192.168.4.200(0xC804A8C0)
// *
// */
// if(os_memcmp((char *)old_xid, (char *)m->xid, sizeof(m->xid)) != 0){
/*
* ��¼���ε�xid�ţ�ͬʱ�����IP����
*/
struct
ip_addr
addr_tmp
;
// os_memcpy((char *)old_xid, (char *)m->xid, sizeof(m->xid));
// {
struct
dhcps_pool
*
pdhcps_pool
=
NULL
;
list_node
*
pnode
=
NULL
;
list_node
*
pback_node
=
NULL
;
struct
ip_addr
first_address
;
bool
flag
=
false
;
// POOL_START:
first_address
.
addr
=
dhcps_lease
.
start_ip
.
addr
;
client_address
.
addr
=
client_address_plus
.
addr
;
renew
=
false
;
// addr_tmp.addr = htonl(client_address_plus.addr);
// addr_tmp.addr++;
// client_address_plus.addr = htonl(addr_tmp.addr);
for
(
pback_node
=
plist
;
pback_node
!=
NULL
;
pback_node
=
pback_node
->
pnext
)
{
pdhcps_pool
=
pback_node
->
pnode
;
if
(
os_memcmp
(
pdhcps_pool
->
mac
,
m
->
chaddr
,
sizeof
(
pdhcps_pool
->
mac
))
==
0
){
// os_printf("the same device request ip\n");
if
(
os_memcmp
(
&
pdhcps_pool
->
ip
.
addr
,
m
->
ciaddr
,
sizeof
(
pdhcps_pool
->
ip
.
addr
))
==
0
)
{
renew
=
true
;
}
client_address
.
addr
=
pdhcps_pool
->
ip
.
addr
;
pdhcps_pool
->
lease_timer
=
DHCPS_LEASE_TIMER
;
pnode
=
pback_node
;
goto
POOL_CHECK
;
}
else
if
(
pdhcps_pool
->
ip
.
addr
==
client_address_plus
.
addr
){
// client_address.addr = client_address_plus.addr;
// os_printf("the ip addr has been request\n");
addr_tmp
.
addr
=
htonl
(
client_address_plus
.
addr
);
addr_tmp
.
addr
++
;
client_address_plus
.
addr
=
htonl
(
addr_tmp
.
addr
);
client_address
.
addr
=
client_address_plus
.
addr
;
}
if
(
flag
==
false
)
{
// search the fisrt unused ip
if
(
first_address
.
addr
<
pdhcps_pool
->
ip
.
addr
)
{
flag
=
true
;
}
else
{
addr_tmp
.
addr
=
htonl
(
first_address
.
addr
);
addr_tmp
.
addr
++
;
first_address
.
addr
=
htonl
(
addr_tmp
.
addr
);
}
}
}
if
(
client_address_plus
.
addr
>
dhcps_lease
.
end_ip
.
addr
)
{
client_address
.
addr
=
first_address
.
addr
;
}
if
(
client_address
.
addr
>
dhcps_lease
.
end_ip
.
addr
)
{
client_address_plus
.
addr
=
dhcps_lease
.
start_ip
.
addr
;
pdhcps_pool
=
NULL
;
pnode
=
NULL
;
}
else
{
pdhcps_pool
=
(
struct
dhcps_pool
*
)
os_zalloc
(
sizeof
(
struct
dhcps_pool
));
pdhcps_pool
->
ip
.
addr
=
client_address
.
addr
;
os_memcpy
(
pdhcps_pool
->
mac
,
m
->
chaddr
,
sizeof
(
pdhcps_pool
->
mac
));
pdhcps_pool
->
lease_timer
=
DHCPS_LEASE_TIMER
;
pnode
=
(
list_node
*
)
os_zalloc
(
sizeof
(
list_node
));
pnode
->
pnode
=
pdhcps_pool
;
pnode
->
pnext
=
NULL
;
node_insert_to_list
(
&
plist
,
pnode
);
if
(
client_address
.
addr
==
dhcps_lease
.
end_ip
.
addr
)
{
client_address_plus
.
addr
=
dhcps_lease
.
start_ip
.
addr
;
}
else
{
addr_tmp
.
addr
=
htonl
(
client_address
.
addr
);
addr_tmp
.
addr
++
;
client_address_plus
.
addr
=
htonl
(
addr_tmp
.
addr
);
}
}
POOL_CHECK:
if
((
client_address
.
addr
>
dhcps_lease
.
end_ip
.
addr
)
||
(
ip_addr_isany
(
&
client_address
))){
os_printf
(
"client_address_plus.addr %x %d
\n
"
,
client_address_plus
.
addr
,
system_get_free_heap_size
());
if
(
pnode
!=
NULL
)
{
node_remove_from_list
(
&
plist
,
pnode
);
os_free
(
pnode
);
pnode
=
NULL
;
}
if
(
pdhcps_pool
!=
NULL
)
{
os_free
(
pdhcps_pool
);
pdhcps_pool
=
NULL
;
}
// client_address_plus.addr = dhcps_lease.start_ip.addr;
return
4
;
}
sint16_t
ret
=
parse_options
(
&
m
->
options
[
4
],
len
);;
if
(
ret
==
DHCPS_STATE_RELEASE
)
{
if
(
pnode
!=
NULL
)
{
node_remove_from_list
(
&
plist
,
pnode
);
os_free
(
pnode
);
pnode
=
NULL
;
}
if
(
pdhcps_pool
!=
NULL
)
{
os_free
(
pdhcps_pool
);
pdhcps_pool
=
NULL
;
}
os_memset
(
&
client_address
,
0x0
,
sizeof
(
client_address
));
}
if
(
wifi_softap_set_station_info
(
m
->
chaddr
,
&
client_address
)
==
false
)
{
return
0
;
}
// }
#if DHCPS_DEBUG
os_printf
(
"dhcps: xid changed
\n
"
);
os_printf
(
"dhcps: client_address.addr = %x
\n
"
,
client_address
.
addr
);
#endif
// }
// }
return
ret
;
}
return
0
;
}
///////////////////////////////////////////////////////////////////////////////////
/*
* DHCP ��������ݰ���մ���ص�����˺�����LWIP UDPģ������ʱ������
* ��Ҫ����udp_recv()������LWIP����ע��.
*
* @param arg
* @param pcb ���յ�UDP��Ŀ��ƿ�?
* @param p ���յ���UDP�е��������?
* @param addr ���ʹ�UDP���Դ�����IP��ַ
* @param port ���ʹ�UDP���Դ�����UDPͨ���˿ں�
*/
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
handle_dhcp
(
void
*
arg
,
struct
udp_pcb
*
pcb
,
struct
pbuf
*
p
,
struct
ip_addr
*
addr
,
uint16_t
port
)
{
struct
dhcps_msg
*
pmsg_dhcps
=
NULL
;
sint16_t
tlen
=
0
;
u16_t
i
=
0
;
u16_t
dhcps_msg_cnt
=
0
;
u8_t
*
p_dhcps_msg
=
NULL
;
u8_t
*
data
=
NULL
;
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> receive a packet
\n
"
);
#endif
if
(
p
==
NULL
)
return
;
pmsg_dhcps
=
(
struct
dhcps_msg
*
)
os_zalloc
(
sizeof
(
struct
dhcps_msg
));
if
(
NULL
==
pmsg_dhcps
){
pbuf_free
(
p
);
return
;
}
p_dhcps_msg
=
(
u8_t
*
)
pmsg_dhcps
;
tlen
=
p
->
tot_len
;
data
=
p
->
payload
;
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> p->tot_len = %d
\n
"
,
tlen
);
os_printf
(
"dhcps: handle_dhcp-> p->len = %d
\n
"
,
p
->
len
);
#endif
for
(
i
=
0
;
i
<
p
->
len
;
i
++
){
p_dhcps_msg
[
dhcps_msg_cnt
++
]
=
data
[
i
];
#if DHCPS_DEBUG
os_printf
(
"%02x "
,
data
[
i
]);
if
((
i
+
1
)
%
16
==
0
){
os_printf
(
"
\n
"
);
}
#endif
}
if
(
p
->
next
!=
NULL
)
{
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> p->next != NULL
\n
"
);
os_printf
(
"dhcps: handle_dhcp-> p->next->tot_len = %d
\n
"
,
p
->
next
->
tot_len
);
os_printf
(
"dhcps: handle_dhcp-> p->next->len = %d
\n
"
,
p
->
next
->
len
);
#endif
data
=
p
->
next
->
payload
;
for
(
i
=
0
;
i
<
p
->
next
->
len
;
i
++
){
p_dhcps_msg
[
dhcps_msg_cnt
++
]
=
data
[
i
];
#if DHCPS_DEBUG
os_printf
(
"%02x "
,
data
[
i
]);
if
((
i
+
1
)
%
16
==
0
){
os_printf
(
"
\n
"
);
}
#endif
}
}
/*
* DHCP �ͻ���������Ϣ����
*/
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> parse_msg(p)
\n
"
);
#endif
switch
(
parse_msg
(
pmsg_dhcps
,
tlen
-
240
))
{
case
DHCPS_STATE_OFFER
:
//1
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> DHCPD_STATE_OFFER
\n
"
);
#endif
send_offer
(
pmsg_dhcps
);
break
;
case
DHCPS_STATE_ACK
:
//3
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> DHCPD_STATE_ACK
\n
"
);
#endif
send_ack
(
pmsg_dhcps
);
break
;
case
DHCPS_STATE_NAK
:
//4
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> DHCPD_STATE_NAK
\n
"
);
#endif
send_nak
(
pmsg_dhcps
);
break
;
default
:
break
;
}
#if DHCPS_DEBUG
os_printf
(
"dhcps: handle_dhcp-> pbuf_free(p)
\n
"
);
#endif
pbuf_free
(
p
);
os_free
(
pmsg_dhcps
);
pmsg_dhcps
=
NULL
;
}
///////////////////////////////////////////////////////////////////////////////////
static
void
ICACHE_FLASH_ATTR
wifi_softap_init_dhcps_lease
(
uint32
ip
)
{
uint32
softap_ip
=
0
,
local_ip
=
0
;
uint32
start_ip
=
0
;
uint32
end_ip
=
0
;
// if (dhcps_lease_flag) {
if
(
dhcps_lease
.
enable
==
TRUE
)
{
softap_ip
=
htonl
(
ip
);
start_ip
=
htonl
(
dhcps_lease
.
start_ip
.
addr
);
end_ip
=
htonl
(
dhcps_lease
.
end_ip
.
addr
);
/*config ip information can't contain local ip*/
if
((
start_ip
<=
softap_ip
)
&&
(
softap_ip
<=
end_ip
))
{
dhcps_lease
.
enable
=
FALSE
;
}
else
{
/*config ip information must be in the same segment as the local ip*/
softap_ip
>>=
8
;
if
(((
start_ip
>>
8
!=
softap_ip
)
||
(
end_ip
>>
8
!=
softap_ip
))
||
(
end_ip
-
start_ip
>
DHCPS_MAX_LEASE
))
{
dhcps_lease
.
enable
=
FALSE
;
}
}
}
if
(
dhcps_lease
.
enable
==
FALSE
)
{
local_ip
=
softap_ip
=
htonl
(
ip
);
softap_ip
&=
0xFFFFFF00
;
local_ip
&=
0xFF
;
if
(
local_ip
>=
0x80
)
local_ip
-=
DHCPS_MAX_LEASE
;
else
local_ip
++
;
os_bzero
(
&
dhcps_lease
,
sizeof
(
dhcps_lease
));
dhcps_lease
.
start_ip
.
addr
=
softap_ip
|
local_ip
;
dhcps_lease
.
end_ip
.
addr
=
softap_ip
|
(
local_ip
+
DHCPS_MAX_LEASE
-
1
);
dhcps_lease
.
start_ip
.
addr
=
htonl
(
dhcps_lease
.
start_ip
.
addr
);
dhcps_lease
.
end_ip
.
addr
=
htonl
(
dhcps_lease
.
end_ip
.
addr
);
}
// dhcps_lease.start_ip.addr = htonl(dhcps_lease.start_ip.addr);
// dhcps_lease.end_ip.addr= htonl(dhcps_lease.end_ip.addr);
// os_printf("start_ip = 0x%x, end_ip = 0x%x\n",dhcps_lease.start_ip, dhcps_lease.end_ip);
}
///////////////////////////////////////////////////////////////////////////////////
void
ICACHE_FLASH_ATTR
dhcps_start
(
struct
ip_info
*
info
)
{
struct
netif
*
apnetif
=
(
struct
netif
*
)
eagle_lwip_getif
(
0x01
);
if
(
apnetif
->
dhcps_pcb
!=
NULL
)
{
udp_remove
(
apnetif
->
dhcps_pcb
);
}
pcb_dhcps
=
udp_new
();
if
(
pcb_dhcps
==
NULL
||
info
==
NULL
)
{
os_printf
(
"dhcps_start(): could not obtain pcb
\n
"
);
}
apnetif
->
dhcps_pcb
=
pcb_dhcps
;
IP4_ADDR
(
&
broadcast_dhcps
,
255
,
255
,
255
,
255
);
server_address
=
info
->
ip
;
wifi_softap_init_dhcps_lease
(
server_address
.
addr
);
client_address_plus
.
addr
=
dhcps_lease
.
start_ip
.
addr
;
udp_bind
(
pcb_dhcps
,
IP_ADDR_ANY
,
DHCPS_SERVER_PORT
);
udp_recv
(
pcb_dhcps
,
handle_dhcp
,
NULL
);
#if DHCPS_DEBUG
os_printf
(
"dhcps:dhcps_start->udp_recv function Set a receive callback handle_dhcp for UDP_PCB pcb_dhcps
\n
"
);
#endif
}
void
ICACHE_FLASH_ATTR
dhcps_stop
(
void
)
{
struct
netif
*
apnetif
=
(
struct
netif
*
)
eagle_lwip_getif
(
0x01
);
udp_disconnect
(
pcb_dhcps
);
// dhcps_lease_flag = true;
if
(
apnetif
->
dhcps_pcb
!=
NULL
)
{
udp_remove
(
apnetif
->
dhcps_pcb
);
apnetif
->
dhcps_pcb
=
NULL
;
}
//udp_remove(pcb_dhcps);
list_node
*
pnode
=
NULL
;
list_node
*
pback_node
=
NULL
;
pnode
=
plist
;
while
(
pnode
!=
NULL
)
{
pback_node
=
pnode
;
pnode
=
pback_node
->
pnext
;
node_remove_from_list
(
&
plist
,
pback_node
);
os_free
(
pback_node
->
pnode
);
pback_node
->
pnode
=
NULL
;
os_free
(
pback_node
);
pback_node
=
NULL
;
}
}
/******************************************************************************
* FunctionName : wifi_softap_set_dhcps_lease
* Description : set the lease information of DHCP server
* Parameters : please -- Additional argument to set the lease information,
* Little-Endian.
* Returns : true or false
*******************************************************************************/
bool
ICACHE_FLASH_ATTR
wifi_softap_set_dhcps_lease
(
struct
dhcps_lease
*
please
)
{
struct
ip_info
info
;
uint32
softap_ip
=
0
;
uint32
start_ip
=
0
;
uint32
end_ip
=
0
;
uint8
opmode
=
wifi_get_opmode
();
if
(
opmode
==
STATION_MODE
||
opmode
==
NULL_MODE
)
{
return
false
;
}
if
(
please
==
NULL
||
wifi_softap_dhcps_status
()
==
DHCP_STARTED
)
return
false
;
if
(
please
->
enable
)
{
os_bzero
(
&
info
,
sizeof
(
struct
ip_info
));
wifi_get_ip_info
(
SOFTAP_IF
,
&
info
);
softap_ip
=
htonl
(
info
.
ip
.
addr
);
start_ip
=
htonl
(
please
->
start_ip
.
addr
);
end_ip
=
htonl
(
please
->
end_ip
.
addr
);
/*config ip information can't contain local ip*/
if
((
start_ip
<=
softap_ip
)
&&
(
softap_ip
<=
end_ip
))
return
false
;
/*config ip information must be in the same segment as the local ip*/
softap_ip
>>=
8
;
if
((
start_ip
>>
8
!=
softap_ip
)
||
(
end_ip
>>
8
!=
softap_ip
))
{
return
false
;
}
if
(
end_ip
-
start_ip
>
DHCPS_MAX_LEASE
)
return
false
;
os_bzero
(
&
dhcps_lease
,
sizeof
(
dhcps_lease
));
// dhcps_lease.start_ip.addr = start_ip;
// dhcps_lease.end_ip.addr = end_ip;
dhcps_lease
.
start_ip
.
addr
=
please
->
start_ip
.
addr
;
dhcps_lease
.
end_ip
.
addr
=
please
->
end_ip
.
addr
;
}
dhcps_lease
.
enable
=
please
->
enable
;
// dhcps_lease_flag = false;
return
true
;
}
/******************************************************************************
* FunctionName : wifi_softap_get_dhcps_lease
* Description : get the lease information of DHCP server
* Parameters : please -- Additional argument to get the lease information,
* Little-Endian.
* Returns : true or false
*******************************************************************************/
bool
ICACHE_FLASH_ATTR
wifi_softap_get_dhcps_lease
(
struct
dhcps_lease
*
please
)
{
uint8
opmode
=
wifi_get_opmode
();
if
(
opmode
==
STATION_MODE
||
opmode
==
NULL_MODE
)
{
return
false
;
}
if
(
NULL
==
please
)
return
false
;
// if (dhcps_lease_flag){
if
(
dhcps_lease
.
enable
==
FALSE
){
if
(
wifi_softap_dhcps_status
()
==
DHCP_STOPPED
)
return
false
;
}
else
{
// os_bzero(please, sizeof(dhcps_lease));
// if (wifi_softap_dhcps_status() == DHCP_STOPPED){
// please->start_ip.addr = htonl(dhcps_lease.start_ip.addr);
// please->end_ip.addr = htonl(dhcps_lease.end_ip.addr);
// }
}
// if (wifi_softap_dhcps_status() == DHCP_STARTED){
// os_bzero(please, sizeof(dhcps_lease));
// please->start_ip.addr = dhcps_lease.start_ip.addr;
// please->end_ip.addr = dhcps_lease.end_ip.addr;
// }
please
->
start_ip
.
addr
=
dhcps_lease
.
start_ip
.
addr
;
please
->
end_ip
.
addr
=
dhcps_lease
.
end_ip
.
addr
;
return
true
;
}
static
void
ICACHE_FLASH_ATTR
kill_oldest_dhcps_pool
(
void
)
{
list_node
*
pre
=
NULL
,
*
p
=
NULL
;
list_node
*
minpre
=
NULL
,
*
minp
=
NULL
;
struct
dhcps_pool
*
pdhcps_pool
=
NULL
,
*
pmin_pool
=
NULL
;
pre
=
plist
;
p
=
pre
->
pnext
;
minpre
=
pre
;
minp
=
p
;
while
(
p
!=
NULL
){
pdhcps_pool
=
p
->
pnode
;
pmin_pool
=
minp
->
pnode
;
if
(
pdhcps_pool
->
lease_timer
<
pmin_pool
->
lease_timer
){
minp
=
p
;
minpre
=
pre
;
}
pre
=
p
;
p
=
p
->
pnext
;
}
minpre
->
pnext
=
minp
->
pnext
;
os_free
(
minp
->
pnode
);
minp
->
pnode
=
NULL
;
os_free
(
minp
);
minp
=
NULL
;
}
void
ICACHE_FLASH_ATTR
dhcps_coarse_tmr
(
void
)
{
uint8
num_dhcps_pool
=
0
;
list_node
*
pback_node
=
NULL
;
list_node
*
pnode
=
NULL
;
struct
dhcps_pool
*
pdhcps_pool
=
NULL
;
pnode
=
plist
;
while
(
pnode
!=
NULL
)
{
pdhcps_pool
=
pnode
->
pnode
;
pdhcps_pool
->
lease_timer
--
;
if
(
pdhcps_pool
->
lease_timer
==
0
){
pback_node
=
pnode
;
pnode
=
pback_node
->
pnext
;
node_remove_from_list
(
&
plist
,
pback_node
);
os_free
(
pback_node
->
pnode
);
pback_node
->
pnode
=
NULL
;
os_free
(
pback_node
);
pback_node
=
NULL
;
}
else
{
pnode
=
pnode
->
pnext
;
num_dhcps_pool
++
;
}
}
if
(
num_dhcps_pool
>=
MAX_STATION_NUM
)
kill_oldest_dhcps_pool
();
}
bool
ICACHE_FLASH_ATTR
wifi_softap_set_dhcps_offer_option
(
uint8
level
,
void
*
optarg
)
{
bool
offer_flag
=
true
;
uint8
option
=
0
;
if
(
optarg
==
NULL
&&
wifi_softap_dhcps_status
()
==
false
)
return
false
;
if
(
level
<=
OFFER_START
||
level
>=
OFFER_END
)
return
false
;
switch
(
level
){
case
OFFER_ROUTER
:
offer
=
(
*
(
uint8
*
)
optarg
)
&
0x01
;
offer_flag
=
true
;
break
;
default
:
offer_flag
=
false
;
break
;
}
return
offer_flag
;
}
bool
ICACHE_FLASH_ATTR
wifi_softap_set_dhcps_lease_time
(
uint32
minute
)
{
uint8
opmode
=
wifi_get_opmode
();
if
(
opmode
==
STATION_MODE
||
opmode
==
NULL_MODE
)
{
return
false
;
}
if
(
wifi_softap_dhcps_status
()
==
DHCP_STARTED
)
{
return
false
;
}
if
(
minute
==
0
)
{
return
false
;
}
dhcps_lease_time
=
minute
;
return
true
;
}
bool
ICACHE_FLASH_ATTR
wifi_softap_reset_dhcps_lease_time
(
void
)
{
uint8
opmode
=
wifi_get_opmode
();
if
(
opmode
==
STATION_MODE
||
opmode
==
NULL_MODE
)
{
return
false
;
}
if
(
wifi_softap_dhcps_status
()
==
DHCP_STARTED
)
{
return
false
;
}
dhcps_lease_time
=
DHCPS_LEASE_TIME_DEF
;
return
true
;
}
uint32
ICACHE_FLASH_ATTR
wifi_softap_get_dhcps_lease_time
(
void
)
// minute
{
return
dhcps_lease_time
;
}
app/lwip/app/espconn.c
View file @
5d5be356
...
...
@@ -25,6 +25,10 @@
#include "lwip/app/espconn.h"
#include "user_interface.h"
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
espconn_msg
*
plink_active
=
NULL
;
espconn_msg
*
pserver_list
=
NULL
;
remot_info
premot
[
linkMax
];
...
...
@@ -385,6 +389,10 @@ espconn_sent(struct espconn *espconn, uint8 *psent, uint16 length)
if
(
espconn_copy_enabled
(
pnode
)){
if
(
espconn_tcp_get_buf_count
(
pnode
->
pcommon
.
pbuf
)
>=
pnode
->
pcommon
.
pbuf_num
)
return
ESPCONN_MAXNUM
;
}
else
{
struct
tcp_pcb
*
pcb
=
pnode
->
pcommon
.
pcb
;
if
(
pcb
->
snd_queuelen
>=
TCP_SND_QUEUELEN
)
return
ESPCONN_MAXNUM
;
}
pbuf
=
(
espconn_buf
*
)
os_zalloc
(
sizeof
(
espconn_buf
));
...
...
@@ -405,13 +413,13 @@ espconn_sent(struct espconn *espconn, uint8 *psent, uint16 length)
if
(
espconn_copy_disabled
(
pnode
))
pnode
->
pcommon
.
write_flag
=
false
;
error
=
espconn_tcp_write
(
pnode
);
if
(
error
!=
ESPCONN_OK
){
/*send the application packet fail,
* ensure that each allocated is deleted*/
espconn_pbuf_delete
(
&
pnode
->
pcommon
.
pbuf
,
pbuf
);
os_free
(
pbuf
);
pbuf
=
NULL
;
}
//
if (error != ESPCONN_OK){
//
/*send the application packet fail,
//
* ensure that each allocated is deleted*/
//
espconn_pbuf_delete(&pnode->pcommon.pbuf, pbuf);
//
os_free(pbuf);
//
pbuf = NULL;
//
}
return
error
;
}
else
return
ESPCONN_ARG
;
...
...
@@ -428,6 +436,33 @@ espconn_sent(struct espconn *espconn, uint8 *psent, uint16 length)
return
ESPCONN_ARG
;
}
/******************************************************************************
* FunctionName : espconn_sendto
* Description : send data for UDP
* Parameters : espconn -- espconn to set for UDP
* psent -- data to send
* length -- length of data to send
* Returns : error
*******************************************************************************/
sint16
ICACHE_FLASH_ATTR
espconn_sendto
(
struct
espconn
*
espconn
,
uint8
*
psent
,
uint16
length
)
{
espconn_msg
*
pnode
=
NULL
;
bool
value
=
false
;
err_t
error
=
ESPCONN_OK
;
if
(
espconn
==
NULL
||
psent
==
NULL
||
length
==
0
)
{
return
ESPCONN_ARG
;
}
/*Find the node depend on the espconn message*/
value
=
espconn_find_connection
(
espconn
,
&
pnode
);
if
(
value
&&
espconn
->
type
==
ESPCONN_UDP
)
return
espconn_udp_sendto
(
pnode
,
psent
,
length
);
else
return
ESPCONN_ARG
;
}
/******************************************************************************
* FunctionName : espconn_send
* Description : sent data for client or server
...
...
app/lwip/app/espconn_tcp.c
View file @
5d5be356
...
...
@@ -24,6 +24,10 @@
#include "lwip/mem.h"
#include "lwip/app/espconn_tcp.h"
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
extern
espconn_msg
*
plink_active
;
extern
espconn_msg
*
pserver_list
;
extern
struct
espconn_packet
pktinfo
[
2
];
...
...
@@ -71,7 +75,7 @@ espconn_kill_oldest(void)
inactivity
=
0
;
inactive
=
NULL
;
for
(
pcb
=
tcp_active_pcbs
;
pcb
!=
NULL
;
pcb
=
pcb
->
next
)
{
if
(
pcb
->
state
==
FIN_WAIT_2
){
if
(
pcb
->
state
==
FIN_WAIT_1
||
pcb
->
state
==
FIN_WAIT_2
){
if
((
u32_t
)
(
tcp_ticks
-
pcb
->
tmr
)
>=
inactivity
)
{
inactivity
=
tcp_ticks
-
pcb
->
tmr
;
inactive
=
pcb
;
...
...
@@ -121,7 +125,7 @@ void ICACHE_FLASH_ATTR espconn_kill_oldest_pcb(void)
break
;
}
if
(
cpcb
->
state
==
FIN_WAIT_2
||
cpcb
->
state
==
LAST_ACK
){
if
(
cpcb
->
state
==
FIN_WAIT_1
||
cpcb
->
state
==
FIN_WAIT_2
||
cpcb
->
state
==
LAST_ACK
){
num_tcp_fin
++
;
if
(
num_tcp_fin
==
MEMP_NUM_TCP_PCB
)
break
;
...
...
@@ -131,6 +135,8 @@ void ICACHE_FLASH_ATTR espconn_kill_oldest_pcb(void)
if
(
num_tcp_fin
==
MEMP_NUM_TCP_PCB
){
num_tcp_fin
=
0
;
espconn_kill_oldest
();
}
else
if
(
cpcb
==
NULL
){
num_tcp_fin
=
0
;
}
}
}
...
...
@@ -901,7 +907,18 @@ espconn_tcp_client(struct espconn *espconn)
pclient
->
pespconn
=
espconn
;
pclient
->
pespconn
->
state
=
ESPCONN_WAIT
;
pclient
->
pcommon
.
pcb
=
pcb
;
tcp_bind
(
pcb
,
IP_ADDR_ANY
,
pclient
->
pespconn
->
proto
.
tcp
->
local_port
);
tcp_bind
(
pcb
,
IP_ADDR_ANY
,
pclient
->
pespconn
->
proto
.
tcp
->
local_port
);
#if 0
pclient->pcommon.err = tcp_bind(pcb, IP_ADDR_ANY, pclient->pespconn->proto.tcp->local_port);
if (pclient->pcommon.err != ERR_OK){
/*remove the node from the client's active connection list*/
espconn_list_delete(&plink_active, pclient);
memp_free(MEMP_TCP_PCB, pcb);
os_free(pclient);
pclient = NULL;
return ERR_USE;
}
#endif
/*Establish the connection*/
pclient
->
pcommon
.
err
=
tcp_connect
(
pcb
,
&
ipaddr
,
pclient
->
pespconn
->
proto
.
tcp
->
remote_port
,
espconn_client_connect
);
...
...
app/lwip/app/espconn_udp.c
View file @
5d5be356
...
...
@@ -22,9 +22,17 @@
#include "lwip/app/espconn_udp.h"
//#include "net80211/ieee80211_var.h"
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
extern
espconn_msg
*
plink_active
;
extern
uint8
default_interface
;
enum
send_opt
{
ESPCONN_SENDTO
,
ESPCONN_SEND
};
static
void
ICACHE_FLASH_ATTR
espconn_data_sentcb
(
struct
espconn
*
pespconn
)
{
if
(
pespconn
==
NULL
)
{
...
...
@@ -36,7 +44,7 @@ static void ICACHE_FLASH_ATTR espconn_data_sentcb(struct espconn *pespconn)
}
}
static
void
ICACHE_FLASH_ATTR
espconn_data_sent
(
void
*
arg
)
static
void
ICACHE_FLASH_ATTR
espconn_data_sent
(
void
*
arg
,
enum
send_opt
opt
)
{
espconn_msg
*
psent
=
arg
;
...
...
@@ -49,7 +57,11 @@ static void ICACHE_FLASH_ATTR espconn_data_sent(void *arg)
// sys_timeout(10, espconn_data_sentcb, psent->pespconn);
espconn_data_sentcb
(
psent
->
pespconn
);
}
else
{
espconn_udp_sent
(
arg
,
psent
->
pcommon
.
ptrbuf
,
psent
->
pcommon
.
cntr
);
if
(
opt
==
ESPCONN_SEND
){
espconn_udp_sent
(
arg
,
psent
->
pcommon
.
ptrbuf
,
psent
->
pcommon
.
cntr
);
}
else
{
espconn_udp_sendto
(
arg
,
psent
->
pcommon
.
ptrbuf
,
psent
->
pcommon
.
cntr
);
}
}
}
...
...
@@ -82,8 +94,8 @@ espconn_udp_sent(void *arg, uint8 *psent, uint16 length)
return
ESPCONN_ARG
;
}
if
(
TCP_MSS
<
length
)
{
datalen
=
TCP_MSS
;
if
(
1470
<
length
)
{
datalen
=
1470
;
}
else
{
datalen
=
length
;
}
...
...
@@ -145,7 +157,9 @@ espconn_udp_sent(void *arg, uint8 *psent, uint16 length)
pbuf_free
(
p
);
pudp_sent
->
pcommon
.
ptrbuf
=
psent
+
datalen
;
pudp_sent
->
pcommon
.
cntr
=
length
-
datalen
;
espconn_data_sent
(
pudp_sent
);
espconn_data_sent
(
pudp_sent
,
ESPCONN_SEND
);
if
(
err
>
0
)
return
ESPCONN_IF
;
return
err
;
}
else
{
pbuf_free
(
p
);
...
...
@@ -153,6 +167,108 @@ espconn_udp_sent(void *arg, uint8 *psent, uint16 length)
}
}
/******************************************************************************
* FunctionName : espconn_udp_sendto
* Description : sent data for UDP
* Parameters : void *arg -- UDP to send
* uint8* psent -- Data to send
* uint16 length -- Length of data to send
* Returns : return espconn error code.
* - ESPCONN_OK. Successful. No error occured.
* - ESPCONN_MEM. Out of memory.
* - ESPCONN_RTE. Could not find route to destination address.
* - More errors could be returned by lower protocol layers.
*******************************************************************************/
err_t
ICACHE_FLASH_ATTR
espconn_udp_sendto
(
void
*
arg
,
uint8
*
psent
,
uint16
length
)
{
espconn_msg
*
pudp_sent
=
arg
;
struct
udp_pcb
*
upcb
=
pudp_sent
->
pcommon
.
pcb
;
struct
espconn
*
pespconn
=
pudp_sent
->
pespconn
;
struct
pbuf
*
p
,
*
q
,
*
p_temp
;
struct
ip_addr
dst_ip
;
u16_t
dst_port
;
u8_t
*
data
=
NULL
;
u16_t
cnt
=
0
;
u16_t
datalen
=
0
;
u16_t
i
=
0
;
err_t
err
;
LWIP_DEBUGF
(
ESPCONN_UDP_DEBUG
,
(
"espconn_udp_sent %d %d %p
\n
"
,
__LINE__
,
length
,
upcb
));
if
(
pudp_sent
==
NULL
||
upcb
==
NULL
||
psent
==
NULL
||
length
==
0
)
{
return
ESPCONN_ARG
;
}
if
(
1470
<
length
)
{
datalen
=
1470
;
}
else
{
datalen
=
length
;
}
p
=
pbuf_alloc
(
PBUF_TRANSPORT
,
datalen
,
PBUF_RAM
);
LWIP_DEBUGF
(
ESPCONN_UDP_DEBUG
,
(
"espconn_udp_sent %d %p
\n
"
,
__LINE__
,
p
));
if
(
p
!=
NULL
)
{
q
=
p
;
while
(
q
!=
NULL
)
{
data
=
(
u8_t
*
)
q
->
payload
;
LWIP_DEBUGF
(
ESPCONN_UDP_DEBUG
,
(
"espconn_udp_sent %d %p
\n
"
,
__LINE__
,
data
));
for
(
i
=
0
;
i
<
q
->
len
;
i
++
)
{
data
[
i
]
=
((
u8_t
*
)
psent
)[
cnt
++
];
}
q
=
q
->
next
;
}
}
else
{
return
ESPCONN_MEM
;
}
dst_port
=
pespconn
->
proto
.
udp
->
remote_port
;
IP4_ADDR
(
&
dst_ip
,
pespconn
->
proto
.
udp
->
remote_ip
[
0
],
pespconn
->
proto
.
udp
->
remote_ip
[
1
],
pespconn
->
proto
.
udp
->
remote_ip
[
2
],
pespconn
->
proto
.
udp
->
remote_ip
[
3
]);
LWIP_DEBUGF
(
ESPCONN_UDP_DEBUG
,
(
"espconn_udp_sent %d %x %d
\n
"
,
__LINE__
,
upcb
->
remote_ip
,
upcb
->
remote_port
));
struct
netif
*
sta_netif
=
(
struct
netif
*
)
eagle_lwip_getif
(
0x00
);
struct
netif
*
ap_netif
=
(
struct
netif
*
)
eagle_lwip_getif
(
0x01
);
if
(
wifi_get_opmode
()
==
ESPCONN_AP_STA
&&
default_interface
==
ESPCONN_AP_STA
&&
sta_netif
!=
NULL
&&
ap_netif
!=
NULL
)
{
if
(
netif_is_up
(
sta_netif
)
&&
netif_is_up
(
ap_netif
)
&&
\
ip_addr_isbroadcast
(
&
upcb
->
remote_ip
,
sta_netif
)
&&
\
ip_addr_isbroadcast
(
&
upcb
->
remote_ip
,
ap_netif
))
{
p_temp
=
pbuf_alloc
(
PBUF_TRANSPORT
,
datalen
,
PBUF_RAM
);
if
(
pbuf_copy
(
p_temp
,
p
)
!=
ERR_OK
)
{
LWIP_DEBUGF
(
ESPCONN_UDP_DEBUG
,
(
"espconn_udp_sendto: copying to new pbuf failed
\n
"
));
return
ESPCONN_ARG
;
}
netif_set_default
(
sta_netif
);
err
=
udp_sendto
(
upcb
,
p_temp
,
&
dst_ip
,
dst_port
);
pbuf_free
(
p_temp
);
netif_set_default
(
ap_netif
);
}
}
err
=
udp_sendto
(
upcb
,
p
,
&
dst_ip
,
dst_port
);
if
(
p
->
ref
!=
0
)
{
pbuf_free
(
p
);
pudp_sent
->
pcommon
.
ptrbuf
=
psent
+
datalen
;
pudp_sent
->
pcommon
.
cntr
=
length
-
datalen
;
if
(
err
==
ERR_OK
)
espconn_data_sent
(
pudp_sent
,
ESPCONN_SENDTO
);
if
(
err
>
0
)
return
ESPCONN_IF
;
return
err
;
}
else
{
pbuf_free
(
p
);
return
ESPCONN_RTE
;
}
}
/******************************************************************************
* FunctionName : espconn_udp_server_recv
* Description : This callback will be called when receiving a datagram.
...
...
@@ -175,15 +291,10 @@ espconn_udp_recv(void *arg, struct udp_pcb *upcb, struct pbuf *p,
LWIP_DEBUGF
(
ESPCONN_UDP_DEBUG
,
(
"espconn_udp_server_recv %d %p
\n
"
,
__LINE__
,
upcb
));
upcb
->
remote_port
=
port
;
upcb
->
remote_ip
=
*
addr
;
precv
->
pcommon
.
remote_ip
[
0
]
=
ip4_addr1_16
(
&
upcb
->
remote_ip
);
precv
->
pcommon
.
remote_ip
[
1
]
=
ip4_addr2_16
(
&
upcb
->
remote_ip
);
precv
->
pcommon
.
remote_ip
[
2
]
=
ip4_addr3_16
(
&
upcb
->
remote_ip
);
precv
->
pcommon
.
remote_ip
[
3
]
=
ip4_addr4_16
(
&
upcb
->
remote_ip
);
os_memcpy
(
precv
->
pespconn
->
proto
.
udp
->
remote_ip
,
precv
->
pcommon
.
remote_ip
,
4
);
precv
->
pespconn
->
proto
.
udp
->
remote_port
=
port
;
precv
->
pcommon
.
remote_ip
[
0
]
=
ip4_addr1_16
(
addr
);
precv
->
pcommon
.
remote_ip
[
1
]
=
ip4_addr2_16
(
addr
);
precv
->
pcommon
.
remote_ip
[
2
]
=
ip4_addr3_16
(
addr
);
precv
->
pcommon
.
remote_ip
[
3
]
=
ip4_addr4_16
(
addr
);
precv
->
pcommon
.
remote_port
=
port
;
precv
->
pcommon
.
pcb
=
upcb
;
...
...
@@ -196,31 +307,13 @@ espconn_udp_recv(void *arg, struct udp_pcb *upcb, struct pbuf *p,
}
else
{
wifi_get_ip_info
(
0
,
&
ipconfig
);
}
// upcb->local_ip = ipconfig.ip;
precv
->
pespconn
->
proto
.
udp
->
local_ip
[
0
]
=
ip4_addr1_16
(
&
ipconfig
.
ip
);
precv
->
pespconn
->
proto
.
udp
->
local_ip
[
1
]
=
ip4_addr2_16
(
&
ipconfig
.
ip
);
precv
->
pespconn
->
proto
.
udp
->
local_ip
[
2
]
=
ip4_addr3_16
(
&
ipconfig
.
ip
);
precv
->
pespconn
->
proto
.
udp
->
local_ip
[
3
]
=
ip4_addr4_16
(
&
ipconfig
.
ip
);
if
(
p
!=
NULL
)
{
// q = p;
// while (q != NULL) {
// pdata = (u8_t *)os_zalloc(q ->len + 1);
// length = pbuf_copy_partial(q, pdata, q ->len, 0);
//
// LWIP_DEBUGF(ESPCONN_UDP_DEBUG, ("espconn_udp_server_recv %d %x\n", __LINE__, length));
// precv->pcommon.pcb = upcb;
//
// if (length != 0) {
// if (precv->pespconn->recv_callback != NULL) {
// precv->pespconn->recv_callback(precv->pespconn, pdata, length);
// }
// }
//
// q = q->next;
// os_free(pdata);
// }
pdata
=
(
u8_t
*
)
os_zalloc
(
p
->
tot_len
+
1
);
length
=
pbuf_copy_partial
(
p
,
pdata
,
p
->
tot_len
,
0
);
precv
->
pcommon
.
pcb
=
upcb
;
...
...
app/lwip/app/netio.c
View file @
5d5be356
...
...
@@ -35,6 +35,10 @@
#if LWIP_TCP
#include "lwip/tcp.h"
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
/*
* This implements a netio server.
* The client sends a command word (4 bytes) then a data length word (4 bytes).
...
...
@@ -321,7 +325,7 @@ netio_accept(void *arg, struct tcp_pcb *pcb, err_t err)
LWIP_UNUSED_ARG
(
err
);
ns
=
mem_malloc
(
sizeof
(
struct
netio_state
));
ns
=
(
struct
netio_state
*
)
mem_malloc
(
sizeof
(
struct
netio_state
));
if
(
ns
==
NULL
){
return
ERR_MEM
;
...
...
@@ -335,7 +339,7 @@ netio_accept(void *arg, struct tcp_pcb *pcb, err_t err)
#if NETIO_USE_STATIC_BUF == 1
ns
->
buf_ptr
=
netio_buf
;
#else
ns
->
buf_ptr
=
mem_malloc
(
NETIO_BUF_SIZE
);
ns
->
buf_ptr
=
(
u8_t
*
)
mem_malloc
(
NETIO_BUF_SIZE
);
if
(
ns
->
buf_ptr
==
NULL
){
mem_free
(
ns
);
...
...
app/lwip/app/ping.c
View file @
5d5be356
...
...
@@ -63,6 +63,10 @@
#include "lwip/inet.h"
#endif
/* PING_USE_SOCKETS */
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
/* ping variables */
static
u16_t
ping_seq_num
=
0
;
static
u32_t
ping_time
;
...
...
app/lwip/core/dhcp.c
View file @
5d5be356
...
...
@@ -84,6 +84,10 @@
#include <string.h>
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
/** Default for DHCP_GLOBAL_XID is 0xABCD0000
* This can be changed by defining DHCP_GLOBAL_XID and DHCP_GLOBAL_XID_HEADER, e.g.
* #define DHCP_GLOBAL_XID_HEADER "stdlib.h"
...
...
@@ -377,6 +381,15 @@ dhcp_fine_tmr()
while
(
netif
!=
NULL
)
{
/* only act on DHCP configured interfaces */
if
(
netif
->
dhcp
!=
NULL
)
{
/*add DHCP retries processing by LiuHan*/
if
(
DHCP_MAXRTX
!=
0
)
{
if
(
netif
->
dhcp
->
tries
>=
DHCP_MAXRTX
){
os_printf
(
"DHCP timeout
\n
"
);
if
(
netif
->
dhcp_event
!=
NULL
)
netif
->
dhcp_event
();
break
;
}
}
/* timer is active (non zero), and is about to trigger now */
if
(
netif
->
dhcp
->
request_timeout
>
1
)
{
netif
->
dhcp
->
request_timeout
--
;
...
...
@@ -392,6 +405,7 @@ dhcp_fine_tmr()
/* proceed to next network interface */
netif
=
netif
->
next
;
}
}
/**
...
...
app/lwip/core/dns.c
View file @
5d5be356
...
...
@@ -83,6 +83,10 @@
#include <string.h>
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
/** DNS server IP address */
#ifndef DNS_SERVER_ADDRESS
#define DNS_SERVER_ADDRESS(ipaddr) (ip4_addr_set_u32(ipaddr, 0xDEDE43D0))
/* resolver1.opendns.com(208.67.222.222) */
...
...
app/lwip/core/init.c
View file @
5d5be356
...
...
@@ -261,7 +261,7 @@ lwip_init(void)
{
MEMP_NUM_TCP_PCB
=
5
;
TCP_WND
=
(
4
*
TCP_MSS
);
TCP_MAXRTX
=
3
;
TCP_MAXRTX
=
12
;
TCP_SYNMAXRTX
=
6
;
/* Sanity check user-configurable values */
...
...
app/lwip/core/ipv4/igmp.c
View file @
5d5be356
...
...
@@ -95,6 +95,10 @@ Steve Reynolds
#include "string.h"
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
/*
* IGMP constants
*/
...
...
app/lwip/core/mdns.c
View file @
5d5be356
...
...
@@ -49,6 +49,11 @@
#include "osapi.h"
#include "os_type.h"
#include "user_interface.h"
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
/** DNS server IP address */
#ifndef DNS_MULTICAST_ADDRESS
#define DNS_MULTICAST_ADDRESS ipaddr_addr("224.0.0.251")
/* resolver1.opendns.com */
...
...
@@ -971,11 +976,21 @@ mdns_get_servername(void) {
void
ICACHE_FLASH_ATTR
mdns_server_unregister
(
void
)
{
struct
ip_addr
ap_host_addr
;
struct
ip_info
ipconfig
;
if
(
register_flag
==
1
){
if
(
igmp_leavegroup
(
&
host_addr
,
&
multicast_addr
)
!=
ERR_OK
)
{
os_printf
(
"udp_leave_multigrup failed!
\n
"
);
os_printf
(
"
sta
udp_leave_multigrup failed!
\n
"
);
return
;
};
if
(
wifi_get_opmode
()
==
0x03
||
wifi_get_opmode
()
==
0x02
)
{
wifi_get_ip_info
(
SOFTAP_IF
,
&
ipconfig
);
ap_host_addr
.
addr
=
ipconfig
.
ip
.
addr
;
if
(
igmp_leavegroup
(
&
ap_host_addr
,
&
multicast_addr
)
!=
ERR_OK
)
{
os_printf
(
"ap udp_join_multigrup failed!
\n
"
);
return
;
};
}
register_flag
=
0
;
}
}
...
...
@@ -1013,6 +1028,8 @@ void ICACHE_FLASH_ATTR
mdns_init
(
struct
mdns_info
*
info
)
{
/* initialize default DNS server address */
multicast_addr
.
addr
=
DNS_MULTICAST_ADDRESS
;
struct
ip_addr
ap_host_addr
;
struct
ip_info
ipconfig
;
if
(
info
->
ipAddr
==
0
)
{
os_printf
(
"mdns ip error!
\n
"
);
return
;
...
...
@@ -1040,10 +1057,20 @@ mdns_init(struct mdns_info *info) {
if
(
mdns_pcb
!=
NULL
)
{
/* join to the multicast address 224.0.0.251 */
if
(
igmp_joingroup
(
&
host_addr
,
&
multicast_addr
)
!=
ERR_OK
)
{
os_printf
(
"udp_join_multigrup failed!
\n
"
);
return
;
};
if
(
wifi_get_opmode
()
==
0x03
||
wifi_get_opmode
()
==
0x01
)
{
if
(
igmp_joingroup
(
&
host_addr
,
&
multicast_addr
)
!=
ERR_OK
)
{
os_printf
(
"sta udp_join_multigrup failed!
\n
"
);
return
;
};
}
if
(
wifi_get_opmode
()
==
0x03
||
wifi_get_opmode
()
==
0x02
)
{
wifi_get_ip_info
(
SOFTAP_IF
,
&
ipconfig
);
ap_host_addr
.
addr
=
ipconfig
.
ip
.
addr
;
if
(
igmp_joingroup
(
&
ap_host_addr
,
&
multicast_addr
)
!=
ERR_OK
)
{
os_printf
(
"ap udp_join_multigrup failed!
\n
"
);
return
;
};
}
register_flag
=
1
;
/* join to any IP address at the port 5353 */
if
(
udp_bind
(
mdns_pcb
,
IP_ADDR_ANY
,
DNS_MDNS_PORT
)
!=
ERR_OK
)
{
...
...
app/lwip/core/pbuf.c
View file @
5d5be356
...
...
@@ -79,6 +79,10 @@
#include <string.h>
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
#ifdef EBUF_LWIP
#define EP_OFFSET 36
#else
...
...
@@ -90,6 +94,45 @@
aligned there. Therefore, PBUF_POOL_BUFSIZE_ALIGNED can be used here. */
#define PBUF_POOL_BUFSIZE_ALIGNED LWIP_MEM_ALIGN_SIZE(PBUF_POOL_BUFSIZE)
/**
* Attempt to reclaim some memory from queued out-of-sequence TCP segments
* if we run out of pool pbufs. It's better to give priority to new packets
* if we're running out.
*/
#if TCP_QUEUE_OOSEQ
void
ICACHE_FLASH_ATTR
pbuf_free_ooseq_new
(
void
*
arg
)
{
struct
tcp_pcb
*
pcb
;
struct
tcp_seg
*
head
=
NULL
;
struct
tcp_seg
*
seg1
=
NULL
;
struct
tcp_seg
*
seg2
=
NULL
;
for
(
pcb
=
tcp_active_pcbs
;
NULL
!=
pcb
;
pcb
=
pcb
->
next
)
{
head
=
pcb
->
ooseq
;
seg1
=
head
;
if
(
head
!=
NULL
)
{
if
(
seg1
->
next
==
NULL
){
head
=
head
->
next
;
tcp_seg_free
(
seg1
);
pcb
->
ooseq
=
head
;
}
else
{
while
(
seg1
!=
NULL
){
seg2
=
seg1
;
seg2
=
seg2
->
next
;
if
(
seg2
->
next
==
NULL
){
seg1
->
next
=
seg2
->
next
;
tcp_seg_free
(
seg2
);
break
;
}
seg1
=
seg1
->
next
;
}
pcb
->
ooseq
=
head
;
}
}
}
}
#endif
#if !LWIP_TCP || !TCP_QUEUE_OOSEQ || NO_SYS
#define PBUF_POOL_IS_EMPTY()
#else
/* !LWIP_TCP || !TCP_QUEUE_OOSEQ || NO_SYS */
...
...
app/lwip/core/raw.c
View file @
5d5be356
...
...
@@ -52,6 +52,10 @@
#include <string.h>
#ifdef MEMLEAK_DEBUG
static
const
char
mem_debug_file
[]
ICACHE_RODATA_ATTR
=
__FILE__
;
#endif
/** The list of RAW PCBs */
static
struct
raw_pcb
*
raw_pcbs
;
...
...
Prev
1
2
Next
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment