ArduinoOTA retrieves incorrect IP for TCP transfer
- Dominant language
- C++
- Stars
- 16.7k
- Forks
- 13.1k
- PR merge metrics
- No merged PRs in 30d
Description
### Basic Infos
- [x] This issue complies with the [issue POLICY doc](https://github.com/esp8266/Arduino/blob/master/POLICY.md).
- [x] I have read the documentation at [readthedocs](https://arduino-esp8266.readthedocs.io/en/latest) and the issue is not addressed there.
- [x] I have tested that the issue is present in current master branch (aka latest git).
- [x] I have searched the issue tracker for a similar issue.
- [x] If there is a stack dump, I have decoded it.
- [x] I have filled out all fields below.
#### Platform
- Hardware: ESP-8266EX
- Core Version: 3.30002.0
- Development Env: Platformio
- Operating System: Windows
### Settings in IDE
- Module: Wemos D1 mini
### Problem Description
When trying to use OTA updates via internet [this call](https://github.com/esp8266/Arduino/blob/3027acaf11db93e877fca943eb815216d0507744/libraries/ArduinoOTA/ArduinoOTA.cpp#L178) retrieves a wrong, local IP.
The UDP communication works just fine but because of the wrong IP the TCP connection (pushing the actual firmware/payload) fails:
```
10:57:53 [INFO]: Sending invitation to: x.x.x.x
10:58:03 [ERROR]: No Answer
```
Network setup it is: Internet -> Router A -> Router B (in Acces Point mode) -> ESP. The call above yields the local IP address of Router A instead of the correct remote one.
I thought I could use the `--host_ip` argument to set the correct IP but it tries to bind the socket to it which fails. And the cpp side does not use this supplied address, it relies on the remote address of the UDP connection.
So I've added some code to `espota.py` to NOT bind to the to `localAddr` but to [`INADDR_ANY`](https://docs.python.org/3/library/socket.html#socket-families)
```python
server_address = ("", localPort)
```
and append the correct IP localAddr with the message:
```python
message = '%d %d %d %s\n%s\n' % (command, localPort, content_size, file_md5, localAddr)
```
and to read it on the cpp side:
```cpp
String ipstring = readStringUntil('\n');
_ota_ip2.fromString(ipstring);
```
and then I use this for the TCP connection:
```cpp
if (!client.connect(_ota_ip2, _ota_port)) {
```
With this now the OTA update works when explicitly setting the IP, e.g. like this:
```
python espota.py --ip=ESP_IP --host_ip=HOST_IP --host_port=HOST_PORT --file=firmware.bin --debug --progress
```
I wonder if this is due to the network setup (two routers, secondary one set to Access Point mode) or why the address resolution does not work even though communication works just fine.
Contributor guide
No contributing guide indexed for this repository
Assessment
This issue has not been assessed yet.