90 lines
2.3 KiB
C
90 lines
2.3 KiB
C
#include <avr/io.h>
|
|
#include <util/delay.h>
|
|
#include <base.h>
|
|
#include <spi.h>
|
|
|
|
typedef struct RFM {
|
|
spi_t spi;
|
|
gpio_t irq;
|
|
gpio_t reset;
|
|
} rfm_t;
|
|
|
|
void rfm_initialize(rfm_t *rfm) {
|
|
spi_initialize(&rfm->spi);
|
|
|
|
spi_acquire(&rfm->spi);
|
|
spi_transfer_byte(&rfm->spi, 0x37 | _BV(7));
|
|
spi_transfer_byte(&rfm->spi, 0);
|
|
spi_release(&rfm->spi);
|
|
|
|
spi_acquire(&rfm->spi);
|
|
spi_transfer_byte(&rfm->spi, 0x38 | _BV(7));
|
|
spi_transfer_byte(&rfm->spi, 1);
|
|
spi_release(&rfm->spi);
|
|
}
|
|
|
|
void rfm_power_off(rfm_t *rfm) {
|
|
spi_acquire(&rfm->spi);
|
|
spi_transfer_byte(&rfm->spi, 0x11);
|
|
spi_transfer_byte(&rfm->spi, 0x00);
|
|
spi_release(&rfm->spi);
|
|
}
|
|
|
|
void rfm_send_data(rfm_t *rfm, uint8_t *data, size_t length) {
|
|
/* Go into standby mode */
|
|
spi_acquire(&rfm->spi);
|
|
spi_transfer_byte(&rfm->spi, 0x11);
|
|
spi_transfer_byte(&rfm->spi, 0x01);
|
|
spi_release(&rfm->spi);
|
|
|
|
/* Write data to FIFO */
|
|
spi_acquire(&rfm->spi);
|
|
spi_transfer_byte(&rfm->spi, 0x10);
|
|
for (size_t i = 0; i < length; i++) {
|
|
spi_transfer_byte(&rfm->spi, data[i]);
|
|
}
|
|
spi_release(&rfm->spi);
|
|
|
|
/* Go into transmit mode */
|
|
spi_acquire(&rfm->spi);
|
|
spi_transfer_byte(&rfm->spi, 0x11);
|
|
spi_transfer_byte(&rfm->spi, 0x03);
|
|
spi_release(&rfm->spi);
|
|
|
|
/* Return to standby mode */
|
|
spi_acquire(&rfm->spi);
|
|
spi_transfer_byte(&rfm->spi, 0x11);
|
|
spi_transfer_byte(&rfm->spi, 0x01);
|
|
spi_release(&rfm->spi);
|
|
}
|
|
|
|
int main(void) {
|
|
spi_t spi = (spi_t){
|
|
.clock = { .ddr = &DDRB, .port = &PORTB, .pin = &PINB, .addr = 1 },
|
|
.data_out = { .ddr = &DDRB, .port = &PORTB, .pin = &PINB, .addr = 2 },
|
|
.data_in = { .ddr = &DDRB, .port = &PORTB, .pin = &PINB, .addr = 3 },
|
|
.chip_select = { .ddr = &DDRB, .port = &PORTB, .pin = &PINB, .addr = 4 },
|
|
};
|
|
|
|
rfm_t rfm = (rfm_t){
|
|
.spi = spi,
|
|
.irq = { .ddr = &DDRE, .port = &PORTE, .pin = &PINE, .addr = 6 },
|
|
.reset = { .ddr = &DDRD, .port = &PORTD, .pin = &PIND, .addr = 4 },
|
|
};
|
|
|
|
gpio_t light = { .ddr = &DDRC, .port = &PORTC, .addr = 7 };
|
|
|
|
rfm_initialize(&rfm);
|
|
|
|
uint8_t count[1] = { 0 };
|
|
while(1) {
|
|
rfm_send_data(&rfm, count, 1);
|
|
count[0]++;
|
|
set_line(&light);
|
|
_delay_ms(50);
|
|
clear_line(&light);
|
|
_delay_ms(50);
|
|
}
|
|
return 0;
|
|
}
|