Unit 2: Advanced GPIO & Peripheral Control

ECE140 — Workshop On Iot For Digital Society 10 min read

I. Orientation — GPIO as a Hardware–Software Interface

General-purpose input/output (GPIO) allows a computer such as a Raspberry Pi to sense digital signals and control external hardware. GPIO pins operate at 3.3 V logic, while software configures each pin as an input, output, or alternate peripheral function.

  • Digital states: A logical LOW is approximately 0 V; a logical HIGH is approximately 3.3 V.
  • Pin numbering:
    • BCM numbering identifies channels by Broadcom GPIO number, such as GPIO17.
    • BOARD numbering identifies physical header positions, such as pin 11.
  • Electrical limits: GPIO pins supply only small currents and must not directly power motors, relays, or other high-current loads.
  • Input stability: Pull-up or pull-down resistors prevent floating inputs; typical internal pulls are software-selectable.
  • Output protection: Current-limiting resistors, transistor stages, driver ICs, and flyback protection isolate the processor from loads.
  • Timing model: Ordinary Python GPIO operations are scheduled by Linux and therefore experience variable latency.
  • Safe convention: Connect grounds between the Raspberry Pi and external driver circuit, but use a suitable external supply for motors.
  • Cleanup requirement: Programs should place outputs in a safe state and release GPIO resources when terminating.

II. Python GPIO Libraries — High-Level Hardware Access

Python GPIO libraries convert pin configuration, input sampling, output control, and event detection into programmable interfaces.

A. Python libraries: RPi.GPIO and GPIO Zero

RPi.GPIO provides procedural, pin-level control, whereas GPIO Zero provides object-oriented abstractions for common devices.

  1. RPi.GPIO
    • Programming model: Functions directly configure and manipulate channels using constants such as GPIO.IN, GPIO.OUT, GPIO.HIGH, and GPIO.LOW.
    • Numbering selection: GPIO.setmode(GPIO.BCM) selects Broadcom numbering; mixing BCM and BOARD identifiers can operate the wrong pin.
    • Output example: An LED on GPIO17 requires a series resistor, commonly 220–330 Ω.
PYTHON
import RPi.GPIO as GPIO
from time import sleep

LED = 17
GPIO.setmode(GPIO.BCM)
GPIO.setup(LED, GPIO.OUT, initial=GPIO.LOW)

try:
    GPIO.output(LED, GPIO.HIGH)
    sleep(1)
finally:
    GPIO.cleanup()
  • PWM support: GPIO.PWM(channel, frequency) implements software pulse-width modulation. If duty cycle is D percent and period is T, HIGH time is:
TEXT
t_high = (D / 100)T

Here, t_high is the HIGH duration in seconds, D is duty cycle in percent, and T = 1/f, where f is frequency in hertz.

  1. GPIO Zero
    • Device model: Classes such as LED, Button, Motor, and Servo represent complete components rather than individual voltage operations.
    • Readable behavior: button.when_pressed = led.on connects an event to an action without an explicit polling loop.
    • Pin factories: GPIO Zero can use different back ends, including local GPIO implementations and pigpio, depending on platform support.
    • Resource management: Device objects support close() and context managers, reducing the chance that pins remain reserved.

B. Applications and limitations

Library choice depends on the required abstraction, timing precision, and hardware platform.

  • RPi.GPIO strength: Direct pin control is useful for teaching signal-level behavior and maintaining older Raspberry Pi projects.
  • GPIO Zero strength: Device classes reduce boilerplate and make application intent clearer.
  • Compatibility: Raspberry Pi models and operating-system releases differ in GPIO subsystem support; the library and back end must explicitly support the target board.
  • Timing limitation: Neither ordinary Python loops nor software PWM should be assumed to provide hard real-time timing under Linux.
  • Privilege and access: GPIO device permissions may require appropriate group membership or service configuration.

III. Interrupt-Driven Input — Responding to External Events

Interrupt-driven programming reacts to signal transitions instead of repeatedly polling an input, reducing wasted processor time and improving responsiveness.

A. Interrupt-driven GPIO programming

An edge event occurs when a signal changes from LOW to HIGH, HIGH to LOW, or in either direction.

  • Edge types:
    • Rising edge: 0 → 1, represented by GPIO.RISING.
    • Falling edge: 1 → 0, represented by GPIO.FALLING.
    • Both edges: Either transition, represented by GPIO.BOTH.
  • Event registration: GPIO.add_event_detect() associates a channel with edge detection and an optional callback.
  • Callback rule: The callback should complete quickly; lengthy calculations or network operations should be passed to a queue or worker thread.
  • Debouncing: Mechanical contacts may generate several transitions over 1–20 ms. Hardware RC networks or software timing suppress these false events.
  • Example: A button connects GPIO23 to ground and uses the internal pull-up.
PYTHON
import RPi.GPIO as GPIO
from signal import pause

BUTTON = 23

def pressed(channel):
    print(f"Falling edge on GPIO{channel}")

GPIO.setmode(GPIO.BCM)
GPIO.setup(BUTTON, GPIO.IN, pull_up_down=GPIO.PUD_UP)
GPIO.add_event_detect(
    BUTTON, GPIO.FALLING, callback=pressed, bouncetime=200
)

try:
    pause()
finally:
    GPIO.cleanup()

Here, bouncetime=200 suppresses additional callbacks for approximately 200 ms.

B. Reliability and concurrency

An interrupt-style API improves structure but still runs within the operating system’s scheduling constraints.

  • Shared data: Callback and main-thread access to mutable state may require a lock or thread-safe queue.
  • Missed events: Very short or high-frequency pulses can be missed when software, kernel, or input filtering cannot service them quickly enough.
  • Level verification: A callback may read the pin again after an edge to confirm its current level.
  • Shutdown behavior: Event detection should be removed and outputs made safe before cleanup.
  • Suitable uses: Buttons, limit switches, encoders at moderate speed, motion sensors, and alarm contacts benefit from edge detection.

IV. DC Motor Drive — Bidirectional Power Switching

A motor driver accepts low-power logic commands and switches an external motor supply, protecting GPIO pins from high current and inductive voltage transients.

A. Motor control using H-bridge and motor driver ICs

An H-bridge uses four switching elements to reverse the voltage across a DC motor, enabling forward motion, reverse motion, braking, and coasting.

  • Direction control: For inputs IN1 and IN2, typical states are:
    • 1,0: current flows in one direction.
    • 0,1: current flows in the opposite direction.
    • 0,0: outputs are disabled or LOW, commonly producing coast.
    • 1,1: commonly produces braking, although behavior depends on the driver.
  • Speed control: PWM applied to an enable or input pin changes average motor voltage approximately as:
TEXT
V_avg ≈ D × V_s

Here, V_avg is average motor voltage, D is duty cycle from 0 to 1, and V_s is motor supply voltage.

  • Driver examples: L293D and L298N are traditional bipolar drivers with noticeable voltage loss; MOSFET-based devices such as TB6612FNG are generally more efficient.
  • Current rating: The driver must tolerate the motor’s stall current, which can be several times its no-load current.
  • Inductive protection: Integrated or external flyback diodes provide a path for current when switching stops.
  • Power arrangement: Motor supply and logic supply may differ, but their ground reference normally must be common.

B. Operating constraints

Correct driver selection is determined by electrical and thermal requirements, not only nominal motor voltage.

  • Shoot-through prevention: Turning on both switches in one bridge leg simultaneously can short the supply; driver dead time prevents this condition.
  • Supply noise: Bulk capacitors near the driver and ceramic decoupling near IC supply pins reduce resets and interference.
  • Thermal loss: Driver dissipation is approximately P = VI; a 1 V drop at 1 A produces 1 W of heat.
  • Direction reversal: Duty cycle should be reduced before reversing to limit current and mechanical shock.
  • Feedback gap: Open-loop PWM does not guarantee speed; encoders and a controller such as PID are required for regulated motion.

V. Positioning Motors — Controlled Angular and Incremental Motion

Servos target an angular position from pulse timing, while stepper motors move through discrete electrical phase sequences.

A. Servo and stepper motor control with acceleration profiles

Acceleration profiles vary velocity gradually so that motors do not experience an instantaneous change in demanded speed.

  1. Servo control

    • Command pulse: Hobby servos commonly accept a repeated pulse near 50 Hz; pulse widths around 1–2 ms often span much of the travel, but exact limits are model-specific.
    • Position mapping: A controller maps desired angle θ to calibrated pulse width rather than assuming universal endpoints.
    • Power requirement: Servos can draw large transient currents and should normally use a separate regulated supply with common ground.
    • Motion profile: Intermediate commands can follow a trapezoidal or S-curve trajectory instead of jumping directly to the final angle.
  2. Stepper control

    • Discrete motion: For a motor with N full steps per revolution, full-step angle is:
TEXT
α = 360° / N

Here, α is step angle in degrees and N is steps per revolution. For N = 200, α = 1.8°.

  • Driver interface: Devices such as A4988, DRV8825, and TMC2209 commonly accept STEP and DIR signals while regulating winding current.
  • Microstepping: Dividing each full step improves smoothness and nominal resolution, but does not proportionally increase absolute positional accuracy.
  • Trapezoidal profile: Step frequency rises at constant acceleration, remains near maximum velocity, and then falls before the destination.
  • S-curve profile: Acceleration changes gradually by limiting jerk, where jerk is j = da/dt; this reduces vibration and mechanical stress.
  • Missed-step risk: Excess acceleration or load torque can make an open-loop stepper lose synchronization without software detecting it.

B. Calibration and safety

Motion systems require limits that reflect both mechanical travel and electrical capacity.

  • Current limiting: A stepper driver’s reference setting must match motor phase current and cooling capability.
  • Homing: A limit switch establishes a repeatable reference because open-loop step counts do not provide an absolute position after startup.
  • Profile planning: Maximum velocity, acceleration, and jerk must remain within available motor torque.
  • Emergency behavior: Disabling a driver removes active torque; vertical mechanisms may therefore require a brake or controlled stop.
  • Servo limits: Commands beyond physical travel can stall the servo, causing overheating and high current.

VI. DMA-Based Timing — Deterministic Waveform Generation

Direct memory access (DMA) transfers prepared data between memory and peripherals with limited CPU intervention, enabling more stable GPIO timing than Python-controlled loops.

A. Real-time GPIO control using DMA

DMA-based GPIO systems construct timed waveforms in memory and let hardware-paced transfers apply pin changes at scheduled intervals.

  • Timing principle: A peripheral clock or pacing source triggers DMA operations, avoiding one Python function call for every transition.
  • Waveform representation: Each entry specifies pins to set, pins to clear, and a delay or sampling interval.
  • Typical tools: The pigpio daemon and compatible interfaces can generate servo pulses, PWM, timed pulse trains, and serial waveforms using lower-level hardware mechanisms.
  • Precision benefit: Timing jitter is usually much lower than with sleep() loops because CPU scheduling does not determine every edge.
  • Parallel control: Bit masks can update several GPIO pins together, supporting synchronized outputs.
  • Finite resources: DMA channels, control blocks, memory, and peripheral pacing hardware are shared system resources.

B. Real-time scope and limitations

DMA improves waveform determinism, but it does not turn an entire Linux application into a hard real-time system.

  • Precomputed behavior: DMA excels when transitions can be prepared before execution; immediate control decisions still depend on software latency.
  • Safety architecture: Motor shutdown and overcurrent protection should use driver hardware or dedicated controllers where delayed response is unacceptable.
  • Platform dependence: Peripheral addresses, DMA architecture, kernel interfaces, and GPIO hardware differ among Raspberry Pi generations.
  • Best applications: Stable servo pulses, synchronized step pulses, LED protocols, waveform playback, and accurately timed sampling.
  • Alternative controllers: Microcontrollers or dedicated motion-control ICs are preferable when strict deadlines, high step rates, or certified fail-safe behavior are required.