HomeArduinoCore TutorialsArduino Serial Communication Tutorial

Arduino UART Tutorial: Serial Communication, Sending & Receiving Data with Examples

Every Arduino project eventually needs to talk to something — a PC for debugging, a GPS module for location data, a GSM module for SMS, an ESP8266 for Wi-Fi, or another microcontroller in a larger system. UART is how that conversation happens. Two wires (TX and RX), a matched baud rate, and the Arduino Serial library — that is the entire setup.

In this tutorial you will learn how UART communication works at the parameter level (baud rate, data bits, stop bits, parity), which pins carry TX and RX on Uno, Nano, and Mega, and how to use every key function in the Arduino Serial library. You will then build three complete examples: sending data from Arduino to your PC, receiving data from the PC and echoing it back, and controlling an LED on pin 13 from commands typed in the Serial Monitor. A troubleshooting section covers the three most common UART problems — baud rate mismatch, crossed TX/RX wiring, and Hardware UART versus SoftwareSerial.

Before starting, check that you are comfortable with:

For other Arduino communication protocols covered on this site:

Browse the full Arduino Core tutorials collection for more.

Arduino UART Serial Communication

Arduino UART Communication — How It Works

What Is UART (Universal Asynchronous Receiver-Transmitter)?

UART (Universal Asynchronous Receiver/Transmitter) is one of the most common ways for Arduino boards to communicate with other devices. It allows data to be sent and received one bit at a time over just two wires: TX (transmit) and RX (receive). Unlike parallel communication, where multiple bits are sent simultaneously, UART is simple, lightweight, and perfect for connecting Arduino to a computer, sensors, or other microcontrollers.

A UART frame diagram shows how data is transmitted bit by bit over a serial line between devices. Each frame consists of several key parts that ensure the data is sent and received correctly:

  1. Idle Line – When no data is being transmitted, the line remains at a logic HIGH (1). This is the default state.
  2. Start Bit – A single logic LOW (0) signals the beginning of a data frame. The receiver detects this to know that incoming bits are about to arrive.
  3. Data Bits – Typically 8 bits, sent least significant bit (LSB) first. These bits carry the actual information. Each bit lasts for the duration defined by the baud rate.
  4. Parity Bit (Optional) – Used for error checking. Depending on the configuration, it can be even or odd parity. If not used, this bit is skipped.
  5. Stop Bit(s) – One or more logic HIGH (1) bits mark the end of the frame, allowing the receiver to prepare for the next data frame.
Arduino UART Frame consisting start bit, data bits, parity and stop bit.

By looking at the UART frame diagram, you can visualize the sequence of bits on the TX/RX line. This makes it easier to understand how serial communication works, troubleshoot errors, and design communication protocols between Arduino and other devices.


UART Communication Parameters

The key UART parameters are:

  1. Baud Rate
    • Defines the speed of data transfer in bits per second (bps).
    • Both the Arduino and the device it communicates with must use the same baud rate.
    • Common baud rates include 9600, 115200, etc.
    • Example in Arduino: Serial.begin(9600);
  2. Data Bits
    • Determines how many bits represent each character or data unit.
    • Standard is 8 bits per character.
  3. Stop Bits
    • Used to indicate the end of a data packet.
    • Can be 1 or 2 bits. Arduino usually uses 1 stop bit by default.
  4. Parity
    • A method to check for errors in transmitted data.
    • Can be None, Even, or Odd. Arduino typically uses No parity.
  5. Flow Control (Optional)
    • Manages the pace of data transfer between devices to prevent data loss.
    • Hardware flow control (RTS/CTS) is rarely used on standard Arduino boards.

These parameters must be correctly configured on both communicating devices to ensure error-free UART communication. In Arduino, most of these settings are handled automatically with the Serial.begin() function, while advanced settings can be configured using lower-level commands.


Arduino UART TX and RX Pins by Board

UART communication on Arduino relies on two main pins: TX (Transmit) and RX (Receive). The TX pin is used to send data from the Arduino to another device, while the RX pin receives data from external devices.

On most Arduino boards:

  • Arduino Uno / Nano:
    • TX = Pin 1
    • RX = Pin 0
  • Arduino Mega:
    • Serial0: TX0 = Pin 1, RX0 = Pin 0
    • Serial1: TX1 = Pin 18, RX1 = Pin 19
    • Serial2: TX2 = Pin 16, RX2 = Pin 17
    • Serial3: TX3 = Pin 14, RX3 = Pin 15
Note: When using the USB connection to your PC, TX and RX pins on Uno/Nano are shared with the USB interface. Be careful if connecting other devices to these pins to avoid conflicts.

Arduino Serial Library — Key Functions

The Arduino Serial Library provides a set of built-in functions to use the UART module for serial communication. It allows Arduino boards to send and receive data over the TX (transmit) and RX (receive) pins easily. Using this library, you can communicate with a PC, another Arduino, or any device that supports UART.

Key Functions of the Serial Library:

  1. Serial.begin(baudRate)
    • Initializes the UART communication with the specified baud rate.
    • Example: Serial.begin(9600);
  2. Serial.print() / Serial.println()
    • Sends data from Arduino to the connected device.
    • Serial.println() adds a new line after the data.
  3. Serial.read()
    • Reads incoming data from the RX pin.
    • Returns the first byte of incoming serial data.
  4. Serial.available()
    • Checks if data is available to read.
    • Returns the number of bytes in the receive buffer.
  5. Serial.flush()
    • Clears the serial buffer to ensure no leftover data interferes with new communication.

The Arduino Serial Library abstracts the low-level details of UART, making it easy for beginners to implement serial communication without worrying about hardware registers or timing.

Connect Arduino to PC via UART

Most Arduinos (Uno, Nano, Mega) come with a USB-to-Serial converter. You can use the USB cable to directly connect the Arduino to the computer. Alternatively, you can also use some external hardware (USB to TTL Converter) to communicate to the computer.

To communicate with your computer using UART:

  1. USB Connection: Simply connect the Arduino via USB to your PC. This allows communication through the Serial Monitor in the Arduino IDE.
  2. Direct UART (Optional): If you want to use the hardware UART pins directly:
    • Connect Arduino TX → USB-to-Serial RX
    • Connect Arduino RX → USB-to-Serial TX
    • Connect GND → GND
      This setup is useful when using external modules or USB adapters without affecting the Arduino’s main USB connection.
Arduino Uno connected to FT232 USB-to-TTL module — Arduino TX to FT232 RX, Arduino RX to FT232 TX, GND to GND for external UART-to-PC communication

The image above shows how to connect the Arduino to an external USB to TTL Module (Like FT232). The TX pin from Arduino connects to the RX pin of the module and RX pin from Arduino connects to the TX pin of the module.

Send Data from Arduino to PC — Serial.println()

We will first learn how to transmit data from Arduino to the PC using UART. This is useful for logging sensor readings, debugging programs, or sending status messages from your Arduino to the computer.

Code — Transmit “Hello, PC!” Every Second

Sending data from Arduino to your PC is simple with the Serial object. First, you need to initialize the UART communication in the setup() function using the Serial.begin() command with a chosen baud rate. For example:

void setup() {
  Serial.begin(9600); // Initialize UART at 9600 baud
}

void loop() {
  Serial.println("Hello, PC!"); // Send data to the PC
  delay(1000); // Wait 1 second before sending the next message
}

Explanation:

  • Serial.begin(9600) sets the communication speed to 9600 bits per second.
  • Serial.println() sends data followed by a newline character, making it easier to read in the Serial Monitor.
  • The delay() function ensures messages are not sent too fast.

Open the Arduino Serial Monitor

Once the Arduino is running the above code:

  1. Open the Arduino IDE.
  2. Go to Tools → Serial Monitor (or press Ctrl+Shift+M).
Arduino IDE with Tools menu open showing Serial Monitor option — set baud rate to 9600 to match Serial.begin(9600) in the sketch
  1. Set the baud rate in the Serial Monitor to match your Serial.begin() (e.g., 9600).
  2. You will see “Hello, PC!” appearing every second.

Output — Message Appears Every 1 Second

The GIF below shows the output of the above code on the Serial monitor.

Animated GIF showing Arduino IDE Serial Monitor with "Hello, PC!" appearing every 1 second — Serial.println() transmitting at 9600 baud

This simple example demonstrates one-way UART communication from Arduino to your PC. It’s useful for debugging, logging sensor data, or sending status messages to your computer.

Receive Data from PC on Arduino — Serial.read()

Arduino can not only send data to a PC but also receive data from the computer over UART. This is useful for controlling Arduino projects from a PC, sending commands, or updating variables in real-time.

How UART Reception Works on Arduino

When data is sent from the PC to Arduino, it arrives on the RX (Receive) pin. Arduino reads this incoming data using the Serial.read() or Serial.readString() functions. The data is stored in a buffer until your program processes it.

Key points:

  • Each character sent from the PC is received one byte at a time.
  • The Arduino must check if data is available before reading it using Serial.available().
  • Matching baud rates on both Arduino and PC is essential; otherwise, the received data may be garbled.

Code — Echo Received Characters Back to PC

Here’s a simple example that reads data from the PC and echoes it back:

void setup() {
  Serial.begin(9600); // Start UART at 9600 baud
  Serial.println("Send me a message:");
}

void loop() {
  if (Serial.available() > 0) {        // Check if data is available
    char receivedChar = Serial.read(); // Read one byte
    Serial.print("You sent: ");        
    Serial.println(receivedChar);      // Echo back the received character
  }
}

Explanation:

  • Serial.available() returns the number of bytes waiting in the buffer.
  • Serial.read() reads the first byte from the buffer.
  • Serial.println() sends a response back to the PC, confirming what was received.

Output — Serial Monitor Echo Demo

The image below shows the data sent by PC is received by Arduino and transmitted back to PC.

Arduino Serial Monitor showing characters typed by user echoed back — "You sent: H", "You sent: i" — demonstrating Serial.read() one-byte-at-a-time reception

Control Arduino LED from PC via UART

You can expand the serial to control LEDs, motors, or other components. For example:

void setup() {
  Serial.begin(9600); // Start UART at 9600 baud
  Serial.println("Send 1 to turn on the LED\n And 0 to turn it OFF");
  pinMode(13, OUTPUT);
}

void loop() {
  if (Serial.available() > 0) {        // Check if data is available
    char receivedChar = Serial.read(); // Read one byte
    if (receivedChar == '1') {
      digitalWrite(13, HIGH); // Turn LED ON
      Serial.println("LED turned ON");
    } else if (receivedChar == '0') {
        digitalWrite(13, LOW);  // Turn LED OFF
        Serial.println("LED turned OFF");
      }
  }
}

We will control the LED connected to pin 13 using the data received from the UART. I have already covered how to control the LED on Arduino, so check out the tutorial if you haven’t.

Here we will turn the LED ON if the data is a ‘1’ and turn it OFF if the data is ‘0’. We will also print the state of the LED on the console.
This way, you can send simple commands from your PC via the Serial Monitor or a custom application to control your Arduino project.

Output — LED Response to Serial Commands

The GIF below shows the LED is controlled by the data received from PC via UART.

Animated GIF showing Arduino Uno onboard LED on pin 13 turning ON when '1' is typed in Serial Monitor and turning OFF when '0' is typed — UART LED control demo

As you can see in the gif, when a ‘1’ is sent by the PC, the LED is turned ON. Similarly, when a ‘0’ is sent, the LED is turned OFF. When any other data is sent (other than ‘0’ and ‘1’), the LED is not affected at all.

UART Troubleshooting — Common Problems & Fixes

UART communication is usually straightforward, but beginners often encounter common problems. Understanding these issues and their solutions can save a lot of debugging time.

Baud Rate Mismatch — Garbled Output

A baud rate mismatch occurs when the Arduino and the device it’s communicating with (PC, module, or another microcontroller) are set to different speeds. For example, if Arduino is transmitting at 9600 baud but the PC is set to 115200, the data received will appear garbled or unreadable.

Fix:

  • Ensure both devices use the same baud rate in code and serial monitor.
  • Double-check Serial.begin(baudRate) in your Arduino sketch matches the PC or module settings.

TX/RX Crossed Incorrectly — No Data

Incorrect wiring of TX (Transmit) and RX (Receive) pins is a very common UART issue. Remember:

  • Arduino TX → Module/PC RX
  • Arduino RX → Module/PC TX

Fix:

  • Always cross the TX and RX connections.
  • Connect GND to GND between devices to ensure a common reference voltage.
  • Avoid connecting devices that use the same UART pins simultaneously (especially on Arduino Uno with USB).

Hardware UART vs SoftwareSerial — When to Use Each

  • Hardware UART: Built into the Arduino’s microcontroller, offers reliable, high-speed communication, usually using the Serial object. Most boards have at least one hardware UART.
  • SoftwareSerial: A library that simulates UART on any digital pins. It is slower and may not be suitable for high-speed communication or simultaneous multiple UART devices.

Use hardware UART whenever possible for reliability, and reserve SoftwareSerial for additional peripherals when hardware UART pins are occupied.


USB Conflict on Arduino Uno — TX/RX Shared with USB

Pins 0 (RX) and 1 (TX) on the Arduino Uno are also used by the USB connection. If another UART device is connected to these pins, sketch uploads or Serial Monitor communication may fail.

Fix

  • Disconnect devices from pins 0 and 1 while uploading code
  • Use SoftwareSerial on different GPIO pins
  • Use boards with multiple UARTs like the Mega 2560

Real-World UART Applications for Arduino

UART is not just for simple message logging. It is widely used in real-world projects for communication with modules, debugging, and remote control.

GPS Modules — NMEA Sentences over UART

Many Arduino-compatible modules rely on UART for communication:

  • GPS Modules: Send location coordinates to Arduino via UART.
  • GSM Modules: Receive and send SMS/AT commands using UART.
  • ESP8266 Wi-Fi Modules: Connect Arduino to the internet, receive commands, or send data via UART.

Tip: Always check the module’s datasheet for the correct TX/RX pins and baud rate.


GSM Modules — AT Commands over UART

UART is a powerful tool for debugging:

  • Send variable values or sensor readings to the Serial Monitor.
  • Track program flow by printing messages at key points in your code.
  • Identify errors in real-time without stopping the program.

Example:

Serial.print("Temperature: ");
Serial.println(sensorValue);

This prints sensor values live, making it easier to troubleshoot and optimize your project.


ESP8266 Wi-Fi Modules — Wi-Fi via UART

ESP8266 modules commonly use UART to communicate with Arduino boards.

Using UART, Arduino can:

  • Send AT commands to the ESP8266
  • Connect to Wi-Fi networks
  • Send sensor data to cloud servers
  • Receive commands from web or mobile applications

Example applications:

  • IoT sensor monitoring
  • Remote LED control
  • Weather stations
  • Home automation systems

Most ESP8266 modules operate at 3.3V logic levels, so avoid connecting 5V UART signals directly.


Debugging Live Sensor Values with Serial Monitor

UART is one of the easiest ways to debug Arduino projects in real time.

Using the Serial Monitor, you can:

  • Print sensor readings continuously
  • Check variable values during execution
  • Verify program logic
  • Detect unexpected behavior quickly

Example:

Serial.print("Temperature: ");
Serial.println(sensorValue);

This sends live sensor values to the Serial Monitor, making troubleshooting much easier during development.

Arduino UART: Frequently Asked Questions

Conclusion

UART is the foundational communication protocol in the Arduino ecosystem — it is how your sketch talks to your PC during development, how your board connects to GPS, GSM, Wi-Fi, and Bluetooth modules in deployed projects, and how two microcontrollers exchange data in larger systems. The Serial library abstracts all the hardware complexity: Serial.begin() configures the baud rate, Serial.available() tells you when data has arrived, and Serial.read() retrieves it one byte at a time.

In this tutorial you covered the full one-wire-per-direction model — TX out, RX in, GND shared — and the four parameters that both sides must agree on before a single byte transfers correctly. You sent data to the PC with Serial.println(), received it back with Serial.read(), parsed command characters to control an LED, and confirmed the behaviour live in the Serial Monitor.

The troubleshooting section covers the three problems that catch nearly every beginner: baud rate mismatch producing garbled output, TX/RX crossed the wrong way producing silence, and using SoftwareSerial on a Uno when hardware UART pins are already occupied by USB.

UART feeds naturally into more advanced protocols. I2C connects multiple sensors on two wires with addressed communication. SPI gives you higher-speed full-duplex transfers for displays and SD cards. External interrupts let your board react to a UART RX event without polling Serial.available() in every loop iteration. Download the full project above and explore the Arduino Core tutorials collection for the next step.

Download Arduino UART Serial Communication Project Files

Complete Arduino sketches for UART serial communication: transmit "Hello, PC!" every second via Serial.println(), receive and echo characters with Serial.read(), and control the onboard LED on pin 13 by sending '1' (ON) and '0' (OFF) from the Serial Monitor. All code runs at 9600 baud and is compatible with Uno, Nano, and Mega. Free to download — support the work if it helped you.

Send + Receive Code LED Control via Serial Uno / Nano / Mega Compatible

Browse More Arduino Core Tutorials

About the Author
Arun Rawat
Arun Rawat
Embedded Systems Engineer · Founder, ControllersTech

Arun is an embedded systems engineer with 10+ years of experience in STM32, ESP32, and AVR microcontrollers. He created ControllersTech to share practical tutorials on embedded software, HAL drivers, RTOS, and hardware design — grounded in real industrial automation experience.

Subscribe
Notify of

0 Comments
Newest
Oldest Most Voted
×

Don’t Miss Future STM32 Tutorials

Join thousands of developers getting free guides, code examples, and updates.