在 WIFI_AP_STA 中设置 AP 和 STA 之间的路由
Setup Routing between AP and STA in WIFI_AP_STA
我正在尝试在我的 nodeMCU 中的 ESP8266 的 AP 和 STA 之间设置路由或某些接口。我正在尝试在 NAT 模式下设置 Wifi 中继器。这是我写的代码,
#include <ESP8266WiFi.h>
#include <ESP8266mDNS.h>
const char* ssid = "********";
const char* password = "********";
/* Settings for SSID to be forwarded*/
IPAddress staticIP(192,168,1,113);
IPAddress gateway(192,168,1,1);
IPAddress subnet(255,255,255,0);
MDNSResponder mdns;
WiFiServer server(80);
int i=0;
void setup(void)
{
Serial.begin(115200);
Serial.println();
WiFi.mode(WIFI_AP_STA);
/*Station Mode Configuration*/
Serial.printf("Connecting to %s\n", ssid);
WiFi.begin(ssid, password);
WiFi.config(staticIP, gateway, subnet);
while (WiFi.status() != WL_CONNECTED)
{
delay(500);
Serial.print(".");
}
Serial.println();
Serial.print("Connected, IP address: ");
Serial.println(WiFi.localIP());
Serial.print("MAC Address: ");
Serial.println(WiFi.macAddress());
Serial.print("Gateway IP: ");
Serial.println(WiFi.gatewayIP());
Serial.print("DNS Server: ");
Serial.println(WiFi.dnsIP());
/*SoftAP configuration */
//Serial.print("Setting soft-AP configuration ... ");
//Serial.println(WiFi.softAPConfig(local_IP, gateway, subnet) ? "Ready" : "Failed!");
Serial.println();
Serial.println("!!!!!!!!!!!!!!!!!!!!!");
Serial.println();
Serial.print("Setting soft-AP ... ");
Serial.println(WiFi.softAP("ESPsoftAP_01") ? "Ready" : "Failed!");
Serial.print("Soft-AP IP address = ");
Serial.println(WiFi.softAPIP());
}
void loop()
{
int j = WiFi.softAPgetStationNum();
if(j != i)
{
Serial.printf("Stations connected to soft-AP = %d\n", WiFi.softAPgetStationNum());
i = j;
}
/* Checks for the requests from the ESP clients and prints them on the serial monitor. */
mdns.update(); // Check for any mDNS queries and send responses
WiFiClient client = server.available(); // Check if a client has connected
if (client)
{
Serial.println("");
Serial.println("New client");
Serial.println("Checkpoint 0");
// Wait for data from client to become available
while (client.connected() && !client.available())
{
delay(1);
}
Serial.println("Checkpoint 1");
// Read the first line of HTTP request
String req = client.readStringUntil('\r');
Serial.println(req);
}
}
我可以将 ESP 连接到我的 Wifi,也可以将一些电台连接到 ESP。但不幸的是,我没有运气在 ESP 的客户端和 Internet 之间传输请求和响应。
问题: 在上一节中,checkpoint 0
未被打印,这意味着客户端返回 false。但是根据这部分
int j = WiFi.softAPgetStationNum();
if(j != i)
{
Serial.printf("Stations connected to soft-AP = %d\n", WiFi.softAPgetStationNum());
i = j;
}
客户端正在连接。为什么会这样?
输出:
Connecting to ********
.......
Connected, IP address: 192.168.1.113
MAC Address: **:**:**:**:**:**
Gateway IP: 192.168.1.1
DNS Server: 0.0.0.0
!!!!!!!!!!!!!!!!!!!!!
Setting soft-AP ... Ready
Soft-AP IP address = 192.168.4.1
Stations connected to soft-AP = 1
这是个好主意,但 ESP8266 上的网络堆栈无法路由数据包或执行 NAT。
您编写的代码试图充当代理,而不是路由器。
路由器在网络接口之间复制 IP 数据包 - 它能够路由所有 运行 通过 IP 的协议。 NAT 重写一些数据包的 IP 地址,以隐藏被 NAT 的网络。 ESP8266 网络堆栈无法执行此操作。
您的代码正在端口 80(Web 端口)上创建 TCP-based 服务器。它只能将 TCP 数据包代理到端口 80——它不能代理名称服务器请求或任何其他协议。
代理比您想象的要复杂得多。 HTTP 需要添加代理 headers。代理加密连接也更复杂,需要监听端口 443。客户端必须配置为知道连接到代理服务器,代理服务器必须能够检查原始请求,以便知道连接到哪里。
ESP8266 网络堆栈只能同时进行 5 个 TCP 连接。如果原始连接来自 Web 浏览器,则 Web 浏览器通常一次打开 5 个以上的连接,因为网页经常从许多位置拉入 CSS、Javascript 和图像。请记住,每个代理连接都需要一个传出连接,因此即使代理 2 个 TCP 连接也会用完 5 个可用连接中的 4 个。 5 个同时连接的限制意味着 ESP8266 将无法成功充当网络浏览器的代理。
Wifi客户端和TCP客户端是有区别的。我希望 Arduino 和 ESP8266 SDK 在此处的命名更加清晰。 WiFiServer
实际上与 WiFi 无关 - 它是一个 TCP 服务器。
你在这里看不到连接 "Checkpoint 0" 因为无论你试图 route/proxy 是什么都不知道打开到你的 ESP8266 的 TCP 连接(假设它甚至在尝试完全使用 TCP)。
这是一个不错的尝试,但不幸的是 ESP8266 不适合这种用途。
我正在尝试在我的 nodeMCU 中的 ESP8266 的 AP 和 STA 之间设置路由或某些接口。我正在尝试在 NAT 模式下设置 Wifi 中继器。这是我写的代码,
#include <ESP8266WiFi.h>
#include <ESP8266mDNS.h>
const char* ssid = "********";
const char* password = "********";
/* Settings for SSID to be forwarded*/
IPAddress staticIP(192,168,1,113);
IPAddress gateway(192,168,1,1);
IPAddress subnet(255,255,255,0);
MDNSResponder mdns;
WiFiServer server(80);
int i=0;
void setup(void)
{
Serial.begin(115200);
Serial.println();
WiFi.mode(WIFI_AP_STA);
/*Station Mode Configuration*/
Serial.printf("Connecting to %s\n", ssid);
WiFi.begin(ssid, password);
WiFi.config(staticIP, gateway, subnet);
while (WiFi.status() != WL_CONNECTED)
{
delay(500);
Serial.print(".");
}
Serial.println();
Serial.print("Connected, IP address: ");
Serial.println(WiFi.localIP());
Serial.print("MAC Address: ");
Serial.println(WiFi.macAddress());
Serial.print("Gateway IP: ");
Serial.println(WiFi.gatewayIP());
Serial.print("DNS Server: ");
Serial.println(WiFi.dnsIP());
/*SoftAP configuration */
//Serial.print("Setting soft-AP configuration ... ");
//Serial.println(WiFi.softAPConfig(local_IP, gateway, subnet) ? "Ready" : "Failed!");
Serial.println();
Serial.println("!!!!!!!!!!!!!!!!!!!!!");
Serial.println();
Serial.print("Setting soft-AP ... ");
Serial.println(WiFi.softAP("ESPsoftAP_01") ? "Ready" : "Failed!");
Serial.print("Soft-AP IP address = ");
Serial.println(WiFi.softAPIP());
}
void loop()
{
int j = WiFi.softAPgetStationNum();
if(j != i)
{
Serial.printf("Stations connected to soft-AP = %d\n", WiFi.softAPgetStationNum());
i = j;
}
/* Checks for the requests from the ESP clients and prints them on the serial monitor. */
mdns.update(); // Check for any mDNS queries and send responses
WiFiClient client = server.available(); // Check if a client has connected
if (client)
{
Serial.println("");
Serial.println("New client");
Serial.println("Checkpoint 0");
// Wait for data from client to become available
while (client.connected() && !client.available())
{
delay(1);
}
Serial.println("Checkpoint 1");
// Read the first line of HTTP request
String req = client.readStringUntil('\r');
Serial.println(req);
}
}
我可以将 ESP 连接到我的 Wifi,也可以将一些电台连接到 ESP。但不幸的是,我没有运气在 ESP 的客户端和 Internet 之间传输请求和响应。
问题: 在上一节中,checkpoint 0
未被打印,这意味着客户端返回 false。但是根据这部分
int j = WiFi.softAPgetStationNum();
if(j != i)
{
Serial.printf("Stations connected to soft-AP = %d\n", WiFi.softAPgetStationNum());
i = j;
}
客户端正在连接。为什么会这样?
输出:
Connecting to ********
.......
Connected, IP address: 192.168.1.113
MAC Address: **:**:**:**:**:**
Gateway IP: 192.168.1.1
DNS Server: 0.0.0.0
!!!!!!!!!!!!!!!!!!!!!
Setting soft-AP ... Ready
Soft-AP IP address = 192.168.4.1
Stations connected to soft-AP = 1
这是个好主意,但 ESP8266 上的网络堆栈无法路由数据包或执行 NAT。
您编写的代码试图充当代理,而不是路由器。
路由器在网络接口之间复制 IP 数据包 - 它能够路由所有 运行 通过 IP 的协议。 NAT 重写一些数据包的 IP 地址,以隐藏被 NAT 的网络。 ESP8266 网络堆栈无法执行此操作。
您的代码正在端口 80(Web 端口)上创建 TCP-based 服务器。它只能将 TCP 数据包代理到端口 80——它不能代理名称服务器请求或任何其他协议。
代理比您想象的要复杂得多。 HTTP 需要添加代理 headers。代理加密连接也更复杂,需要监听端口 443。客户端必须配置为知道连接到代理服务器,代理服务器必须能够检查原始请求,以便知道连接到哪里。
ESP8266 网络堆栈只能同时进行 5 个 TCP 连接。如果原始连接来自 Web 浏览器,则 Web 浏览器通常一次打开 5 个以上的连接,因为网页经常从许多位置拉入 CSS、Javascript 和图像。请记住,每个代理连接都需要一个传出连接,因此即使代理 2 个 TCP 连接也会用完 5 个可用连接中的 4 个。 5 个同时连接的限制意味着 ESP8266 将无法成功充当网络浏览器的代理。
Wifi客户端和TCP客户端是有区别的。我希望 Arduino 和 ESP8266 SDK 在此处的命名更加清晰。 WiFiServer
实际上与 WiFi 无关 - 它是一个 TCP 服务器。
你在这里看不到连接 "Checkpoint 0" 因为无论你试图 route/proxy 是什么都不知道打开到你的 ESP8266 的 TCP 连接(假设它甚至在尝试完全使用 TCP)。
这是一个不错的尝试,但不幸的是 ESP8266 不适合这种用途。