The 2026 Raspberry Pi GPIO Pin Diagram: What Changed with the Pi 5?

If you are looking at a Raspberry Pi GPIO pin diagram for the first time, the physical 40-pin header layout looks identical across the Pi 3, 4, and 5. The 5V, 3V3, Ground, and GPIO numbering (BCM) on the physical pins have not moved. However, if you are wiring up a Raspberry Pi 5, the internal architecture has fundamentally changed, and treating it exactly like a Pi 4 will lead to bricked peripherals and failed scripts.

The Raspberry Pi 5 uses the RP1 southbridge chip to handle all GPIO, I2C, SPI, and PWM routing. The main BCM2712 processor no longer talks directly to the pins. This means the legacy RPi.GPIO Python library—which relied on direct memory access to the BCM2711 registers—is completely deprecated and will throw fatal errors on Pi 5 hardware running Bookworm OS or later.

Callout Tip: For all new Pi 5 projects, you must use the gpiozero library (which automatically routes through the RP1 pin factory) or the C-based lgpio library. Never start a new Pi 5 build with RPi.GPIO.

Project Build: I2C Thermal Monitor with PWM Cooling

To make sense of the Raspberry Pi GPIO pin diagram, we need a practical build that exercises multiple pin types: I2C for data, hardware PWM for motor control, and power/ground rails. We are building a thermal monitor that reads an I2C temperature sensor and spins up a 5V PWM PC fan when the threshold is crossed.

Parts List & Exact Variants

  • Board: Raspberry Pi 5 (4GB or 8GB variant) running Raspberry Pi OS Bookworm (64-bit).
  • Sensor: Adafruit MCP9808 High Accuracy I2C Temperature Sensor (Product ID: 1782). Default I2C address: 0x18.
  • Fan: Noctua NF-A4x20 5V PWM (4-pin). Do not use a 12V fan; the Pi 5 GPIO and 5V rail cannot safely drive 12V logic.
  • Switching: 2N2222 NPN Bipolar Junction Transistor (BJT) to handle the fan's 100mA+ draw.
  • Protection: 1N4007 rectifier diode (flyback protection) and a 1kΩ base resistor.
  • Wiring: 24 AWG silicone jumper wires and a half-size breadboard.

Pin Mapping Table

This table maps the physical pin numbers on the Raspberry Pi GPIO pin diagram to the BCM (software) numbers and the specific component connections.

Physical Pin BCM GPIO Function Wiring Destination
1 N/A 3V3 Power MCP9808 VDD
3 GPIO 2 (SDA1) I2C Data MCP9808 SDA
5 GPIO 3 (SCL1) I2C Clock MCP9808 SCL
6 N/A Ground MCP9808 GND & 2N2222 Emitter
12 GPIO 18 Hardware PWM0 1kΩ Resistor to 2N2222 Base
2 N/A 5V Power Noctua Fan 5V Wire (Red)

Numbered Wiring Steps

  1. De-energize the Pi: Always unplug the USB-C power supply before wiring the GPIO header to prevent shorting the 5V rail to a data pin.
  2. Wire the I2C Sensor: Connect Pin 1 (3V3) to the MCP9808 VDD. Connect Pin 3 (SDA) and Pin 5 (SCL) to the sensor's respective pins. Connect Pin 6 (GND) to the sensor GND.
  3. Build the Fan Driver: Connect the 2N2222 transistor's Collector to the Noctua Fan's PWM control wire (Blue) and Ground wire (Black) to Pin 6 (GND). *Note: The Noctua 5V PWM fan requires a 5V supply on its Red wire (Pin 2) and the Black wire to GND, while the Blue wire receives the PWM signal.*
  4. Add Flyback Protection: Place the 1N4007 diode across the fan's power terminals (stripe facing the 5V Red wire) to absorb inductive voltage spikes when the fan spins down.
  5. Verify Connections: Use a multimeter in continuity mode to ensure no 5V or 3V3 lines are shorted to adjacent GPIO data pins before applying power.

Complete Python Code (gpiozero & smbus2)

This script targets the Raspberry Pi 5 (4GB) running Bookworm. It uses smbus2 for raw I2C register reads (avoiding heavy dependency chains) and gpiozero for safe RP1-compatible PWM control. Install dependencies via terminal: sudo apt install python3-smbus2 python3-gpiozero.

import time
import sys
from smbus2 import SMBus
from gpiozero import PWMOutputDevice

# --- PIN & ADDRESS DEFINITIONS ---
I2C_BUS_ID = 1          # Physical pins 3 (SDA) and 5 (SCL)
MCP9808_ADDR = 0x18     # Default I2C address for Adafruit MCP9808
TEMP_REG = 0x05         # Ambient Temperature Register
FAN_PWM_PIN = 18        # Physical pin 12 (Hardware PWM0)

# --- THRESHOLDS ---
TEMP_THRESHOLD = 35.0   # Celsius - Fan kicks on above this
FAN_MIN_SPEED = 0.3     # 30% duty cycle minimum to overcome fan stall voltage

# Initialize PWM Fan (gpiozero handles RP1 routing automatically)
fan = PWMOutputDevice(FAN_PWM_PIN, frequency=25000) # 25kHz is standard for PC fans

def read_temperature_celsius():
    try:
        with SMBus(I2C_BUS_ID) as bus:
            # Read 2 bytes from the ambient temperature register
            raw_data = bus.read_i2c_block_data(MCP9808_ADDR, TEMP_REG, 2)
            
            # Convert raw bytes to Celsius (MCP9808 datasheet formula)
            upper_byte = raw_data[0] & 0x1F  # Clear alert flag bits
            lower_byte = raw_data[1]
            
            if upper_byte & 0x10:  # Check if temperature is negative
                upper_byte &= 0x0F
                return (upper_byte * 16 + lower_byte / 16) - 256
            return (upper_byte * 16 + lower_byte / 16)
            
    except OSError as e:
        # Catch the exact I2C bus error
        if e.errno == 121:
            print(f'CRITICAL I2C ERROR: {e}')
            print('Remote I/O error. Check SDA/SCL wiring and pull-up resistors.')
            sys.exit(1)
        else:
            raise

try:
    print('Starting thermal monitor... Press CTRL+C to stop.')
    while True:
        current_temp = read_temperature_celsius()
        print(f'Current Temp: {current_temp:.2f} C', end='\r')
        
        if current_temp > TEMP_THRESHOLD:
            # Scale fan speed based on how far over the threshold we are
            # Max out at 1.0 (100% duty cycle)
            speed = min(1.0, FAN_MIN_SPEED + ((current_temp - TEMP_THRESHOLD) * 0.1))
            fan.value = speed
        else:
            fan.value = 0  # Turn fan off
            
        time.sleep(2)

except KeyboardInterrupt:
    print('\nShutting down safely...')
    fan.off()
    sys.exit(0)

Debugging: First 3 Things to Check When GPIO Fails

When your build fails to boot or the script crashes, don't start rewriting code. Hardware and bus configurations are the culprit 90% of the time. Here are the first three things to check, ranked by probability.

1. The I2C Bus Address & Physical Wiring

The Symptom: Your script crashes immediately with the exact error string: OSError: [Errno 121] Remote I/O error.

The Cause: The Pi's I2C controller sent a clock pulse on SCL, but no device acknowledged on SDA. This means the sensor is either wired backwards, lacks power, or is on a different I2C address.

The Fix: Run i2cdetect -y 1 in the terminal. If the grid is empty, swap your SDA and SCL wires (it won't damage the Pi 5 RP1 chip, but it will fail to communicate). If you see a different address (like 0x19), update the MCP9808_ADDR variable in the code. The Pi 5 internal pull-ups are generally sufficient for short breadboard runs, but if your wires exceed 12 inches, add external 4.7kΩ pull-up resistors to 3V3.

2. PWM Clock Routing and Pin Factory Errors

The Symptom: gpiozero.exc.GPIOZeroError: Pin factory error or the fan simply stays at 100% speed and ignores the PWM duty cycle.

The Cause: You are either trying to use a software PWM pin that the RP1 is struggling to time accurately under CPU load, or you have a conflicting legacy library installed.

The Fix: Ensure you are using Physical Pin 12 (BCM GPIO 18). This is a dedicated hardware PWM pin on the Pi 5. Software PWM on random GPIO pins will cause fan stuttering and audible whining due to microsecond timing jitter in the Linux kernel scheduler. Furthermore, ensure you haven't installed RPi.GPIO via pip, as it can pollute the pin factory environment variables.

3. Power Brownout and USB-C Throttling

The Symptom: The Pi reboots randomly when the fan spins up to 100%, or you see a lightning bolt icon on the display.

The Cause: The Pi 5 requires a robust 5V/5A (27W) USB-C PD power supply. If you are using an old Pi 4 (5V/3A) charger, the transient current spike of the fan starting up pulls the 5V rail below 4.65V, triggering the RP1's brownout protection.

The Fix: Use the official Raspberry Pi 27W USB-C PD power supply. If you must use a standard 5V/3A supply, the Pi 5 will restrict the USB ports and GPIO 5V rail current limit to prevent brownouts, which may starve your fan.

Extending and Simplifying the Build

Not every project needs to be this complex. Here is how to adapt this Raspberry Pi GPIO pin diagram project to your specific skill level or use case.

To Simplify: If you only want to log temperatures for a server rack and don't need active cooling, drop the Noctua fan, the transistor, and the diode entirely. Remove the gpiozero imports from the Python script and just append the current_temp variable to a CSV file with a timestamp. You can power the MCP9808 directly from the 3V3 and GND pins and run the script as a background cron job.

To Extend: To integrate this into a smart home dashboard, add the paho-mqtt library. Inside the while True loop, publish the current_temp and fan.value to an MQTT broker (like Mosquitto running on Home Assistant). You can then map the physical I2C sensor to a virtual thermostat entity in Home Assistant, allowing you to adjust the TEMP_THRESHOLD via a web dashboard without touching the Python code.

Frequently Asked Questions

Where can I find a printable Raspberry Pi GPIO pin diagram?

The most reliable, up-to-date printable diagrams are hosted on the official Raspberry Pi documentation site and the Pinout.xyz interactive database. When printing, ensure the diagram explicitly labels both the 'Physical Pin' (1-40) and the 'BCM GPIO' numbers, as Python libraries use the BCM numbering scheme by default, while physical wiring requires the physical pin layout.

Are the Raspberry Pi 4 and Pi 5 GPIO pin diagrams identical?

Physically, yes. The 40-pin header footprint, power pin locations, and primary I2C/SPI/UART pinouts are identical. Electrically and logically, no. The Pi 5 routes these pins through the RP1 southbridge chip, which changes the maximum continuous current per pin (capped strictly at 16mA on Pi 5 compared to the Pi 4's more forgiving limits) and alters the I2C clock stretching behavior. Always treat Pi 5 pins as more sensitive to overcurrent.

Why does my Raspberry Pi GPIO pin diagram show multiple ground pins?

You will notice eight separate Ground (GND) pins scattered across the 40-pin header (Pins 6, 9, 14, 20, 25, 30, 34, and 39). This is intentional. High-speed buses like SPI and I2C require a ground reference immediately adjacent to the signal wire to minimize inductive loop area and reduce electromagnetic interference (EMI). Having multiple ground pins allows you to pair a ground wire directly next to every data wire in your ribbon cables.

Can I use 5V sensors directly with the Raspberry Pi GPIO pins?

No. The Raspberry Pi 5 (and all previous models) uses 3.3V logic on its GPIO data pins. While the 5V power pins can supply current to a 5V sensor's VCC line, the sensor's data output (TX, SDA, or digital out) will send 5V back into the Pi's RX or SDA pin. This will permanently destroy the RP1 southbridge pin or the internal ESD protection diodes. You must use a bidirectional logic level converter (like the BSS138 MOSFET-based modules) to step 5V data signals down to 3.3V before they reach the Pi.