yahboom
HomeLearn
Solution
Blog
Online Store
About Us
EN/中文
ESP32 Core Board📖
1. ESP32 Introduction
  • 1. ESP32S3 Overview
  • 2. Environment Setup Introduction
  • 3. Dev Board Introduction
2. ESP-IDF Development Tutorial
1. Before Development
  • 1. Environment Setup (Windows)
  • 2. Environment Setup (Linux)
  • 3. Build and Flash
2. Basic Peripherals
  • 1. LED Control
  • 2. Button Detection
  • 3. Peripheral Interrupts
  • 4. ESP_TIMER
  • 5. GPTIMER
  • 6. Watchdog Timer
  • 7. DMA
  • 8. ADC
  • 9. PWM Breathing LED
  • 10. RGB LED Effects
3. Serial Communication and Storage System
  • 1. Serial UART Communication Experiment
  • 2. I2C_OLED Display Experiment
  • 3. SPI Bus Communication Experiment
  • 4. PSRAM External Memory Experiment
  • 5. Flash Read and Write Experiment
  • 6. USB Emulated Mass Storage Experiment
4. FreeRTOS operating system
  • 1.FreeRTOS Core Concepts Theory
  • 2.Task Creation and Management
  • 3.Queue
  • 4.Binary Semaphore
  • 5.Mutex
  • 6.Event Groups
  • 7.Software Timer
  • 8.Task Scheduler
  • 9.Low Power Mode
  • 10.Deadlock
  • 11.Priority Inversion
5. Network Protocols and Wireless Communication
  • 1. WIFI Network Basics
  • 2. WIFI STA Mode
  • 3. WIFI AP Mode
  • 4. UDP Client Experiment
  • 5. UDP Server Experiment
  • 6. TCP Client Experiment
  • 7. TCP Server Experiment
  • 8. Socket Programming Basics
  • 9. HTTP Client Experiment
  • 10. HTTP Server Experiment
  • 11. MQTT IoT Communication Protocol
  • 12. WIFI OTA Upgrade
  • 13. Bluetooth Fundamentals
  • 14. Bluetooth Slave Mode
  • 15. Bluetooth Master Mode
6. Audio Applications
  • 1.I2S Microphone Recording and U-Disk Playback
  • 2.I2S Audio Playback Experiment
  • 3.Repeater Experiment
7. Xiaozhi AI Voice
  • 1. Burn Xiaozhi Firmware
  • 2. Network and Configuration
  • 3. AI Agent Settings
  • 4. Program Analysis
  • 5. Free Chat
3. Arduino Development Course
1. Before Development
  • 1. Environment Setup
  • 2. Build and Flash
2. Basic Peripherals
  • 1. LED Control
  • 2. Button Detection
  • 3. Peripheral Interrupts
  • 4. ESP_TIMER
  • 5. GPTIMER
  • 6. Watchdog Timer
  • 7. ADC
  • 8. PWM Breathing LED
  • 9. RGB LED Effects
3. Serial Communication and Storage System
  • 1. Serial UART Communication
  • 2. I2C OLED Display
  • 3. SPI Bus Communication
  • 4. Flash Read and Write
  • 5. USB Emulated Mass Storage
4. Network Protocols and Wireless Communication
  • 1. WIFI Network Basics
  • 2. WIFI STA Mode
  • 3. WIFI AP Mode
  • 4. UDP Server Experiment
  • 5. UDP Client Experiment
  • 6. TCP Client Experiment
  • 7. TCP Server Experiment
  • 8. HTTP Client Experiment
  • 9. HTTP Server Experiment
  • 10. MQTT IoT Communication Protocol
  • 11. WIFI OTA Upgrade
  • 12. Bluetooth Fundamentals
  • 13. Bluetooth Slave Mode
  • 14. Bluetooth Master Mode
5. Audio Applications
  • 1.I2S Microphone Recording and U-Disk Playback
  • 2.I2S Audio Playback Experiment
  • 3.Repeater Experiment
4. MicroPython Development Course
1. Before Development
  • 1. Environment Setup
  • 2. Build and Flash
  • 3. Thonny IDE
2. Basic Peripherals
  • 1. LED Control
  • 2. Button Detection
  • 3. Peripheral Interrupts
  • 4. TIMER_IT
  • 5. Watchdog Timer
  • 6. ADC
  • 7. PWM Breathing LED
  • 8. RGB LED Effects
3. Serial Communication and Storage System
  • 1. Serial UART Communication Experiment
  • 2. I2C_OLED Display Experiment
  • 3. SPI Bus Communication Experiment
  • 4. Flash Read and Write Experiment
  • 5. Print Storage
4. Network Protocols and Wireless Communication
  • 1. WIFI Network Basics
  • 2. WIFI STA Mode
  • 3. WIFI AP Mode
  • 4. UDP Client Experiment
  • 5. UDP Server Experiment
  • 6. TCP Client Experiment
  • 7. TCP Server Experiment
  • 8. HTTP Client Experiment
  • 9. HTTP Server Experiment
  • 10. MQTT
  • 11. Bluetooth Fundamentals
  • 12. Bluetooth Slave Mode
  • 13. Bluetooth Master Mode
5. Audio Applications
  • 1. I2S Audio Playback Experiment
  • 2. Repeater Experiment
Download
  • Code
  • Hardware_Info
  • 3D_Model_File
  • Software_Tools
  • VMware
  • VM_File
Download ZIP

Welcome to ESP32 Core Board repository

6. TCP Client Experiment

TCP Client Experiment


TCP Client Experiment1. TCP Overview2. Core Concepts2.1 TCP Three-Way Handshake2.2 TCP vs UDP API Comparison2.3 Three Return Values of recv()3. Project Architecture and Flow3.1 TCP Client4. Hardware Dependencies5. Source Code Analysis — TCP Client5.1 Macro Configuration5.2 WiFi Initialization (Review)5.3 vTcpClientTask() — TCP Client Core6. Operation Flow6.1 Build and Flash Flow6.2 Testing Method6.3 Normal Log — TCP Client7. Common Problems


1. TCP Overview

TCP (Transmission Control Protocol) is a connection-oriented, reliable, byte-stream transport layer protocol. It establishes connections via three-way handshake, ensuring data arrives in order and intact.

FeatureTCPUDP
ConnectionThree-way handshakeConnectionless
ReliabilityGuaranteed delivery, guaranteed orderNot guaranteed
Flow/ Congestion ControlBuilt-in sliding window, slow startNone
Transmission ModeByte stream (no message boundaries)Datagram (has message boundaries)
Server APIbind → listen → accept → recv/sendbind → recvfrom/sendto
Client APIsocket → connect → recv/sendsocket → sendto/recvfrom

TCP is the foundation of IoT communications. Whether HTTP web requests, MQTT message push, OTA firmware upgrades, or database remote connections, all rely on TCP's reliable transmission at the bottom. In industrial automation, smart home, and remote monitoring scenarios, devices report sensor data and receive control instructions—all requiring "no data loss, no order disruption"—which is TCP's core value. UDP is fast but unreliable; TCP has the overhead of three-way handshake but gains an end-to-end acknowledgment and retransmission mechanism, irreplaceable in most IoT scenarios.

This project contains both TCP client and server routines: the client connects to the server and sends data periodically; the server listens on a port, accepts client connections, sends/receives data, and supports reconnecting after client disconnection.


2. Core Concepts

2.1 TCP Three-Way Handshake

  Client                               Server
    │                                    │
    │──── SYN (seq=x) ──────────────────→│  1. Client requests connection
    │                                    │
    │←─── SYN+ACK (seq=y, ack=x+1) ─────│  2. Server acknowledges + requests
    │                                    │
    │──── ACK (ack=y+1) ────────────────→│  3. Client acknowledges
    │                                    │
    │═══════ ESTABLISHED ═══════════════│

In code, the client calls connect() to trigger the handshake, and the server calls accept() to wait for handshake completion.

2.2 TCP vs UDP API Comparison

​x
// === TCP Server ===                        // === UDP Server ===
socket(AF_INET, SOCK_STREAM, 0)            socket(AF_INET, SOCK_DGRAM, 0)
bind(fd, addr, len)                        bind(fd, addr, len)
listen(fd, 5)                              // No listen
client_fd = accept(fd, ...)                // No accept, use recvfrom directly
recv(client_fd, buf, len, 0)              recvfrom(fd, buf, len, 0, &addr, &len)
send(client_fd, buf, len, 0)              sendto(fd, buf, len, 0, &addr, len)

// === TCP Client ===                        // === UDP Client ===
socket(AF_INET, SOCK_STREAM, 0)            socket(AF_INET, SOCK_DGRAM, 0)
connect(fd, &addr, len)                    // No connect
send(fd, buf, len, 0)                     sendto(fd, buf, len, 0, &addr, len)
recv(fd, buf, len, 0)                     recvfrom(fd, buf, len, 0, &addr, &len)

2.3 Three Return Values of recv()

Return ValueMeaningHandling
> 0Received n bytes of dataProcess normally
= 0Peer closed connection normally (sent FIN)close() and break
< 0No data available (non-blocking) or errorIgnore with MSG_DONTWAIT; check errno for others

recv() == 0 is a TCP-specific "peer closed" signal; UDP has no such concept.


3. Project Architecture and Flow

3.1 TCP Client

xxxxxxxxxx
app_main()
  ├─ wifi_init()                         ← WiFi STA init (wait for IP)
  │
  └─ xTaskCreate(vTcpClientTask, ...)   ← Create TCP client task
      └─ vTcpClientTask():
          ├─ socket(AF_INET, SOCK_STREAM, 0)  → Create TCP socket
          ├─ connect(192.168.11.183:8080)     → Three-way handshake
          └─ while(1):
              ├─ send("ESP32 TCP Client Data")
              ├─ recv(MSG_DONTWAIT)  ← Non-blocking receive
              ├─ recv==0 → server disconnected, break
              └─ vTaskDelay(200ms)

4. Hardware Dependencies

  • Hardware Connection: No external wiring, WiFi wireless communication

  • Required Components: lwip/sockets, esp_wifi, esp_netif, esp_event, nvs_flash, FreeRTOS


5. Source Code Analysis — TCP Client

Full source: Source Code → ESP-IDF → 5.Network_Protocol → 4.TCP → TCP_Client

5.1 Macro Configuration

These macros define WiFi connection info and TCP server address. Modify SSID, password, and target IP according to your network environment.

xxxxxxxxxx
#define WIFI_SSID        "Your_WiFi_SSID"       // WiFi SSID
#define WIFI_PASS        "Your_WiFi_Password"   // WiFi password
#define TCP_SERVER_IP    "192.168.11.183"       // Server IP
#define TCP_SERVER_PORT  8080                   // Server port
#define WIFI_TIMEOUT_MS  15000

5.2 WiFi Initialization (Review)

The WiFi STA connection code in this experiment (wifi_init_sta(), event callback, NVS init, etc.) is identical to 5.2 WIFI-STA Mode. app_main() does NVS init → WiFi connection to get IP → xTaskCreate() for TCP task.

For details, review: 5. Network Protocols and Wireless Communication -> 2. WIFI-STA Mode -> WIFI-STA Mode

5.3 vTcpClientTask() — TCP Client Core

The biggest difference from UDP client: TCP is "make a call before speaking"—send()/recv() only after connect() three-way handshake succeeds. UDP is "send a letter directly"—sendto() doesn't need a connection first. Also TCP uses SOCK_STREAM (streaming), UDP uses SOCK_DGRAM (datagram).

In the send-receive loop, a key judgment—recv() returning 0 means the server normally closed the connection (sent FIN package), then break out to close socket and delete task. UDP has no this problem because UDP is connectionless, recvfrom() never returns 0.

xxxxxxxxxx
void vTcpClientTask(void *pv)
{
    int sock_fd;
    struct sockaddr_in server_addr = {0};
    char send_buf[64] = {0};
    char recv_buf[64] = {0};

    // Create TCP socket
    sock_fd = socket(AF_INET, SOCK_STREAM, 0);
    if (sock_fd < 0) {
        ESP_LOGE(TAG, "Create TCP socket failed");
        vTaskDelete(NULL);
        return;
    }

    // Configure server address and connect
    server_addr.sin_family = AF_INET;
    // Port to network byte order
    server_addr.sin_port = htons(TCP_SERVER_PORT);
    inet_pton(AF_INET, TCP_SERVER_IP, &server_addr.sin_addr.s_addr);

    if (connect(sock_fd, (struct sockaddr*)&server_addr,
                sizeof(server_addr)) < 0) {
        // Connect failed
        ESP_LOGE(TAG, "Connect TCP server failed");
        close(sock_fd);
        vTaskDelete(NULL);
        return;
    }
    // TCP handshake complete
    ESP_LOGI(TAG, "TCP server connected");

    // Send-receive loop
    while (1) {
        // Build send data
        sprintf(send_buf, "ESP32 TCP Client Data");
        // Send data
        int ret = send(sock_fd, send_buf, strlen(send_buf), 0);
        if (ret <= 0) {
            // Send failed
            ESP_LOGE(TAG, "Send failed");
            break;
        }
        ESP_LOGI(TAG, "Send: %s", send_buf);
        // Non-blocking receive
        int recv_len = recv(sock_fd, recv_buf, sizeof(recv_buf) - 1,
                            MSG_DONTWAIT);
        if (recv_len > 0) {
            recv_buf[recv_len] = '\0';
            ESP_LOGI(TAG, "Recv: %s", recv_buf);
        }
        else if (recv_len == 0) {
            // Peer closed connection
            ESP_LOGE(TAG, "TCP server disconnected");
            break;
        }

        vTaskDelay(pdMS_TO_TICKS(200));
    }

    close(sock_fd);
    vTaskDelete(NULL);
}

6. Operation Flow

6.1 Build and Flash Flow

ESP-IDF Flash Flow: See ESP-IDF → 1. Before Development → 3. Build and Flash.

6.2 Testing Method

  1. Run a network debugging assistant on PC, select TCP Server mode, listen on port 8080.

Network Debug Assistant Icon

  1. Flash TCP_Client to ESP32. Serial shows connection success → send data → receive reply.

Client Serial Output

6.3 Normal Log — TCP Client

xxxxxxxxxx
I (2856) TCP-CLIENT: Got IP: 192.168.11.100
I (2858) TCP-CLIENT: WiFi connected
I (2860) TCP-CLIENT: TCP socket created
I (2862) TCP-CLIENT: TCP server connected
I (2864) TCP-CLIENT: Send: ESP32 TCP Client Data
I (2866) TCP-CLIENT: Recv: Hello from TCP Server!

Client Serial Output


7. Common Problems

SymptomCauseSolution
connect() returns -1, connection failedServer not started or wrong IPConfirm PC TCP Server is listening, IP and port are correct
Server accept() blocks and doesn't returnNo client connectedNormal behavior, it's a blocking call
Client recv() returns 0Server actively closed connectionNormal disconnect, break then close()
Consecutive send() failuresPeer closed / network interruptedTCP connection broken, need to connect() again
bind() failedPort in useUse a different port / wait 2 minutes (TIME_WAIT timeout)
recv() data "sticks" togetherTCP is byte stream, no message boundariesDefine frame header+length or delimiter protocol at application layer
Server can only connect one clientSingle-threaded sequential processingChange to xTaskCreate for each accept() for independent tasks
Meaning of listen() second parameter 5Not max connections, it's the pending connection queue lengthAlready-accepted connections don't count
UDP Server Experiment
TCP Server Experiment

COMPANY

  • About us
  • Team Style
  • Blog

LEARNING & EXPLORATION

  • Tutorials
  • Edge AI hardware
  • Educational robots
  • Embedded intelligent hardware

WHERE TO BUY

  • Yahboom Online Store
  • Amazon
  • Alibaba
  • AliExpress
  • Mercado

TECHNOLOGY SUPPORT

  • Email: support@yahboom.com

BE A DISTRIBUTOR

  • Email: sales@yahboom.com
QR Code
QR Code

Copyright © 2017-2026 Yahboom. All Rights Reserved.

EN/中文