Blinking an [LED](https://www.onzuu.com/category/led-emitters-infrared-uv-visible) is the “hello world” of [microcontrollers](https://www.ampheo.com/c/microcontrollers): configure a GPIO pin as an output, then toggle it HIGH/LOW with a delay.

**Wiring (don’t skip this)**
* MCU GPIO pin → 220–1kΩ [resistor](https://www.onzuu.com/category/resistors) → LED anode (long leg)
* LED cathode (short leg/flat side) → GND
(Or wire LED to VCC and have the pin sink current—either works.)
**Generic pseudocode**
```
init_gpio_output(LED_PIN);
while (1) {
set_pin_high(LED_PIN);
delay_ms(500);
set_pin_low(LED_PIN);
delay_ms(500);
}
```
**[Arduino](https://www.ampheo.com/c/development-board-arduino) (Uno/Nano)**
```
const int LED_PIN = 13;
void setup() {
pinMode(LED_PIN, OUTPUT);
}
void loop() {
digitalWrite(LED_PIN, HIGH);
delay(500);
digitalWrite(LED_PIN, LOW);
delay(500);
}
```
**[STM32](https://www.ampheo.com/search/STM32) (HAL / CubeIDE) example**
Assume your LED is on PA5 (common on [Nucleo boards](https://www.onzuu.com/search/Nucleo)):
```
// after MX_GPIO_Init() has set PA5 as Output Push-Pull
while (1)
{
HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_5);
HAL_Delay(500);
}
```
In CubeMX, set PA5 → GPIO_Output and generate code.
**Bare-metal AVR example ([ATmega328P](https://www.ampheo.com/search/ATmega328P))**
Blink on PB5 ([Arduino Uno](https://www.ampheo.com/product/a000046-25542493) LED):
```
#include <avr/io.h>
#include <util/delay.h>
int main(void) {
DDRB |= (1 << DDB5); // PB5 output
while (1) {
PORTB ^= (1 << PORTB5); // toggle
_delay_ms(500);
}
}
```
**Common mistakes**
* No resistor → LED can burn out or overload the pin.
* Wrong polarity (LED reversed).
* Pin not actually configured as output.
* Using the wrong pin name/port for your board.