Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for ATmega8 #384

Merged
merged 8 commits into from
Feb 23, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,10 @@ jobs:
name: atmega1284p
spec: atmega1284p
crate: atmega-hal
- type: mcu
name: atmega8
spec: atmega8
crate: atmega-hal
- type: mcu
name: attiny85
spec: attiny85
Expand Down
8 changes: 5 additions & 3 deletions avr-hal-generic/src/adc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -214,7 +214,7 @@ macro_rules! impl_adc {
pins: {
$(
$(#[$pin_attr:meta])*
$pin:ty: ($pin_channel:expr, $didr:ident::$didr_method:ident),
$pin:ty: ($pin_channel:expr$(, $didr:ident::$didr_method:ident)?),
)+
},
$(channels: {
Expand Down Expand Up @@ -263,8 +263,9 @@ macro_rules! impl_adc {
fn raw_enable_channel(&mut self, channel: Self::Channel) {
match channel {
$(
$(#[$pin_attr])*
x if x == $pin_channel => self.$didr.modify(|_, w| w.$didr_method().set_bit()),
x if x == $pin_channel => {
$(self.$didr.modify(|_, w| w.$didr_method().set_bit());)?
}
)+
_ => unreachable!(),
}
Expand Down Expand Up @@ -304,3 +305,4 @@ macro_rules! impl_adc {
)*)?
};
}

62 changes: 62 additions & 0 deletions avr-hal-generic/src/eeprom.rs
Original file line number Diff line number Diff line change
Expand Up @@ -236,6 +236,68 @@ macro_rules! impl_eeprom_common {
};
}

#[macro_export]
macro_rules! impl_eeprom_atmega_old {
(
hal: $HAL:ty,
peripheral: $EEPROM:ty,
capacity: $capacity:literal,
addr_width: $addrwidth:ty,
set_address: |$periph_var:ident, $address:ident| $set_address:block,
) => {
mod atmega_helper {
#[inline]
pub unsafe fn wait_read(regs: &$EEPROM) {
//Wait for completion of previous write.
while regs.eecr.read().eewe().bit_is_set() {}
}

#[inline]
pub unsafe fn set_address(regs: &$EEPROM, address: u16) {
wait_read(regs);
let $periph_var = regs;
let $address = address;
$set_address
}
}

impl $crate::eeprom::EepromOps<$HAL> for $EEPROM {
const CAPACITY: u16 = $capacity;


fn raw_read_byte(&self, address: u16) -> u8 {
unsafe {
atmega_helper::set_address(&self, address);
}
self.eecr.write(|w| w.eere().set_bit());
self.eedr.read().bits()
}

fn raw_write_byte(&mut self, address: u16, data: u8) {
unsafe {
atmega_helper::set_address(&self, address);
}

//Start EEPROM read operation
self.eedr.write(|w| unsafe {
w.bits(data)
});

self.eecr.write(|w|
w
.eemwe().set_bit()
.eewe().clear_bit());

self.eecr.write(|w| w.eewe().set_bit());
}

fn raw_erase_byte(&mut self, address: u16) {
self.raw_write_byte(address, 0);
}
}
};
}

#[macro_export]
macro_rules! impl_eeprom_atmega {
(
Expand Down
13 changes: 6 additions & 7 deletions avr-hal-generic/src/wdt.rs
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,7 @@ macro_rules! impl_wdt {
hal: $HAL:ty,
peripheral: $WDT:ty,
mcusr: $MCUSR:ty,
wdtcsr_name: $wdtcsr:ident,
timeout: |$to:ident, $w:ident| $to_match:expr,
) => {
impl $crate::wdt::WdtOps<$HAL> for $WDT {
Expand All @@ -111,10 +112,9 @@ macro_rules! impl_wdt {
// Reset the watchdog timer.
self.raw_feed();
// Enable watchdog configuration mode.
self.wdtcsr
.modify(|_, w| w.wdce().set_bit().wde().set_bit());
self.$wdtcsr.modify(|_, w| w.wdce().set_bit().wde().set_bit());
// Enable watchdog and set interval.
self.wdtcsr.write(|w| {
self.$wdtcsr.write(|w| {
let $to = timeout;
let $w = w;
($to_match).wde().set_bit().wdce().clear_bit()
Expand Down Expand Up @@ -142,12 +142,11 @@ macro_rules! impl_wdt {
// Reset the watchdog timer.
self.raw_feed();
// Enable watchdog configuration mode.
self.wdtcsr
.modify(|_, w| w.wdce().set_bit().wde().set_bit());
self.$wdtcsr.modify(|_, w| w.wdce().set_bit().wde().set_bit());
// Disable watchdog.
self.wdtcsr.reset();
self.$wdtcsr.reset();
})
}
}
};
}
}
31 changes: 31 additions & 0 deletions avr-specs/avr-atmega8.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
{
"arch": "avr",
"cpu": "atmega8",
"data-layout": "e-P1-p:16:8-i8:8-i16:8-i32:8-i64:8-f32:8-f64:8-n8-a:8",
"env": "",
"executables": true,
"linker": "avr-gcc",
"linker-flavor": "gcc",
"linker-is-gnu": true,
"llvm-target": "avr-unknown-unknown",
"os": "unknown",
"position-independent-executables": false,
"exe-suffix": ".elf",
"eh-frame-header": false,
"pre-link-args": {
"gcc": [
"-Os",
"-mmcu=atmega8"
]
},
"late-link-args": {
"gcc": [
"-lc",
"-lgcc"
]
},
"target-c-int-width": "16",
"target-endian": "little",
"target-pointer-width": "16",
"vendor": "unknown"
}
3 changes: 3 additions & 0 deletions avr-specs/sync-from-upstream.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,9 @@
"atmega1284p": {
"cpu": "atmega1284p",
},
"atmega8": {
"cpu": "atmega8",
},
"attiny85": {
"cpu": "attiny85",
},
Expand Down
1 change: 1 addition & 0 deletions mcu/atmega-hal/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ atmega32u4 = ["avr-device/atmega32u4", "device-selected"]
atmega2560 = ["avr-device/atmega2560", "device-selected"]
atmega1280 = ["avr-device/atmega1280", "device-selected"]
atmega1284p = ["avr-device/atmega1284p", "device-selected"]
atmega8 = ["avr-device/atmega8", "device-selected"]

critical-section-impl = ["avr-device/critical-section-impl"]

Expand Down
32 changes: 32 additions & 0 deletions mcu/atmega-hal/src/adc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,7 @@ pub mod channel {
feature = "atmega328pb",
feature = "atmega48p",
feature = "atmega1284p",
feature = "atmega8",
),
feature = "enable-extra-adc",
))]
Expand All @@ -88,6 +89,7 @@ pub mod channel {
feature = "atmega328pb",
feature = "atmega48p",
feature = "atmega1284p",
feature = "atmega8",
),
feature = "enable-extra-adc",
))]
Expand All @@ -101,6 +103,7 @@ pub mod channel {
feature = "atmega32u4",
feature = "atmega48p",
feature = "atmega1284p",
feature = "atmega8",
))]
pub struct Vbg;
#[cfg(any(
Expand All @@ -112,6 +115,7 @@ pub mod channel {
feature = "atmega32u4",
feature = "atmega48p",
feature = "atmega1284p",
feature = "atmega8",
))]
pub struct Gnd;
#[cfg(any(
Expand Down Expand Up @@ -252,3 +256,31 @@ avr_hal_generic::impl_adc! {
channel::Gnd: crate::pac::adc::admux::MUX_A::ADC_GND,
},
}

#[cfg(any(feature = "atmega8"))]
avr_hal_generic::impl_adc! {
hal: crate::Atmega,
peripheral: crate::pac::ADC,
settings: AdcSettings,
apply_settings: |peripheral, settings| { apply_settings(peripheral, settings) },
channel_id: crate::pac::adc::admux::MUX_A,
set_channel: |peripheral, id| {
peripheral.admux.modify(|_, w| w.mux().variant(id));
},
pins: {
port::PC0: (crate::pac::adc::admux::MUX_A::ADC0),
port::PC1: (crate::pac::adc::admux::MUX_A::ADC1),
port::PC2: (crate::pac::adc::admux::MUX_A::ADC2),
port::PC3: (crate::pac::adc::admux::MUX_A::ADC3),
port::PC4: (crate::pac::adc::admux::MUX_A::ADC4),
port::PC5: (crate::pac::adc::admux::MUX_A::ADC5),
},
channels: {
#[cfg(feature = "enable-extra-adc")]
channel::ADC6: crate::pac::adc::admux::MUX_A::ADC6,
#[cfg(feature = "enable-extra-adc")]
channel::ADC7: crate::pac::adc::admux::MUX_A::ADC7,
channel::Vbg: crate::pac::adc::admux::MUX_A::ADC_VBG,
channel::Gnd: crate::pac::adc::admux::MUX_A::ADC_GND,
},
}
13 changes: 13 additions & 0 deletions mcu/atmega-hal/src/eeprom.rs
Original file line number Diff line number Diff line change
Expand Up @@ -54,3 +54,16 @@ avr_hal_generic::impl_eeprom_atmega! {
peripheral.eear.write(|w| w.bits(address));
},
}

#[cfg(any(
feature = "atmega8"
))]
avr_hal_generic::impl_eeprom_atmega_old! {
hal: crate::Atmega,
peripheral: crate::pac::EEPROM,
capacity: 512,
addr_width: u16,
set_address: |peripheral, address| {
peripheral.eear.write(|w| w.bits(address));
},
}
4 changes: 2 additions & 2 deletions mcu/atmega-hal/src/i2c.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,15 +18,15 @@ avr_hal_generic::impl_i2c_twi! {
scl: port::PD0,
}

#[cfg(any(feature = "atmega328p", feature = "atmega168", feature = "atmega48p"))]
#[cfg(any(feature = "atmega328p", feature = "atmega168", feature = "atmega48p", feature = "atmega8"))]
pub type I2c<CLOCK> = avr_hal_generic::i2c::I2c<
crate::Atmega,
crate::pac::TWI,
port::Pin<port::mode::Input, port::PC4>,
port::Pin<port::mode::Input, port::PC5>,
CLOCK,
>;
#[cfg(any(feature = "atmega328p", feature = "atmega168", feature = "atmega48p"))]
#[cfg(any(feature = "atmega328p", feature = "atmega168", feature = "atmega48p", feature = "atmega8"))]
avr_hal_generic::impl_i2c_twi! {
hal: crate::Atmega,
peripheral: crate::pac::TWI,
Expand Down
15 changes: 15 additions & 0 deletions mcu/atmega-hal/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
#![cfg_attr(feature = "atmega2560", doc = "**ATmega2560**.")]
#![cfg_attr(feature = "atmega1280", doc = "**ATmega1280**.")]
#![cfg_attr(feature = "atmega1284p", doc = "**ATmega1284P**.")]
#![cfg_attr(feature = "atmega8", doc = "**ATmega8**.")]
//! This means that only items which are available for this MCU are visible. If you are using
//! a different chip, try building the documentation locally with:
//!
Expand All @@ -37,6 +38,7 @@ compile_error!(
* atmega1280
* atmega2560
* atmega1284p
* atmega8
"
);

Expand Down Expand Up @@ -64,6 +66,9 @@ pub use avr_device::atmega48p as pac;
/// Reexport of `atmega1284p` from `avr-device`
#[cfg(feature = "atmega1284p")]
pub use avr_device::atmega1284p as pac;
/// Reexport of `atmega8` from `avr-device`
#[cfg(feature = "atmega8")]
pub use avr_device::atmega8 as pac;

/// See [`avr_device::entry`](https://docs.rs/avr-device/latest/avr_device/attr.entry.html).
#[cfg(feature = "rt")]
Expand Down Expand Up @@ -158,3 +163,13 @@ macro_rules! pins {
)
};
}

#[cfg(any(feature = "atmega8"))]
#[macro_export]
macro_rules! pins {
($p:expr) => {
$crate::Pins::new(
$p.PORTB, $p.PORTC, $p.PORTD,
)
};
}
35 changes: 35 additions & 0 deletions mcu/atmega-hal/src/port.rs
Original file line number Diff line number Diff line change
Expand Up @@ -265,3 +265,38 @@ avr_hal_generic::impl_port_traditional! {
pd7: PD7 = (crate::pac::PORTD, PORTD, 7, portd, pind, ddrd),
}
}

#[cfg(any(feature = "atmega8"))]
avr_hal_generic::impl_port_traditional! {
enum Ports {
PORTB: (crate::pac::PORTB, portb, pinb, ddrb),
PORTC: (crate::pac::PORTC, portc, pinc, ddrc),
PORTD: (crate::pac::PORTD, portd, pind, ddrd),
}

pub struct Pins {
pb0: PB0 = (crate::pac::PORTB, PORTB, 0, portb, pinb, ddrb),
pb1: PB1 = (crate::pac::PORTB, PORTB, 1, portb, pinb, ddrb),
pb2: PB2 = (crate::pac::PORTB, PORTB, 2, portb, pinb, ddrb),
pb3: PB3 = (crate::pac::PORTB, PORTB, 3, portb, pinb, ddrb),
pb4: PB4 = (crate::pac::PORTB, PORTB, 4, portb, pinb, ddrb),
pb5: PB5 = (crate::pac::PORTB, PORTB, 5, portb, pinb, ddrb),
pb6: PB6 = (crate::pac::PORTB, PORTB, 6, portb, pinb, ddrb),
pb7: PB7 = (crate::pac::PORTB, PORTB, 7, portb, pinb, ddrb),
pc0: PC0 = (crate::pac::PORTC, PORTC, 0, portc, pinc, ddrc),
pc1: PC1 = (crate::pac::PORTC, PORTC, 1, portc, pinc, ddrc),
pc2: PC2 = (crate::pac::PORTC, PORTC, 2, portc, pinc, ddrc),
pc3: PC3 = (crate::pac::PORTC, PORTC, 3, portc, pinc, ddrc),
pc4: PC4 = (crate::pac::PORTC, PORTC, 4, portc, pinc, ddrc),
pc5: PC5 = (crate::pac::PORTC, PORTC, 5, portc, pinc, ddrc),
pc6: PC6 = (crate::pac::PORTC, PORTC, 6, portc, pinc, ddrc),
pd0: PD0 = (crate::pac::PORTD, PORTD, 0, portd, pind, ddrd),
pd1: PD1 = (crate::pac::PORTD, PORTD, 1, portd, pind, ddrd),
pd2: PD2 = (crate::pac::PORTD, PORTD, 2, portd, pind, ddrd),
pd3: PD3 = (crate::pac::PORTD, PORTD, 3, portd, pind, ddrd),
pd4: PD4 = (crate::pac::PORTD, PORTD, 4, portd, pind, ddrd),
pd5: PD5 = (crate::pac::PORTD, PORTD, 5, portd, pind, ddrd),
pd6: PD6 = (crate::pac::PORTD, PORTD, 6, portd, pind, ddrd),
pd7: PD7 = (crate::pac::PORTD, PORTD, 7, portd, pind, ddrd),
}
}
Loading