ATMEGA328P and ATMEGA328PB are different in programming
2025-07-22
I got this error is i change "MODEL=atmega328p" to "MODEL=atmega328pb" in my makefile. Github copilot said the error occurs because the ATmega328PB has two TWI (I2C) modules, and its I/O register naming is different from the ATmega328P. Specifically, the ATmega328PB splits some port definitions (like DDRC, PORTC) into two sets (for PORTC and PORTD, etc.), and some macros or register names may not be defined as expected.
In file included from ssd1306/TWI.h:19,
from ssd1306/TWI.c:1:
ssd1306/TWI.c: In function 'TWI_Setup':
ssd1306/IO_Macros.h:26:42: error: 'DDRC' undeclared (first use in this function); did you mean 'DDR'?
26 | #define PinMode( x, y) ( y ? _SET(DDR, x) : _CLEAR(DDR, x) )
I need to change IO_Macros.h from
#ifndef IO_MACROS_H_INCLUDED
#define IO_MACROS_H_INCLUDED
/*
||
|| Filename: IO_Macros.h
|| Title: IO manipulation macros
|| Author: Efthymios Koktsidis
|| Email: [email protected]
|| Compiler: AVR-GCC
|| Description: This library contains macros for
|| easy port manipulation (similar
|| to Arduino).
||
|| Demo:
|| 1. #define LED A, 0 || 6. PinModeToggle(BUTTON);
|| 2. #define BUTTON A, 1 || 7. DigitalWrite(LED, LOW);
|| 3. || 8. DigitalWrite(LED, HIGH);
|| 4. PinMode(BUTTON, OUTPUT); || 9. DigitalLevelToggle(LED);
|| 5. PinMode(LED, OUTPUT); ||10. int a = DigitalRead(BUTTON);
||
*/
#include <avr/io.h>
//----- I/O Macros -----
//Macros to edit PORT, DDR and PIN
#define PinMode( x, y) ( y ? _SET(DDR, x) : _CLEAR(DDR, x) )
#define DigitalWrite( x, y) ( y ? _SET(PORT, x) : _CLEAR(PORT, x) )
#define DigitalRead( x) ( _GET(PIN, x) )
#define PinModeToggle( x) ( _TOGGLE(DDR, x) )
#define DigitalLevelToggle( x) ( _TOGGLE(PORT, x) )
//General use bit manipulating commands
#define BitSet( x, y) ( x |= (1UL<<y) )
#define BitClear( x, y) ( x &= (~(1UL<<y)) )
#define BitToggle( x, y) ( x ^= (1UL<<y) )
#define BitCheck( x, y) ( x & (1UL<<y) ? 1 : 0 )
//Access PORT, DDR and PIN
#define PORT( port) (_PORT( port))
#define DDR( port) (_DDR( port))
#define PIN( port) (_PIN( port))
#define _PORT( port) (PORT## port)
#define _DDR( port) (DDR## port)
#define _PIN( port) (PIN## port)
#define _SET( type, port, bit) ( BitSet( (type##port), bit) )
#define _CLEAR( type, port, bit) ( BitClear( (type##port), bit) )
#define _TOGGLE(type, port, bit) ( BitToggle( (type##port), bit) )
#define _GET( type, port, bit) ( BitCheck( (type##port), bit) )
//Definitions
#define Input 0
#define Output !Input
#define Low 0
#define High !Low
#define False 0
#define True !False
//------------------
#endif
to
#ifndef IO_MACROS_H_INCLUDED
#define IO_MACROS_H_INCLUDED
/*
||
|| Filename: IO_Macros.h
|| Title: IO manipulation macros
|| Author: Efthymios Koktsidis
|| Email: [email protected]
|| Compiler: AVR-GCC
|| Description: This library contains macros for
|| easy port manipulation (similar
|| to Arduino).
||
|| Demo:
|| 1. #define LED A, 0 || 6. PinModeToggle(BUTTON);
|| 2. #define BUTTON A, 1 || 7. DigitalWrite(LED, LOW);
|| 3. || 8. DigitalWrite(LED, HIGH);
|| 4. PinMode(BUTTON, OUTPUT); || 9. DigitalLevelToggle(LED);
|| 5. PinMode(LED, OUTPUT); ||10. int a = DigitalRead(BUTTON);
||
*/
#include <avr/io.h>
//----- I/O Macros -----
//Macros to edit PORT, DDR and PIN
// Usage: PinMode(C, 4, Output); // Set PC4 as output
#define PinMode(port, bit, mode) ((mode) ? BitSet(DDR##port, bit) : BitClear(DDR##port, bit))
#define DigitalWrite(port, bit, level) ((level) ? BitSet(PORT##port, bit) : BitClear(PORT##port, bit))
#define DigitalRead(port, bit) (BitCheck(PIN##port, bit))
#define PinModeToggle(port, bit) (BitToggle(DDR##port, bit))
#define DigitalLevelToggle(port, bit) (BitToggle(PORT##port, bit))
//General use bit manipulating commands
#define BitSet(x, y) ( x |= (1UL<<(y)) )
#define BitClear(x, y) ( x &= (~(1UL<<(y))) )
#define BitToggle(x, y) ( x ^= (1UL<<(y)) )
#define BitCheck(x, y) ( ((x) & (1UL<<(y))) ? 1 : 0 )
//Definitions
#define Input 0
#define Output 1
#define Low 0
#define High 1
#define False 0
#define True 1
//------------------
#endif