A joystick-controlled 4-wheel robot car written in bare-metal C for the ATmega328P microcontroller — no Arduino libraries, pure register-level programming.
| File | Description |
|---|---|
Application.c |
Main loop — ties all modules together |
GPIO.c / .h |
GPIO driver — pin/port read & write |
ADC.c / .h |
ADC driver — analog reads & voltage conversion |
Motordriver.c / .h |
L298N H-bridge motor control |
Joystick.c / .h |
XY analog joystick input |
Battery.c / .h |
LiPo battery voltage monitor |
Types.h |
Shared typedefs and bit manipulation macros |
- MCU: ATmega328P (16 MHz)
- Motor Driver: L298N dual H-bridge
- Input: Analog XY joystick (ADC)
- Battery: 2-cell LiPo with resistor voltage divider (100kΩ / 10kΩ)
| Pin | Function |
|---|---|
| PC0 (ADC0) | Battery voltage monitor |
| PC1 (ADC1) | Joystick X-axis |
| PC2 (ADC2) | Joystick Y-axis |
| PB0 | Low battery LED |
| PD4 / PD5 | L298N IN1 / IN2 (left motors) |
| PD6 / PD7 | L298N IN3 / IN4 (right motors) |
- ADC initialized at startup with AVCC reference and DIV_128 prescaler (125 kHz ADC clock)
- Every loop iteration checks battery voltage first — if below 6.6V, motors stop and LED turns on
- Joystick X/Y values are read via ADC and mapped to 5 motor states: FORWARD, BACKWARD, LEFT, RIGHT, STOP
- Motor states are sent to the L298N via 4 GPIO output pins
The project uses a layered HAL (Hardware Abstraction Layer) pattern:
_Private.hfiles contain raw register addresses — internal use only_Interface.hfiles expose the public API.cfiles contain the implementation- Upper layers never access hardware registers directly