mirror of
https://github.com/espressif/ESP8266_RTOS_SDK.git
synced 2025-10-21 15:32:02 +08:00
feat(lwip): LWIP and tcpip adapter using esp_socket to read/write low-level data
This commit is contained in:
@@ -18,7 +18,7 @@
|
|||||||
#include "esp_libc.h"
|
#include "esp_libc.h"
|
||||||
#include "esp_wifi.h"
|
#include "esp_wifi.h"
|
||||||
#include "tcpip_adapter.h"
|
#include "tcpip_adapter.h"
|
||||||
|
#include "esp_socket.h"
|
||||||
|
|
||||||
int8_t ieee80211_output_pbuf(uint8_t fd, uint8_t* dataptr, uint16_t datalen);
|
int8_t ieee80211_output_pbuf(uint8_t fd, uint8_t* dataptr, uint16_t datalen);
|
||||||
int8_t wifi_get_netif(uint8_t fd);
|
int8_t wifi_get_netif(uint8_t fd);
|
||||||
@@ -54,6 +54,22 @@ static void low_level_init(struct netif* netif)
|
|||||||
/* Do whatever else is needed to initialize interface. */
|
/* Do whatever else is needed to initialize interface. */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* @brief LWIP low-level AI/O sending callback function, it is to free pbuf
|
||||||
|
*
|
||||||
|
* @param aio AI/O control block pointer
|
||||||
|
*
|
||||||
|
* @return 0 meaning successs
|
||||||
|
*/
|
||||||
|
static int low_level_send_cb(esp_aio_t *aio)
|
||||||
|
{
|
||||||
|
struct pbuf *pbuf = aio->arg;
|
||||||
|
|
||||||
|
pbuf_free(pbuf);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This function should do the actual transmission of the packet. The packet is
|
* This function should do the actual transmission of the packet. The packet is
|
||||||
* contained in the pbuf that is passed to the function. This pbuf
|
* contained in the pbuf that is passed to the function. This pbuf
|
||||||
@@ -72,6 +88,7 @@ static void low_level_init(struct netif* netif)
|
|||||||
|
|
||||||
static int8_t low_level_output(struct netif* netif, struct pbuf* p)
|
static int8_t low_level_output(struct netif* netif, struct pbuf* p)
|
||||||
{
|
{
|
||||||
|
esp_aio_t aio;
|
||||||
int8_t err = ERR_OK;
|
int8_t err = ERR_OK;
|
||||||
|
|
||||||
if (netif == NULL) {
|
if (netif == NULL) {
|
||||||
@@ -83,20 +100,20 @@ static int8_t low_level_output(struct netif* netif, struct pbuf* p)
|
|||||||
pbuf_header(p, -ETH_PAD_SIZE); /* drop the padding word */
|
pbuf_header(p, -ETH_PAD_SIZE); /* drop the padding word */
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
uint8_t* outputbuf = (uint8_t*)os_malloc(p->len + 36);
|
pbuf_ref(p);
|
||||||
if (outputbuf == NULL) {
|
|
||||||
TCPIP_ATAPTER_LOG("ERROR no memory\n");
|
|
||||||
return ERR_MEM;
|
|
||||||
}
|
|
||||||
|
|
||||||
outputbuf += 36;
|
aio.fd = (int)netif->state;
|
||||||
memcpy(outputbuf, p->payload, p->len);
|
aio.pbuf = p->payload;
|
||||||
|
aio.len = p->len;
|
||||||
|
aio.cb = low_level_send_cb;
|
||||||
|
aio.arg = p;
|
||||||
|
aio.ret = 0;
|
||||||
|
|
||||||
if (netif == esp_netif[TCPIP_ADAPTER_IF_STA]) {
|
/*
|
||||||
err = ieee80211_output_pbuf(TCPIP_ADAPTER_IF_STA, outputbuf, p->len);
|
* we use "SOCK_RAW" to create socket, so all input/output datas include full ethernet
|
||||||
} else {
|
* header, meaning we should not pass target low-level address here.
|
||||||
err = ieee80211_output_pbuf(TCPIP_ADAPTER_IF_AP, outputbuf, p->len);
|
*/
|
||||||
}
|
err = esp_aio_sendto(&aio, NULL, 0);
|
||||||
|
|
||||||
if (err == ERR_MEM) {
|
if (err == ERR_MEM) {
|
||||||
err = ERR_OK;
|
err = ERR_OK;
|
||||||
|
@@ -21,6 +21,16 @@
|
|||||||
#include "esp_misc.h"
|
#include "esp_misc.h"
|
||||||
#include "tcpip_adapter.h"
|
#include "tcpip_adapter.h"
|
||||||
#include "dhcpserver/dhcpserver.h"
|
#include "dhcpserver/dhcpserver.h"
|
||||||
|
#include "net/sockio.h"
|
||||||
|
#include "esp_socket.h"
|
||||||
|
|
||||||
|
struct tcpip_adapter_pbuf {
|
||||||
|
struct pbuf_custom pbuf;
|
||||||
|
|
||||||
|
void *base;
|
||||||
|
|
||||||
|
struct netif *netif;
|
||||||
|
};
|
||||||
|
|
||||||
/* Avoid warning. No header file has include these function */
|
/* Avoid warning. No header file has include these function */
|
||||||
err_t ethernetif_init(struct netif* netif);
|
err_t ethernetif_init(struct netif* netif);
|
||||||
@@ -86,6 +96,90 @@ static void tcpip_adapter_station_dhcp_start()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* @brief LWIP custom pbuf callback function, it is to free custom pbuf
|
||||||
|
*
|
||||||
|
* @param p LWIP pbuf pointer
|
||||||
|
*
|
||||||
|
* @return none
|
||||||
|
*/
|
||||||
|
static void tcpip_adapter_free_pbuf(struct pbuf *p)
|
||||||
|
{
|
||||||
|
struct tcpip_adapter_pbuf *pa = (struct tcpip_adapter_pbuf *)p;
|
||||||
|
int s = (int)pa->netif->state;
|
||||||
|
|
||||||
|
esp_free_pbuf(s, pa->base);
|
||||||
|
os_free(pa);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* @brief TCPIP adapter AI/O recieve callback function, it is to recieve input data
|
||||||
|
* and pass it to LWIP core
|
||||||
|
*
|
||||||
|
* @param aio AI/O control block pointer
|
||||||
|
*
|
||||||
|
* @return 0 if success or others if failed
|
||||||
|
*/
|
||||||
|
static int tcpip_adapter_recv_cb(struct esp_aio *aio)
|
||||||
|
{
|
||||||
|
struct pbuf *pbuf = NULL;
|
||||||
|
struct tcpip_adapter_pbuf *p;
|
||||||
|
struct netif *netif = (struct netif *)aio->arg;
|
||||||
|
|
||||||
|
extern void ethernetif_input(struct netif *netif, struct pbuf *p);
|
||||||
|
|
||||||
|
p = os_malloc(sizeof(struct tcpip_adapter_pbuf));
|
||||||
|
if (!p)
|
||||||
|
return -ENOMEM;
|
||||||
|
p->pbuf.custom_free_function = tcpip_adapter_free_pbuf;
|
||||||
|
p->base = (void *)aio->pbuf;
|
||||||
|
p->netif = netif;
|
||||||
|
|
||||||
|
// PBUF_RAW means payload = (char *)aio->pbuf + offset(=0)
|
||||||
|
pbuf = pbuf_alloced_custom(PBUF_RAW, aio->len, PBUF_REF, &p->pbuf, (void *)aio->pbuf, aio->len);
|
||||||
|
if (!pbuf)
|
||||||
|
return -ENOMEM;
|
||||||
|
|
||||||
|
ethernetif_input(netif, pbuf);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* @brief create a "esp_socket" and bind it to target net card
|
||||||
|
*
|
||||||
|
* @param name net card name pointer
|
||||||
|
* @param netif LWIP net interface pointer
|
||||||
|
*
|
||||||
|
* @return 0 if success or others if failed
|
||||||
|
*/
|
||||||
|
static int tcpip_adapter_bind_netcard(const char *name, struct netif *netif)
|
||||||
|
{
|
||||||
|
int s, ret;
|
||||||
|
|
||||||
|
s = esp_socket(AF_PACKET, SOCK_RAW, ETH_P_ALL);
|
||||||
|
if (s < 0) {
|
||||||
|
TCPIP_ATAPTER_LOG("create socket of (AF_PACKET, SOCK_RAW, ETH_P_ALL) error\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = esp_ioctl(s, SIOCGIFINDEX, name);
|
||||||
|
if (ret) {
|
||||||
|
TCPIP_ATAPTER_LOG("bind socket %d to netcard %s error\n", s, name);
|
||||||
|
esp_close(s);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = esp_aio_event(s, ESP_SOCKET_RECV_EVENT, tcpip_adapter_recv_cb, netif);
|
||||||
|
if (ret) {
|
||||||
|
TCPIP_ATAPTER_LOG("socket %d register receive callback function %p error\n", s, tcpip_adapter_recv_cb);
|
||||||
|
esp_close(s);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
|
||||||
void tcpip_adapter_start(uint8_t netif_index, bool authed)
|
void tcpip_adapter_start(uint8_t netif_index, bool authed)
|
||||||
{
|
{
|
||||||
if (!TCPIP_ADAPTER_IF_VALID(netif_index)) {
|
if (!TCPIP_ADAPTER_IF_VALID(netif_index)) {
|
||||||
@@ -98,10 +192,20 @@ void tcpip_adapter_start(uint8_t netif_index, bool authed)
|
|||||||
if (netif_index == TCPIP_ADAPTER_IF_STA) {
|
if (netif_index == TCPIP_ADAPTER_IF_STA) {
|
||||||
if (authed == 0) {
|
if (authed == 0) {
|
||||||
if (esp_netif[netif_index] == NULL) {
|
if (esp_netif[netif_index] == NULL) {
|
||||||
|
int s;
|
||||||
|
const char *netcard_name = "sta0";
|
||||||
|
|
||||||
esp_netif[netif_index] = (struct netif*)os_zalloc(sizeof(*esp_netif[netif_index]));
|
esp_netif[netif_index] = (struct netif*)os_zalloc(sizeof(*esp_netif[netif_index]));
|
||||||
TCPIP_ATAPTER_LOG("Malloc netif:%d\n", netif_index);
|
TCPIP_ATAPTER_LOG("Malloc netif:%d\n", netif_index);
|
||||||
TCPIP_ATAPTER_LOG("Add netif:%d\n", netif_index);
|
TCPIP_ATAPTER_LOG("Add netif:%d\n", netif_index);
|
||||||
netif_add(esp_netif[netif_index], NULL, NULL, NULL, NULL, ethernetif_init, tcpip_input);
|
|
||||||
|
s = tcpip_adapter_bind_netcard(netcard_name, esp_netif[netif_index]);
|
||||||
|
if (s < 0) {
|
||||||
|
TCPIP_ATAPTER_LOG("TCPIP adapter bind net card %s error\n", netcard_name);
|
||||||
|
return ;
|
||||||
|
}
|
||||||
|
|
||||||
|
netif_add(esp_netif[netif_index], NULL, NULL, NULL, (void *)s, ethernetif_init, tcpip_input);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if ((esp_netif[netif_index]->flags & NETIF_FLAG_DHCP) == 0) {
|
if ((esp_netif[netif_index]->flags & NETIF_FLAG_DHCP) == 0) {
|
||||||
@@ -131,10 +235,20 @@ void tcpip_adapter_start(uint8_t netif_index, bool authed)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (esp_netif[netif_index] == NULL) {
|
if (esp_netif[netif_index] == NULL) {
|
||||||
|
int s;
|
||||||
|
const char *netcard_name = "ap0";
|
||||||
|
|
||||||
TCPIP_ATAPTER_LOG("Malloc netif:%d\n", netif_index);
|
TCPIP_ATAPTER_LOG("Malloc netif:%d\n", netif_index);
|
||||||
esp_netif[netif_index] = (struct netif*)os_zalloc(sizeof(*esp_netif[netif_index]));
|
esp_netif[netif_index] = (struct netif*)os_zalloc(sizeof(*esp_netif[netif_index]));
|
||||||
|
|
||||||
|
s = tcpip_adapter_bind_netcard(netcard_name, esp_netif[netif_index]);
|
||||||
|
if (s < 0) {
|
||||||
|
TCPIP_ATAPTER_LOG("TCPIP adapter bind net card %s error\n", netcard_name);
|
||||||
|
return ;
|
||||||
|
}
|
||||||
|
|
||||||
netif_add(esp_netif[netif_index], &esp_ip[TCPIP_ADAPTER_IF_AP].ip,
|
netif_add(esp_netif[netif_index], &esp_ip[TCPIP_ADAPTER_IF_AP].ip,
|
||||||
&esp_ip[TCPIP_ADAPTER_IF_AP].netmask, &esp_ip[TCPIP_ADAPTER_IF_AP].gw, NULL, ethernetif_init, tcpip_input);
|
&esp_ip[TCPIP_ADAPTER_IF_AP].netmask, &esp_ip[TCPIP_ADAPTER_IF_AP].gw, (void *)s, ethernetif_init, tcpip_input);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (dhcps_flag) {
|
if (dhcps_flag) {
|
||||||
|
Reference in New Issue
Block a user