Skip to content
Snippets Groups Projects
Commit b467ed2e authored by Sergi Hernandez's avatar Sergi Hernandez
Browse files

Completed the compass module.

Changed the control and status interface of all the modules.
parent 248348b5
No related branches found
No related tags found
No related merge requests found
......@@ -17,6 +17,7 @@ void compass_start(void);
void compass_stop(void);
void compass_start_calibration(void);
void compass_stop_calibration(void);
void compass_set_num_samples(uint8_t num);
void compass_loop(void);
#endif
......@@ -26,7 +26,7 @@
#define VOLTAGE_ERROR 0x01
#define NO_ERROR 0x00
void do_write(uint8_t address,uint8_t length,uint8_t *data);
uint8_t do_write(uint8_t address,uint8_t length,uint8_t *data);
uint8_t do_read(uint8_t address,uint8_t length,uint8_t **data);
#endif
This diff is collapsed.
......@@ -5,7 +5,7 @@
// number of channels to convert
#define NUM_CH 8
// number of samples to average
#define MAX_NUM_SAMPLES 16
#define ADC_MAX_NUM_SAMPLES 16
// private variables
volatile uint8_t adc_sample_period_ms;
......@@ -14,7 +14,7 @@ volatile uint8_t adc_current_ch;
// channel data
volatile int16_t adc_data[NUM_CH];
// averaged channel data
volatile int16_t adc_ch_data[NUM_CH][MAX_NUM_SAMPLES];
volatile int16_t adc_ch_data[NUM_CH][ADC_MAX_NUM_SAMPLES];
volatile uint8_t adc_current_sample;
volatile uint8_t adc_num_samples;
volatile uint8_t adc_running;
......@@ -65,8 +65,8 @@ void adc_init(void)
adc_current_ch=0;
adc_current_sample=0;
adc_running=0;
adc_num_samples=MAX_NUM_SAMPLES;
ram_data[ADC_NUM_SAMPLES]=MAX_NUM_SAMPLES;
adc_num_samples=ADC_MAX_NUM_SAMPLES;
ram_data[ADC_NUM_SAMPLES]=ADC_MAX_NUM_SAMPLES;
adc_sample_period_ms=0x01;
ram_data[ADC_SAMPLE_PERIOD]=0x01;
adc_set_sample_period(adc_sample_period_ms);
......@@ -90,7 +90,7 @@ void adc_start(void)
// configure the timer prescaler and count value
adc_running=0x01;
adc_set_sample_period(adc_sample_period_ms);
ram_data[ADC_CONTROL]|=0x02;
ram_data[ADC_CONTROL]|=0x04;
}
void adc_stop(void)
......@@ -99,13 +99,13 @@ void adc_stop(void)
// disable the ADC
ADCSRA&=~(1<<ADEN);
adc_running=0x00;
ram_data[ADC_CONTROL]&=0xFD;
ram_data[ADC_CONTROL]&=0xFB;
}
void adc_set_num_samples(uint8_t num)
{
if(num>MAX_NUM_SAMPLES)
adc_num_samples=MAX_NUM_SAMPLES;
if(num>ADC_MAX_NUM_SAMPLES)
adc_num_samples=ADC_MAX_NUM_SAMPLES;
else
{
if(num<=0)
......@@ -115,6 +115,7 @@ void adc_set_num_samples(uint8_t num)
}
if(adc_current_sample>num)
adc_current_sample=0;
ram_data[ADC_NUM_SAMPLES]=num;
}
void adc_set_sample_period(uint8_t time_ms)
......@@ -139,6 +140,7 @@ void adc_set_sample_period(uint8_t time_ms)
break;
}
}
ram_data[ADC_SAMPLE_PERIOD]=time_ms;
}
void adc_loop(void)
......
......@@ -3,26 +3,31 @@
#include "mem.h"
#include "ports.h"
#define COMPASS_MAX_NUM_SAMPLES 16
typedef enum {idle,get_data,get_data_delay,read_data,start_cal,calibrating,calibration_delay,stop_cal} compass_states_t;
/* private variables */
volatile uint16_t compass_heading;
volatile uint16_t compass_heading_averaged;
volatile uint8_t compass_waiting_data;
volatile uint8_t compass_calibrated;
volatile uint8_t compass_calibrating;
volatile uint8_t compass_stopping;
volatile uint8_t compass_stopped;
volatile uint8_t compass_current_sample;
volatile uint8_t compass_num_samples;
volatile uint8_t compass_start_cal;
volatile uint8_t compass_stop_cal;
volatile uint8_t compass_stop_op;
volatile uint8_t compass_start_op;
volatile compass_states_t compass_state;
// time control variables
volatile uint8_t compass_delay_done;
/* private functions */
void compass_avrg(uint16_t heading)
{
static unsigned long int new_average,first_value;
static uint8_t num_data=0;
unsigned long int diff=0;
if(num_data==0)
if(compass_current_sample==0)
{
num_data=num_data+1;
compass_current_sample++;
first_value=(long int)heading;
}
else
......@@ -33,16 +38,17 @@ void compass_avrg(uint16_t heading)
else if(diff>5400)
diff=diff-3600;
new_average=new_average+diff;
num_data=num_data+1;
if(num_data==17)
compass_current_sample++;
if(compass_current_sample==compass_num_samples)
{
new_average=new_average/16;
new_average=new_average/(compass_num_samples-1);
new_average=new_average+first_value;
compass_heading_averaged=(uint16_t)new_average;
if(compass_heading_averaged>3600)
compass_heading_averaged=compass_heading_averaged-3600;
if(new_average>3600)
new_average-=3600;
ram_data[COMPASS_AVG_HEADING_VAL_L]=new_average%256;
ram_data[COMPASS_AVG_HEADING_VAL_H]=new_average/256;
new_average=0;
num_data=0;
compass_current_sample=0;
}
}
}
......@@ -73,14 +79,15 @@ ISR(TIMER0_COMP_vect)
void compass_init(void)
{
/* initialize private variables */
compass_calibrated=0x00;
compass_calibrating=0x00;
compass_stopped=0x01;
compass_stopping=0x00;
compass_waiting_data=0x00;
compass_heading=0;
compass_heading_averaged=0;
compass_start_cal=0;
compass_stop_cal=0;
compass_stop_op=0;
compass_start_op=0;
compass_delay_done=0x00;
compass_state=idle;
compass_current_sample=0;
compass_num_samples=COMPASS_MAX_NUM_SAMPLES;
ram_data[COMPASS_NUM_SAMPLES]=COMPASS_MAX_NUM_SAMPLES;
/* use timer 0 to control the operation delay */
TCCR0=(1<<WGM01);//campare mode, output disable, prescaler 0
......@@ -95,134 +102,151 @@ void compass_init(void)
void compass_start(void)
{
compass_stopping=0x00;
compass_stopped=0x00;
compass_waiting_data=0x00;
ram_data[COMPASS_CONTROL]|=0x04;
compass_stop_op=0;
compass_start_op=1;
ram_data[COMPASS_CONTROL]|=0x40;
}
void compass_stop(void)
{
compass_stopping=0x01;
compass_stop_op=1;
compass_start_op=0;
}
void compass_start_calibration(void)
{
compass_start_cal=1;
compass_stop_cal=0;
}
void compass_stop_calibration(void)
{
compass_start_cal=0;
compass_stop_cal=1;
}
void compass_loop(void)
void compass_set_num_samples(uint8_t num)
{
uint8_t cmd,heading[2];
if(compass_stopped==0x00)// compass is running
{
if(i2c_get_state()==I2C_IDLE)// the last I2C command has terminated
{
if(compass_waiting_data==0x01)// we are waiting heading data
{
if(compass_is_delay_done()==0x01)// the required time from the command has elapsed
{
i2c_get_data(2,heading);
compass_heading=heading[1]+(heading[0]<<8);
compass_avrg(compass_heading);
compass_waiting_data=0x00;
toggle_led();
}
}
else
{
if(compass_stopping==0x00)
{
cmd=COMPASS_HEADING;
i2c_master_send(COMPASS_ADDR,1,&cmd);
compass_waiting_data=0x01;
compass_start_time_delay(10);
}
else
{
compass_stopping=0x00;
compass_stopped=0x00;
ram_data[COMPASS_CONTROL]&=0xFB;
}
}
}
}
if(num>COMPASS_MAX_NUM_SAMPLES)
compass_num_samples=COMPASS_MAX_NUM_SAMPLES;
else if(num<=2)
compass_num_samples=2;
else
compass_num_samples=num;
ram_data[COMPASS_NUM_SAMPLES]=compass_num_samples;
}
/*void compass_periodic_call(void)
void compass_loop(void)
{
uint8_t cmd,heading[2];
static int count=0;
unsigned short int compass_heading;
static compass_states_t prev_state=idle;
if(i2cGetState()==I2C_IDLE)
switch(compass_state)
{
if(compass_waiting_data)
{
if(compass_calibrate)
{
compass_calibrating=TRUE;
compass_calibrate=FALSE;
count=100;
}
else if(compass_calibrating)
{
if(count>0)
count--;
else
{
cmd=COMPASS_START_CAL;
i2cMasterSend(COMPASS_ADDR, 1, &cmd);
compass_waiting_data=FALSE;
}
}
else
{
if(count>0)
count--;
else
{
i2c_get_data(2,heading);
compass_heading=heading[1]+(heading[0]<<8);
compass_avrg(compass_heading);
cmd=COMPASS_HEADING;
i2cMasterSend(COMPASS_ADDR, 1, &cmd);
compass_waiting_data=FALSE;
count = 10;
}
}
}
else
{
if(compass_calibrating)
{
count++;
if(count==30000)
{
cmd=COMPASS_STOP_CAL;
i2cMasterSend(COMPASS_ADDR, 1, &cmd);
compass_waiting_data=TRUE;
compass_calibrate=FALSE;
compass_calibrating=FALSE;
count = 100;
}
}
else
{
if(count>0)
count--;
else
{
i2cMasterReceive(COMPASS_ADDR,2);
compass_waiting_data=TRUE;
}
}
}
case idle: if(compass_start_op==1)
{
compass_state=get_data;
compass_start_op=0;
}
else
{
if(compass_start_cal==1)
{
compass_start_cal=0;
compass_state=start_cal;
prev_state=idle;
}
else
compass_state=idle;
}
break;
case get_data: if(i2c_get_state()==I2C_IDLE)
{
cmd=COMPASS_HEADING;
i2c_master_send(COMPASS_ADDR,1,&cmd);
compass_start_time_delay(10);
compass_state=get_data_delay;
}
else
compass_state=get_data;
break;
case get_data_delay: if(compass_is_delay_done()==1)
{
if(i2c_get_state()==I2C_IDLE)
{
i2c_master_receive(COMPASS_ADDR,2);
compass_state=read_data;
}
else
compass_state=get_data_delay;
}
else
compass_state=get_data_delay;
break;
case read_data: if(i2c_get_state()==I2C_IDLE)
{
i2c_get_data(2,heading);
compass_heading=heading[1]+(heading[0]<<8);
ram_data[COMPASS_HEADING_VAL_L]=heading[1];
ram_data[COMPASS_HEADING_VAL_H]=heading[0];
compass_avrg(compass_heading);
if(compass_stop_op==1)
{
compass_stop_op=0;
compass_state=idle;
ram_data[COMPASS_CONTROL]&=0xBF;
}
else
{
if(compass_start_cal==1)
{
compass_start_cal=0;
compass_state=start_cal;
prev_state=get_data;
}
else
compass_state=get_data;
}
}
else
compass_state=read_data;
break;
case start_cal: if(i2c_get_state()==I2C_IDLE)
{
cmd=COMPASS_START_CAL;
i2c_master_send(COMPASS_ADDR,1,&cmd);
ram_data[COMPASS_CONTROL]|=0x80;
compass_state=calibrating;
}
else
compass_state=start_cal;
break;
case calibrating: if(compass_stop_cal==1)
{
compass_state=stop_cal;
compass_stop_cal=0;
}
else
compass_state=calibrating;
break;
case stop_cal: if(i2c_get_state()==I2C_IDLE)
{
cmd=COMPASS_STOP_CAL;
i2c_master_send(COMPASS_ADDR,1,&cmd);
compass_start_time_delay(20);
compass_state=calibration_delay;
}
else
compass_state=stop_cal;
break;
case calibration_delay: if(compass_is_delay_done()==1)
{
compass_state=prev_state;
ram_data[COMPASS_CONTROL]&=0x7F;
}
else
compass_state=calibration_delay;
break;
}
}*/
}
......@@ -40,6 +40,7 @@ void dac_start(void)
TCCR1B&=0xF8;
TCCR1B|=DAC_PRESCALE_MASK;
dac_running=0x01;
ram_data[DAC_CONTROL]|=0x10;
}
void dac_stop(void)
......@@ -47,6 +48,7 @@ void dac_stop(void)
/* set the prescaler to 0 (no clock source) */
TCCR1B&=0xF8;
dac_running=0x00;
ram_data[DAC_CONTROL]&=0xEF;
}
void dac_enable_channel(dac_ch_t ch)
......@@ -54,8 +56,10 @@ void dac_enable_channel(dac_ch_t ch)
switch(ch)
{
case dac0: TCCR1A|=(1<<COMA1);
ram_data[DAC_CONTROL]|=0x40;
break;
case dac1: TCCR1A|=(1<<COMB1);
ram_data[DAC_CONTROL]|=0x80;
break;
}
}
......@@ -65,8 +69,10 @@ void dac_disable_channel(dac_ch_t ch)
switch(ch)
{
case dac0: TCCR1A&=~(1<<COMA1);
ram_data[DAC_CONTROL]&=0xBF;
break;
case dac1: TCCR1A&=~(1<<COMB1);
ram_data[DAC_CONTROL]|=0x7F;
break;
}
}
......@@ -83,9 +89,13 @@ void dac_set_voltage(dac_ch_t ch,uint16_t voltage)
{
case dac0: OCR1AH=(compare_value>>8)&0xFF;
OCR1AL=(compare_value)&0xFF;
ram_data[DAC_CH0_VOLTAGE_L]=voltage%256;
ram_data[DAC_CH0_VOLTAGE_H]=voltage/256;
break;
case dac1: OCR1BH=(compare_value>>8)&0xFF;
OCR1BL=(compare_value)&0xFF;
ram_data[DAC_CH1_VOLTAGE_L]=voltage%256;
ram_data[DAC_CH1_VOLTAGE_H]=voltage/256;
break;
}
}
......
......@@ -5,8 +5,9 @@
#include "adc.h"
#include "pwm.h"
#include "dac.h"
#include "compass.h"
void do_write(uint8_t address,uint8_t length,uint8_t *data)
uint8_t do_write(uint8_t address,uint8_t length,uint8_t *data)
{
uint8_t i,num=0;
uint8_t low_byte=0x00;
......@@ -41,9 +42,9 @@ void do_write(uint8_t address,uint8_t length,uint8_t *data)
/* ADC interface */
else if(i==ADC_CONTROL)
{
if(data[num]==0x00)
if(data[num]&0x01)
adc_stop();
else
else if(data[num]&0x02)
adc_start();
}
else if(i==ADC_NUM_SAMPLES)
......@@ -55,23 +56,26 @@ void do_write(uint8_t address,uint8_t length,uint8_t *data)
{
if(data[num]&0x01)
pwm_start();
else
else if(data[num]&0x02)
pwm_stop();
if(data[num]&0x02)
}
else if(i==PWM_ENABLE)
{
if(data[num]&0x01)
pwm_enable_ch(pwm0);
else
else if(data[num]&0x10)
pwm_disable_ch(pwm0);
if(data[num]&0x04)
if(data[num]&0x02)
pwm_enable_ch(pwm1);
else
else if(data[num]&0x20)
pwm_disable_ch(pwm1);
if(data[num]&0x08)
if(data[num]&0x04)
pwm_enable_ch(pwm2);
else
else if(data[num]&0x40);
pwm_disable_ch(pwm2);
if(data[num]&0x10)
if(data[num]&0x08)
pwm_enable_ch(pwm3);
else
else if(data[num]&0x80)
pwm_disable_ch(pwm3);
}
else if(i==PWM_FREQ_L)
......@@ -85,15 +89,18 @@ void do_write(uint8_t address,uint8_t length,uint8_t *data)
{
if(data[num]&0x01)
dac_start();
else
else if(data[num]&0x02)
dac_stop();
if(data[num]&0x02)
}
else if(i==DAC_ENABLE)
{
if(data[num]&0x01)
dac_enable_channel(dac0);
else
else if(data[num]&0x04);
dac_disable_channel(dac0);
if(data[num]&0x04)
if(data[num]&0x02)
dac_enable_channel(dac1);
else
else if(data[num]&0x08)
dac_disable_channel(dac1);
}
else if(i==DAC_CH0_VOLTAGE_L)
......@@ -104,8 +111,24 @@ void do_write(uint8_t address,uint8_t length,uint8_t *data)
low_byte=data[num];
else if(i==DAC_CH1_VOLTAGE_H)
dac_set_voltage(dac1,low_byte+data[num]*256);
/* compass interface */
else if(i==COMPASS_CONTROL)
{
if(data[num]&0x01)
compass_start();
else if(data[num]&0x02)
compass_stop();
else if(data[num]&0x04)
compass_start_calibration();
else if(data[num]&0x08)
compass_stop_calibration();
}
else if(i==COMPASS_NUM_SAMPLES)
compass_set_num_samples(data[num]);
num++;
}
return 0x01;
}
uint8_t do_read(uint8_t address,uint8_t length,uint8_t **data)
......
......@@ -320,11 +320,8 @@ void dyn_slave_diff_loop(void)
else
dyn_slave_diff_send_status(dyn_slave_diff_error|INSTRUCTION_ERROR,0x00,0x00000000);
break;
case INST_WRITE: if(ram_write(dyn_slave_diff_get_address(),dyn_slave_diff_get_write_length(),dyn_slave_diff_get_write_data()))
{
do_write(dyn_slave_diff_get_address(),dyn_slave_diff_get_write_length(),dyn_slave_diff_get_write_data());
case INST_WRITE: if(do_write(dyn_slave_diff_get_address(),dyn_slave_diff_get_write_length(),dyn_slave_diff_get_write_data()))
dyn_slave_diff_send_status(dyn_slave_diff_error|NO_ERROR,0x00,0x00000000);
}
else
dyn_slave_diff_send_status(dyn_slave_diff_error|INSTRUCTION_ERROR,0x00,0x00000000);
break;
......@@ -338,11 +335,8 @@ void dyn_slave_diff_loop(void)
break;
case INST_ACTION: if(dyn_slave_diff_reg_pending)
{
if(ram_write(dyn_slave_diff_tmp_address,dyn_slave_diff_tmp_length,dyn_slave_diff_tmp_data))
{
do_write(dyn_slave_diff_tmp_address,dyn_slave_diff_tmp_length,dyn_slave_diff_tmp_data);
if(do_write(dyn_slave_diff_tmp_address,dyn_slave_diff_tmp_length,dyn_slave_diff_tmp_data))
dyn_slave_diff_send_status(dyn_slave_diff_error|NO_ERROR,0x00,0x00000000);
}
}
else
dyn_slave_diff_send_status(dyn_slave_diff_error|INSTRUCTION_ERROR,0x00,0x00000000);
......@@ -368,10 +362,7 @@ void dyn_slave_diff_loop(void)
}
break;
case INST_SYNC_WRITE: if(dyn_slave_diff_sync_write_id_present(&data))
{
if(ram_write(dyn_slave_diff_get_address(),dyn_slave_diff_get_read_length(),data))
do_write(dyn_slave_diff_get_address(),dyn_slave_diff_get_read_length(),data);
}
do_write(dyn_slave_diff_get_address(),dyn_slave_diff_get_read_length(),data);
break;
case INST_BULK_READ: dyn_slave_diff_bulk_read_previous=dyn_slave_diff_bulk_read_id_present(&dyn_slave_diff_tmp_address,&dyn_slave_diff_tmp_length);
if(dyn_slave_diff_bulk_read_previous!=0xFF)
......@@ -388,10 +379,7 @@ void dyn_slave_diff_loop(void)
}
break;
case INST_BULK_WRITE: if(dyn_slave_diff_bulk_write_id_present(&dyn_slave_diff_tmp_address,&dyn_slave_diff_tmp_length,&data))
{
if(ram_write(dyn_slave_diff_tmp_address,dyn_slave_diff_tmp_length,data))
do_write(dyn_slave_diff_tmp_address,dyn_slave_diff_tmp_length,data);
}
do_write(dyn_slave_diff_tmp_address,dyn_slave_diff_tmp_length,data);
break;
default: dyn_slave_diff_send_status(dyn_slave_diff_error|INSTRUCTION_ERROR,0x00,0x00000000);
break;
......
......@@ -296,11 +296,13 @@ void dyn_slave_se_set_baudrate(uint8_t baudrate)
{
UBRR1H = 0;
UBRR1L = baudrate;
ram_data[Baud_Rate]=baudrate;
}
void dyn_slave_se_set_id(uint8_t id)
{
dyn_slave_se_id=id;
ram_data[ID]=id;
}
void dyn_slave_se_loop(void)
......@@ -322,11 +324,8 @@ void dyn_slave_se_loop(void)
else
dyn_slave_se_send_status(dyn_slave_se_error|INSTRUCTION_ERROR,0x00,0x00000000);
break;
case INST_WRITE: if(ram_write(dyn_slave_se_get_address(),dyn_slave_se_get_write_length(),dyn_slave_se_get_write_data()))
{
do_write(dyn_slave_se_get_address(),dyn_slave_se_get_write_length(),dyn_slave_se_get_write_data());
case INST_WRITE: if(do_write(dyn_slave_se_get_address(),dyn_slave_se_get_write_length(),dyn_slave_se_get_write_data()))
dyn_slave_se_send_status(dyn_slave_se_error|NO_ERROR,0x00,0x00000000);
}
else
dyn_slave_se_send_status(dyn_slave_se_error|INSTRUCTION_ERROR,0x00,0x00000000);
break;
......@@ -340,11 +339,8 @@ void dyn_slave_se_loop(void)
break;
case INST_ACTION: if(dyn_slave_se_reg_pending)
{
if(ram_write(dyn_slave_se_tmp_address,dyn_slave_se_tmp_length,dyn_slave_se_tmp_data))
{
do_write(dyn_slave_se_tmp_address,dyn_slave_se_tmp_length,dyn_slave_se_tmp_data);
if(do_write(dyn_slave_se_tmp_address,dyn_slave_se_tmp_length,dyn_slave_se_tmp_data))
dyn_slave_se_send_status(dyn_slave_se_error|NO_ERROR,0x00,0x00000000);
}
}
else
dyn_slave_se_send_status(dyn_slave_se_error|INSTRUCTION_ERROR,0x00,0x00000000);
......@@ -370,10 +366,7 @@ void dyn_slave_se_loop(void)
}
break;
case INST_SYNC_WRITE: if(dyn_slave_se_sync_write_id_present(&data))
{
if(ram_write(dyn_slave_se_get_address(),dyn_slave_se_get_read_length(),data))
do_write(dyn_slave_se_get_address(),dyn_slave_se_get_read_length(),data);
}
do_write(dyn_slave_se_get_address(),dyn_slave_se_get_read_length(),data);
break;
case INST_BULK_READ: dyn_slave_se_bulk_read_previous=dyn_slave_se_bulk_read_id_present(&dyn_slave_se_tmp_address,&dyn_slave_se_tmp_length);
if(dyn_slave_se_bulk_read_previous!=0xFF)
......@@ -390,10 +383,7 @@ void dyn_slave_se_loop(void)
}
break;
case INST_BULK_WRITE: if(dyn_slave_se_bulk_write_id_present(&dyn_slave_se_tmp_address,&dyn_slave_se_tmp_length,&data))
{
if(ram_write(dyn_slave_se_tmp_address,dyn_slave_se_tmp_length,data))
do_write(dyn_slave_se_tmp_address,dyn_slave_se_tmp_length,data);
}
do_write(dyn_slave_se_tmp_address,dyn_slave_se_tmp_length,data);
break;
default: dyn_slave_se_send_status(dyn_slave_se_error|INSTRUCTION_ERROR,0x00,0x00000000);
break;
......
......@@ -22,8 +22,6 @@ int16_t main(void)
compass_init();
sei();
compass_start();
while (1)
{
adc_loop();
......
......@@ -43,9 +43,15 @@ void config_port(uint8_t port_id,uint8_t dir)
if(port_id>=0 && port_id<NUM_GPIO)
{
if(dir==OUTPUT)// configure as an output
{
*(gpio_bits[port_id].dir_reg)|=0x01<<gpio_bits[port_id].bit;
ram_data[GPIO0_config+port_id*2]=0x01;
}
else// configure as an input
{
*(gpio_bits[port_id].dir_reg)&=~(0x01<<gpio_bits[port_id].bit);
ram_data[GPIO0_config+port_id*2]=0x00;
}
}
}
......@@ -68,13 +74,19 @@ uint8_t get_port_config(uint8_t port_id)
void set_port(uint8_t port_id)
{
if(port_id>=0 && port_id<NUM_GPIO)
{
*(gpio_bits[port_id].write_reg)|=0x01<<gpio_bits[port_id].bit;
ram_data[GPIO0_data+port_id*2]=0x01;
}
}
void clear_port(uint8_t port_id)
{
if(port_id>=0 && port_id<NUM_GPIO)
{
*(gpio_bits[port_id].write_reg)&=~(0x01<<gpio_bits[port_id].bit);
ram_data[GPIO0_data+port_id*2]=0x00;
}
}
uint8_t read_port(uint8_t port_id)
......@@ -101,16 +113,19 @@ uint8_t read_port(uint8_t port_id)
void set_led(void)
{
PORTE&=0xFB;
ram_data[LED]=0x01;
}
void clear_led(void)
{
PORTE|=0x04;
ram_data[LED]=0x00;
}
void toggle_led(void)
{
PORTE^=0x04;
ram_data[LED]^=0x01;
}
uint8_t get_selector_value(void)
......
......@@ -52,6 +52,7 @@ void pwm_start(void)
ICR3H=(pwm_top_value>>8)&0xFF;
ICR3L=(pwm_top_value)&0xFF;
pwm_running=0x01;
ram_data[PWM_CONTROL]|=0x04;
}
void pwm_stop(void)
......@@ -59,6 +60,7 @@ void pwm_stop(void)
/* set the prescaler to 0 (no clock source) */
TCCR3B&=0xF8;
pwm_running=0x00;
ram_data[PWM_CONTROL]&=0xFB;
}
void pwm_enable_ch(pwm_id_t id)
......@@ -66,10 +68,13 @@ void pwm_enable_ch(pwm_id_t id)
switch(id)
{
case pwm0: TCCR3A|=(1<<COMA1);
ram_data[PWM_CONTROL]|=0x10;
break;
case pwm1: TCCR3A|=(1<<COMB1);
ram_data[PWM_CONTROL]|=0x20;
break;
case pwm2: TCCR3A|=(1<<COMC1);
ram_data[PWM_CONTROL]|=0x40;
break;
case pwm3: break;
}
......@@ -80,10 +85,13 @@ void pwm_disable_ch(pwm_id_t id)
switch(id)
{
case pwm0: TCCR3A&=~(1<<COMA1);
ram_data[PWM_CONTROL]&=0xEF;
break;
case pwm1: TCCR3A&=~(1<<COMB1);
ram_data[PWM_CONTROL]&=0xDF;
break;
case pwm2: TCCR3A&=~(1<<COMC1);
ram_data[PWM_CONTROL]&=0xBF;
break;
case pwm3: break;
}
......@@ -117,6 +125,8 @@ void pwm_set_frequency(uint16_t freq_hz)
}
else
pwm_prescaler_mask=(i+1);
ram_data[PWM_FREQ_L]=freq_hz%256;
ram_data[PWM_FREQ_H]=freq_hz/256;
break;
}
}
......@@ -133,14 +143,17 @@ void pwm_set_duty_cycle(pwm_id_t id,uint8_t duty)
case pwm0: OCR3AH=(compare_value>>8)&0xFF;
OCR3AL=(compare_value&0xFF);
pwm_duty_cycle[0]=duty;
ram_data[PWM_CH0_DUTY]=duty;
break;
case pwm1: OCR3BH=(compare_value>>8)&0xFF;
OCR3BL=(compare_value&0xFF);
pwm_duty_cycle[1]=duty;
ram_data[PWM_CH1_DUTY]=duty;
break;
case pwm2: OCR3CH=(compare_value>>8)&0xFF;
OCR3CL=(compare_value&0xFF);
pwm_duty_cycle[2]=duty;
ram_data[PWM_CH2_DUTY]=duty;
break;
case pwm3: break;
}
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment