ATmega328 Origins - IDE
IntroductionArduino 11 did not natively support compiling code for the ATmega328P. The following changes had to be made:
avrdude Configuration FileCurrent avrdude builds do not include native support for the ATmega328P, and I couldn't find a config file, so the following addition has been built from the ATmega168 section and much datasheet reading. The config file is normally kept in #------------------------------------------------------------ # ATmega328 #------------------------------------------------------------ part id = "m328p"; desc = "ATMEGA328P"; has_debugwire = yes; flash_instr = 0xB6, 0x01, 0x11; eeprom_instr = 0xBD, 0xF2, 0xBD, 0xE1, 0xBB, 0xCF, 0xB4, 0x00, 0xBE, 0x01, 0xB6, 0x01, 0xBC, 0x00, 0xBB, 0xBF, 0x99, 0xF9, 0xBB, 0xAF; stk500_devcode = 0x86; # avr910_devcode = 0x; signature = 0x1e 0x95 0x0F; pagel = 0xd7; bs2 = 0xc2; chip_erase_delay = 9000; pgm_enable = "1 0 1 0 1 1 0 0 0 1 0 1 0 0 1 1", "x x x x x x x x x x x x x x x x"; chip_erase = "1 0 1 0 1 1 0 0 1 0 0 x x x x x", "x x x x x x x x x x x x x x x x"; timeout = 200; stabdelay = 100; cmdexedelay = 25; synchloops = 32; bytedelay = 0; pollindex = 3; pollvalue = 0x53; predelay = 1; postdelay = 1; pollmethod = 1; pp_controlstack = 0x0E, 0x1E, 0x0F, 0x1F, 0x2E, 0x3E, 0x2F, 0x3F, 0x4E, 0x5E, 0x4F, 0x5F, 0x6E, 0x7E, 0x6F, 0x7F, 0x66, 0x76, 0x67, 0x77, 0x6A, 0x7A, 0x6B, 0x7B, 0xBE, 0xFD, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00; hventerstabdelay = 100; progmodedelay = 0; latchcycles = 5; togglevtg = 1; poweroffdelay = 15; resetdelayms = 1; resetdelayus = 0; hvleavestabdelay = 15; resetdelay = 15; chiperasepulsewidth = 0; chiperasepolltimeout = 10; programfusepulsewidth = 0; programfusepolltimeout = 5; programlockpulsewidth = 0; programlockpolltimeout = 5; memory "eeprom" paged = no; page_size = 4; size = 1024; min_write_delay = 3600; max_write_delay = 3600; readback_p1 = 0xff; readback_p2 = 0xff; read = " 1 0 1 0 0 0 0 0", " 0 0 0 x x x a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; write = " 1 1 0 0 0 0 0 0", " 0 0 0 x x x a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_lo = " 1 1 0 0 0 0 0 1", " 0 0 0 0 0 0 0 0", " 0 0 0 0 0 0 a1 a0", " i i i i i i i i"; writepage = " 1 1 0 0 0 0 1 0", " 0 0 x x x x a9 a8", " a7 a6 a5 a4 a3 a2 0 0", " x x x x x x x x"; mode = 0x41; delay = 5; blocksize = 4; readsize = 256; ; memory "flash" paged = yes; size = 32768; page_size = 128; num_pages = 256; min_write_delay = 4500; max_write_delay = 4500; readback_p1 = 0xff; readback_p2 = 0xff; read_lo = " 0 0 1 0 0 0 0 0", " 0 0 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; read_hi = " 0 0 1 0 1 0 0 0", " 0 0 a13 a12 a11 a10 a9 a8", " a7 a6 a5 a4 a3 a2 a1 a0", " o o o o o o o o"; loadpage_lo = " 0 1 0 0 0 0 0 0", " 0 0 0 x x x x x", " x x a5 a4 a3 a2 a1 a0", " i i i i i i i i"; loadpage_hi = " 0 1 0 0 1 0 0 0", " 0 0 0 x x x x x", " x x a5 a4 a3 a2 a1 a0", " i i i i i i i i"; writepage = " 0 1 0 0 1 1 0 0", " 0 0 a13 a12 a11 a10 a9 a8", " a7 a6 x x x x x x", " x x x x x x x x"; mode = 0x41; delay = 6; blocksize = 128; readsize = 256; ; memory "lfuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0", "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 0 1 0 0 0 0 0", "x x x x x x x x i i i i i i i i"; ; memory "hfuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x o o o o o o o o"; write = "1 0 1 0 1 1 0 0 1 0 1 0 1 0 0 0", "x x x x x x x x i i i i i i i i"; ; memory "efuse" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 0 0 0 0 0 0 0 0 1 0 0 0", "x x x x x x x x x x x x x o o o"; write = "1 0 1 0 1 1 0 0 1 0 1 0 0 1 0 0", "x x x x x x x x x x x x x i i i"; ; memory "lock" size = 1; min_write_delay = 4500; max_write_delay = 4500; read = "0 1 0 1 1 0 0 0 0 0 0 0 0 0 0 0", "x x x x x x x x x x o o o o o o"; write = "1 0 1 0 1 1 0 0 1 1 1 x x x x x", "x x x x x x x x 1 1 i i i i i i"; ; memory "calibration" size = 1; read = "0 0 1 1 1 0 0 0 0 0 0 x x x x x", "0 0 0 0 0 0 0 0 o o o o o o o o"; ; memory "signature" size = 3; read = "0 0 1 1 0 0 0 0 0 0 0 x x x x x", "x x x x x x a1 a0 o o o o o o o o"; ; ; The boards.txt FileTo actually use the ATmega328, we need to give the Arduino IDE a build target in the form of a board. These are defined in diecimila_328.name=Arduino w/ ATmega328 diecimila_328.upload.protocol=stk500 diecimila_328.upload.maximum_size=30720 diecimila_328.upload.speed=19200 diecimila_328.bootloader.low_fuses=0xff diecimila_328.bootloader.high_fuses=0xdd diecimila_328.bootloader.extended_fuses=0x00 diecimila_328.bootloader.path=atmega328 diecimila_328.bootloader.file=ATmegaBOOT_328_diecimila.hex diecimila_328.bootloader.unlock_bits=0x3F diecimila_328.bootloader.lock_bits=0x0F diecimila_328.build.mcu=atmega328p diecimila_328.build.f_cpu=16000000L diecimila_328.build.core=arduino Update iom328p.hThis was likely the trickiest bit of all; without this modification, code will build and upload, but it just won't run. This discrepency was found by running the Arduino IDE's build script with all calls to avr-gcc suffixed with -E to generate the post-preproccessor code. This was done twice, once for an ATmega168 build and once for an ATmega328P build. The resulting files were then run through diff to discover any differences. Anyhow, modify #ifndef _AVR_IOM328P_H_ #define _AVR_IOM328P_H_ 1 #include /* Constants */ #define SPM_PAGESIZE 128 #define RAMEND 0x8FF /* Last On-Chip SRAM Location */ #define XRAMSIZE 0 #define XRAMEND (RAMEND + XRAMSIZE) #define E2END 0x3FF #define FLASHEND 0x7FFF /* Fuses */ #define FUSE_MEMORY_SIZE 3 /* Low Fuse Byte */ #define FUSE_CKSEL0 ~_BV(0) /* Select Clock Source */ #define FUSE_CKSEL1 ~_BV(1) /* Select Clock Source */ #define FUSE_CKSEL2 ~_BV(2) /* Select Clock Source */ #define FUSE_CKSEL3 ~_BV(3) /* Select Clock Source */ #define FUSE_SUT0 ~_BV(4) /* Select start-up time */ #define FUSE_SUT1 ~_BV(5) /* Select start-up time */ #define FUSE_CKOUT ~_BV(6) /* Clock output */ #define FUSE_CKDIV8 ~_BV(7) /* Divide clock by 8 */ #define LFUSE_DEFAULT (FUSE_CKSEL0 & FUSE_CKSEL2 & FUSE_CKSEL3 & FUSE_SUT0 & FUSE_CKDIV8) /* High Fuse Byte */ #define FUSE_BODLEVEL0 ~_BV(0) /* Brown-out Detector trigger level */ #define FUSE_BODLEVEL1 ~_BV(1) /* Brown-out Detector trigger level */ #define FUSE_BODLEVEL2 ~_BV(2) /* Brown-out Detector trigger level */ #define FUSE_EESAVE ~_BV(3) /* EEPROM memory is preserved through chip erase */ #define FUSE_WDTON ~_BV(4) /* Watchdog Timer Always On */ #define FUSE_SPIEN ~_BV(5) /* Enable Serial programming and Data Downloading */ #define FUSE_DWEN ~_BV(6) /* debugWIRE Enable */ #define FUSE_RSTDISBL ~_BV(7) /* External reset disable */ #define HFUSE_DEFAULT (FUSE_SPIEN) /* Extended Fuse Byte */ #define FUSE_BOOTRST ~_BV(0) #define FUSE_BOOTSZ0 ~_BV(1) #define FUSE_BOOTSZ1 ~_BV(2) #define EFUSE_DEFAULT (FUSE_BOOTSZ0 & FUSE_BOOTSZ1) /* Lock Bits */ #define __LOCK_BITS_EXIST #define __BOOT_LOCK_BITS_0_EXIST #define __BOOT_LOCK_BITS_1_EXIST #endif /* _AVR_IOM328P_H_ */ |