added master/slave IF. Still having issues with ADC and SPI dma

This commit is contained in:
Nicolas Trimborn
2021-08-18 19:38:37 +02:00
parent c415d29ee0
commit 012e0f87c5
238 changed files with 186131 additions and 185 deletions

View File

@@ -49,6 +49,7 @@
<file category="doc" condition="ARMCC, GCC, IAR" name="hal/documentation/pwm.rst"/>
<file category="doc" condition="ARMCC, GCC, IAR" name="hal/documentation/quad_spi_dma.rst"/>
<file category="doc" condition="ARMCC, GCC, IAR" name="hal/documentation/spi_master_async.rst"/>
<file category="doc" condition="ARMCC, GCC, IAR" name="hal/documentation/spi_master_dma.rst"/>
<file category="doc" condition="ARMCC, GCC, IAR" name="hal/documentation/spi_master_sync.rst"/>
<file category="doc" condition="ARMCC, GCC, IAR" name="hal/documentation/timer.rst"/>
<file category="header" condition="ARMCC, GCC, IAR" name="hal/include/hal_atomic.h"/>
@@ -63,6 +64,7 @@
<file category="header" condition="ARMCC, GCC, IAR" name="hal/include/hal_qspi_dma.h"/>
<file category="header" condition="ARMCC, GCC, IAR" name="hal/include/hal_sleep.h"/>
<file category="header" condition="ARMCC, GCC, IAR" name="hal/include/hal_spi_m_async.h"/>
<file category="header" condition="ARMCC, GCC, IAR" name="hal/include/hal_spi_m_dma.h"/>
<file category="header" condition="ARMCC, GCC, IAR" name="hal/include/hal_spi_m_sync.h"/>
<file category="header" condition="ARMCC, GCC, IAR" name="hal/include/hpl_adc_dma.h"/>
<file category="header" condition="ARMCC, GCC, IAR" name="hal/include/hpl_cmcc.h"/>
@@ -176,6 +178,7 @@
<file category="source" condition="ARMCC, GCC, IAR" name="hal/src/hal_ext_irq.c"/>
<file category="source" condition="ARMCC, GCC, IAR" name="hal/src/hal_pwm.c"/>
<file category="source" condition="ARMCC, GCC, IAR" name="hal/src/hal_spi_m_async.c"/>
<file category="source" condition="ARMCC, GCC, IAR" name="hal/src/hal_spi_m_dma.c"/>
<file category="source" condition="ARMCC, GCC, IAR" name="hal/src/hal_spi_m_sync.c"/>
<file category="source" condition="ARMCC, GCC, IAR" name="hal/src/hal_timer.c"/>
<file category="header" condition="ARMCC, GCC, IAR" name="hal/utils/include/parts.h"/>

View File

@@ -393,7 +393,7 @@ drivers:
the transaction
dmac_blockact_9: Channel will be disabled if it is the last block transfer in
the transaction
dmac_channel_0_settings: false
dmac_channel_0_settings: true
dmac_channel_10_settings: false
dmac_channel_11_settings: false
dmac_channel_12_settings: false
@@ -404,7 +404,7 @@ drivers:
dmac_channel_17_settings: false
dmac_channel_18_settings: false
dmac_channel_19_settings: false
dmac_channel_1_settings: false
dmac_channel_1_settings: true
dmac_channel_20_settings: false
dmac_channel_21_settings: false
dmac_channel_22_settings: false
@@ -426,7 +426,7 @@ drivers:
dmac_channel_8_settings: false
dmac_channel_9_settings: false
dmac_dbgrun: false
dmac_dstinc_0: false
dmac_dstinc_0: true
dmac_dstinc_1: false
dmac_dstinc_10: false
dmac_dstinc_11: false
@@ -599,7 +599,7 @@ drivers:
dmac_lvl_17: Channel priority 0
dmac_lvl_18: Channel priority 0
dmac_lvl_19: Channel priority 0
dmac_lvl_2: Channel priority 0
dmac_lvl_2: Channel priority 1
dmac_lvl_20: Channel priority 0
dmac_lvl_21: Channel priority 0
dmac_lvl_22: Channel priority 0
@@ -610,7 +610,7 @@ drivers:
dmac_lvl_27: Channel priority 0
dmac_lvl_28: Channel priority 0
dmac_lvl_29: Channel priority 0
dmac_lvl_3: Channel priority 0
dmac_lvl_3: Channel priority 1
dmac_lvl_30: Channel priority 0
dmac_lvl_31: Channel priority 0
dmac_lvl_4: Channel priority 0
@@ -624,7 +624,7 @@ drivers:
dmac_lvlen2: true
dmac_lvlen3: true
dmac_lvlpri0: 0
dmac_lvlpri1: 0
dmac_lvlpri1: 1
dmac_lvlpri2: 0
dmac_lvlpri3: 0
dmac_rrlvlen0: Static arbitration scheme for channel with priority 0
@@ -664,7 +664,7 @@ drivers:
dmac_runstdby_8: false
dmac_runstdby_9: false
dmac_srcinc_0: false
dmac_srcinc_1: false
dmac_srcinc_1: true
dmac_srcinc_10: false
dmac_srcinc_11: false
dmac_srcinc_12: false
@@ -696,7 +696,7 @@ drivers:
dmac_srcinc_8: false
dmac_srcinc_9: false
dmac_stepsel_0: Step size settings apply to the destination address
dmac_stepsel_1: Step size settings apply to the destination address
dmac_stepsel_1: Step size settings apply to the source address
dmac_stepsel_10: Step size settings apply to the destination address
dmac_stepsel_11: Step size settings apply to the destination address
dmac_stepsel_12: Step size settings apply to the destination address
@@ -759,8 +759,8 @@ drivers:
dmac_stepsize_7: Next ADDR = ADDR + (BEATSIZE + 1) * 1
dmac_stepsize_8: Next ADDR = ADDR + (BEATSIZE + 1) * 1
dmac_stepsize_9: Next ADDR = ADDR + (BEATSIZE + 1) * 1
dmac_trifsrc_0: Only software/event triggers
dmac_trifsrc_1: Only software/event triggers
dmac_trifsrc_0: SERCOM1 RX Trigger
dmac_trifsrc_1: SERCOM1 TX Trigger
dmac_trifsrc_10: Only software/event triggers
dmac_trifsrc_11: Only software/event triggers
dmac_trifsrc_12: Only software/event triggers
@@ -791,8 +791,8 @@ drivers:
dmac_trifsrc_7: Only software/event triggers
dmac_trifsrc_8: Only software/event triggers
dmac_trifsrc_9: Only software/event triggers
dmac_trigact_0: One trigger required for each block transfer
dmac_trigact_1: One trigger required for each block transfer
dmac_trigact_0: One trigger required for each beat transfer
dmac_trigact_1: One trigger required for each beat transfer
dmac_trigact_10: One trigger required for each block transfer
dmac_trigact_11: One trigger required for each block transfer
dmac_trigact_12: One trigger required for each block transfer
@@ -1800,22 +1800,25 @@ drivers:
variant: null
clocks:
domain_group: null
SPI_1:
user_label: SPI_1
definition: Atmel:SAME51_Drivers:0.0.1::SAME51J19A-MF::SERCOM1::driver_config_definition::SPI.Master::HAL:Driver:SPI.Master.Sync
SPI_1_MSIF:
user_label: SPI_1_MSIF
definition: Atmel:SAME51_Drivers:0.0.1::SAME51J19A-MF::SERCOM1::driver_config_definition::SPI.Master::HAL:Driver:SPI.Master.DMA
functionality: SPI
api: HAL:Driver:SPI_Master_Sync
api: HAL:Driver:SPI_Master_DMA
configuration:
spi_master_advanced: false
spi_master_advanced: true
spi_master_arch_cpha: Sample input on leading edge
spi_master_arch_cpol: SCK is low when idle
spi_master_arch_dbgstop: Keep running
spi_master_arch_dord: MSB first
spi_master_arch_ibon: In data stream
spi_master_arch_runstdby: false
spi_master_baud_rate: 50000
spi_master_baud_rate: 8000000
spi_master_character_size: 8 bits
spi_master_dma_rx_channel: 0
spi_master_dma_tx_channel: 1
spi_master_dummybyte: 511
spi_master_rx_channel: true
spi_master_rx_enable: true
optional_signals: []
variant:
@@ -2535,9 +2538,10 @@ pads:
SPI1_CS:
name: PB22
definition: Atmel:SAME51_Drivers:0.0.1::SAME51J19A-MF::pad::PB22
mode: Peripheral IO
mode: Digital output
user_label: SPI1_CS
configuration: null
configuration:
pad_initial_level: High
SPI1_MISO:
name: PB23
definition: Atmel:SAME51_Drivers:0.0.1::SAME51J19A-MF::pad::PB23

View File

@@ -51,7 +51,7 @@
// <o> Level 1 Channel Priority Number <0x00-0xFF>
// <id> dmac_lvlpri1
#ifndef CONF_DMAC_LVLPRI1
#define CONF_DMAC_LVLPRI1 0
#define CONF_DMAC_LVLPRI1 1
#endif
// <q> Priority Level 2
// <i> Indicates whether Priority Level 2 is enabled or not
@@ -105,7 +105,7 @@
// <e> Channel 0 settings
// <id> dmac_channel_0_settings
#ifndef CONF_DMAC_CHANNEL_0_SETTINGS
#define CONF_DMAC_CHANNEL_0_SETTINGS 0
#define CONF_DMAC_CHANNEL_0_SETTINGS 1
#endif
// <q> Channel Run in Standby
@@ -122,7 +122,7 @@
// <i> Defines the trigger action used for a transfer
// <id> dmac_trigact_0
#ifndef CONF_DMAC_TRIGACT_0
#define CONF_DMAC_TRIGACT_0 0
#define CONF_DMAC_TRIGACT_0 2
#endif
// <o> Trigger source
@@ -214,7 +214,7 @@
// <i> Defines the peripheral trigger which is source of the transfer
// <id> dmac_trifsrc_0
#ifndef CONF_DMAC_TRIGSRC_0
#define CONF_DMAC_TRIGSRC_0 0
#define CONF_DMAC_TRIGSRC_0 6
#endif
// <o> Channel Arbitration Level
@@ -291,7 +291,7 @@
// <i> Indicates whether the destination address incrementation is enabled or not
// <id> dmac_dstinc_0
#ifndef CONF_DMAC_DSTINC_0
#define CONF_DMAC_DSTINC_0 0
#define CONF_DMAC_DSTINC_0 1
#endif
// <o> Beat Size
@@ -329,7 +329,7 @@
// <e> Channel 1 settings
// <id> dmac_channel_1_settings
#ifndef CONF_DMAC_CHANNEL_1_SETTINGS
#define CONF_DMAC_CHANNEL_1_SETTINGS 0
#define CONF_DMAC_CHANNEL_1_SETTINGS 1
#endif
// <q> Channel Run in Standby
@@ -346,7 +346,7 @@
// <i> Defines the trigger action used for a transfer
// <id> dmac_trigact_1
#ifndef CONF_DMAC_TRIGACT_1
#define CONF_DMAC_TRIGACT_1 0
#define CONF_DMAC_TRIGACT_1 2
#endif
// <o> Trigger source
@@ -438,7 +438,7 @@
// <i> Defines the peripheral trigger which is source of the transfer
// <id> dmac_trifsrc_1
#ifndef CONF_DMAC_TRIGSRC_1
#define CONF_DMAC_TRIGSRC_1 0
#define CONF_DMAC_TRIGSRC_1 7
#endif
// <o> Channel Arbitration Level
@@ -501,14 +501,14 @@
// <i> Defines whether source or destination addresses are using the step size settings
// <id> dmac_stepsel_1
#ifndef CONF_DMAC_STEPSEL_1
#define CONF_DMAC_STEPSEL_1 0
#define CONF_DMAC_STEPSEL_1 1
#endif
// <q> Source Address Increment
// <i> Indicates whether the source address incrementation is enabled or not
// <id> dmac_srcinc_1
#ifndef CONF_DMAC_SRCINC_1
#define CONF_DMAC_SRCINC_1 0
#define CONF_DMAC_SRCINC_1 1
#endif
// <q> Destination Address Increment
@@ -673,7 +673,7 @@
// <i> Defines the arbitration level for this channel
// <id> dmac_lvl_2
#ifndef CONF_DMAC_LVL_2
#define CONF_DMAC_LVL_2 0
#define CONF_DMAC_LVL_2 1
#endif
// <q> Channel Event Output
@@ -897,7 +897,7 @@
// <i> Defines the arbitration level for this channel
// <id> dmac_lvl_3
#ifndef CONF_DMAC_LVL_3
#define CONF_DMAC_LVL_3 0
#define CONF_DMAC_LVL_3 1
#endif
// <q> Channel Event Output

View File

@@ -11,6 +11,28 @@
#define CONF_SERCOM_1_SPI_ENABLE 1
#endif
//<o> SPI DMA TX Channel <0-32>
//<i> This defines DMA channel to be used
//<id> spi_master_dma_tx_channel
#ifndef CONF_SERCOM_1_SPI_M_DMA_TX_CHANNEL
#define CONF_SERCOM_1_SPI_M_DMA_TX_CHANNEL 1
#endif
// <e> SPI RX Channel Enable
// <id> spi_master_rx_channel
#ifndef CONF_SERCOM_1_SPI_RX_CHANNEL
#define CONF_SERCOM_1_SPI_RX_CHANNEL 1
#endif
//<o> DMA Channel <0-32>
//<i> This defines DMA channel to be used
//<id> spi_master_dma_rx_channel
#ifndef CONF_SERCOM_1_SPI_M_DMA_RX_CHANNEL
#define CONF_SERCOM_1_SPI_M_DMA_RX_CHANNEL 0
#endif
// </e>
// Set module in SPI Master mode
#ifndef CONF_SERCOM_1_SPI_MODE
#define CONF_SERCOM_1_SPI_MODE 0x03
@@ -37,7 +59,7 @@
// <i> The SPI data transfer rate
// <id> spi_master_baud_rate
#ifndef CONF_SERCOM_1_SPI_BAUD
#define CONF_SERCOM_1_SPI_BAUD 50000
#define CONF_SERCOM_1_SPI_BAUD 8000000
#endif
// </h>
@@ -45,7 +67,7 @@
// <e> Advanced Configuration
// <id> spi_master_advanced
#ifndef CONF_SERCOM_1_SPI_ADVANCED
#define CONF_SERCOM_1_SPI_ADVANCED 0
#define CONF_SERCOM_1_SPI_ADVANCED 1
#endif
// <o> Dummy byte <0x00-0x1ff>

View File

@@ -45,44 +45,51 @@ static volatile int16_t *EMG_CH5 = (((int16_t *)&QSPI_tx_buffer[12]));
static volatile int16_t *EMG_CH6 = (((int16_t *)&QSPI_tx_buffer[12])+1);
static volatile int16_t *EMG_CH7 = (((int16_t *)&QSPI_tx_buffer[13]));
static volatile int16_t *EMG_CH8 = (((int16_t *)&QSPI_tx_buffer[13])+1);
/* Reserved space */
static volatile int16_t *Spare1_tx = (((int16_t *)&QSPI_tx_buffer[14]));
static volatile int16_t *Spare2_tx = (((int16_t *)&QSPI_tx_buffer[14])+1);
static volatile int16_t *Spare3_tx = (((int16_t *)&QSPI_tx_buffer[15]));
static volatile int16_t *Spare4_tx = (((int16_t *)&QSPI_tx_buffer[15])+1);
/* Motor 3*/
static volatile uint8_t *M3_Status = (uint8_t *)&QSPI_tx_buffer[14];
static volatile uint8_t *M3_Mode = (((uint8_t *)&QSPI_tx_buffer[14])+1);
static volatile int16_t *M3_Joint_rel_position = (((int16_t *)&QSPI_tx_buffer[14])+1);
static volatile int16_t *M3_Joint_abs_position = ((int16_t *)&QSPI_tx_buffer[15]);
static volatile int16_t *M3_Motor_speed = (((int16_t *)&QSPI_tx_buffer[15])+1);
static volatile int16_t *M3_Motor_current_bus = ((int16_t *)&QSPI_tx_buffer[16]);
static volatile int16_t *M3_Motor_currentPhA = (((int16_t *)&QSPI_tx_buffer[16])+1);
static volatile int16_t *M3_Motor_currentPhB = ((int16_t *)&QSPI_tx_buffer[17]);
static volatile int16_t *M3_Motor_currentPhC = (((int16_t *)&QSPI_tx_buffer[17])+1);
static volatile int16_t *M3_Motor__hallState = ((int16_t *)&QSPI_tx_buffer[18]);
static volatile int16_t *M3_Motor_dutyCycle = (((int16_t *)&QSPI_tx_buffer[18])+1);
static volatile uint8_t *M3_Status = (uint8_t *)&QSPI_tx_buffer[16];
static volatile uint8_t *M3_Mode = (((uint8_t *)&QSPI_tx_buffer[16])+1);
static volatile int16_t *M3_Joint_rel_position = (((int16_t *)&QSPI_tx_buffer[16])+1);
static volatile int16_t *M3_Joint_abs_position = ((int16_t *)&QSPI_tx_buffer[17]);
static volatile int16_t *M3_Motor_speed = (((int16_t *)&QSPI_tx_buffer[17])+1);
static volatile int16_t *M3_Motor_current_bus = ((int16_t *)&QSPI_tx_buffer[18]);
static volatile int16_t *M3_Motor_currentPhA = (((int16_t *)&QSPI_tx_buffer[18])+1);
static volatile int16_t *M3_Motor_currentPhB = ((int16_t *)&QSPI_tx_buffer[19]);
static volatile int16_t *M3_Motor_currentPhC = (((int16_t *)&QSPI_tx_buffer[19])+1);
static volatile int16_t *M3_Motor__hallState = ((int16_t *)&QSPI_tx_buffer[20]);
static volatile int16_t *M3_Motor_dutyCycle = (((int16_t *)&QSPI_tx_buffer[20])+1);
/* Motor 4*/
static volatile uint8_t *M4_Status = (uint8_t *)&QSPI_tx_buffer[19];
static volatile uint8_t *M4_Mode = (((uint8_t *)&QSPI_tx_buffer[19])+1);
static volatile int16_t *M4_Joint_rel_position = (((int16_t *)&QSPI_tx_buffer[19])+1);
static volatile int16_t *M4_Joint_abs_position = ((int16_t *)&QSPI_tx_buffer[20]);
static volatile int16_t *M4_Motor_speed = (((int16_t *)&QSPI_tx_buffer[20])+1);
static volatile int16_t *M4_Motor_current_bus = ((int16_t *)&QSPI_tx_buffer[21]);
static volatile int16_t *M4_Motor_currentPhA = (((int16_t *)&QSPI_tx_buffer[21])+1);
static volatile int16_t *M4_Motor_currentPhB = ((int16_t *)&QSPI_tx_buffer[22]);
static volatile int16_t *M4_Motor_currentPhC = (((int16_t *)&QSPI_tx_buffer[22])+1);
static volatile int16_t *M4_Motor__hallState = ((int16_t *)&QSPI_tx_buffer[23]);
static volatile int16_t *M4_Motor_dutyCycle = (((int16_t *)&QSPI_tx_buffer[23])+1);
static volatile uint8_t *M4_Status = (uint8_t *)&QSPI_tx_buffer[21];
static volatile uint8_t *M4_Mode = (((uint8_t *)&QSPI_tx_buffer[21])+1);
static volatile int16_t *M4_Joint_rel_position = (((int16_t *)&QSPI_tx_buffer[21])+1);
static volatile int16_t *M4_Joint_abs_position = ((int16_t *)&QSPI_tx_buffer[22]);
static volatile int16_t *M4_Motor_speed = (((int16_t *)&QSPI_tx_buffer[22])+1);
static volatile int16_t *M4_Motor_current_bus = ((int16_t *)&QSPI_tx_buffer[23]);
static volatile int16_t *M4_Motor_currentPhA = (((int16_t *)&QSPI_tx_buffer[23])+1);
static volatile int16_t *M4_Motor_currentPhB = ((int16_t *)&QSPI_tx_buffer[24]);
static volatile int16_t *M4_Motor_currentPhC = (((int16_t *)&QSPI_tx_buffer[24])+1);
static volatile int16_t *M4_Motor__hallState = ((int16_t *)&QSPI_tx_buffer[25]);
static volatile int16_t *M4_Motor_dutyCycle = (((int16_t *)&QSPI_tx_buffer[25])+1);
/* IMU */
static volatile int16_t *q_x0 = (((int16_t *)&QSPI_tx_buffer[24]));
static volatile int16_t *q_y0 = (((int16_t *)&QSPI_tx_buffer[24])+1);
static volatile int16_t *q_z0 = (((int16_t *)&QSPI_tx_buffer[25]));
static volatile int16_t *q_w0 = (((int16_t *)&QSPI_tx_buffer[25])+1);
static volatile int16_t *q_x0 = (((int16_t *)&QSPI_tx_buffer[26]));
static volatile int16_t *q_y0 = (((int16_t *)&QSPI_tx_buffer[26])+1);
static volatile int16_t *q_z0 = (((int16_t *)&QSPI_tx_buffer[27]));
static volatile int16_t *q_w0 = (((int16_t *)&QSPI_tx_buffer[27])+1);
/* EMG */
static volatile int16_t *FSR_CH1 = (((int16_t *)&QSPI_tx_buffer[26]));
static volatile int16_t *FSR_CH2 = (((int16_t *)&QSPI_tx_buffer[26])+1);
static volatile int16_t *FSR_CH3 = (((int16_t *)&QSPI_tx_buffer[27]));
static volatile int16_t *FSR_CH4 = (((int16_t *)&QSPI_tx_buffer[27])+1);
static volatile int16_t *FSR_CH5 = (((int16_t *)&QSPI_tx_buffer[28]));
static volatile int16_t *Pressure_CH1 = (((int16_t *)&QSPI_tx_buffer[28])+1);
static volatile int16_t *Pressure_CH2 = (((int16_t *)&QSPI_tx_buffer[29]));
static volatile int16_t *Pressure_CH3 = (((int16_t *)&QSPI_tx_buffer[29])+1);
static volatile int16_t *FSR_CH1 = (((int16_t *)&QSPI_tx_buffer[28]));
static volatile int16_t *FSR_CH2 = (((int16_t *)&QSPI_tx_buffer[28])+1);
static volatile int16_t *FSR_CH3 = (((int16_t *)&QSPI_tx_buffer[29]));
static volatile int16_t *FSR_CH4 = (((int16_t *)&QSPI_tx_buffer[29])+1);
static volatile int16_t *FSR_CH5 = (((int16_t *)&QSPI_tx_buffer[30]));
static volatile int16_t *Pressure_CH1 = (((int16_t *)&QSPI_tx_buffer[30])+1);
static volatile int16_t *Pressure_CH2 = (((int16_t *)&QSPI_tx_buffer[31]));
static volatile int16_t *Pressure_CH3 = (((int16_t *)&QSPI_tx_buffer[31])+1);
//Read From Ecat Total (XX Bytes)
//QSPI_rx_buffer
@@ -106,26 +113,46 @@ static volatile int16_t *M2_Max_pos = ((int16_t *)&QSPI_rx_buffer[6]);
static volatile int16_t *M2_Max_velocity = ((int16_t *)&QSPI_rx_buffer[6]+1);
static volatile int16_t *M2_Max_current = ((int16_t *)&QSPI_rx_buffer[7]);
static volatile int16_t *M2_Desired_dc = ((int16_t *)&QSPI_rx_buffer[7]+1); //Spare
/* Reserved space */
/* 64 bytes reserved for each */
static volatile int16_t *Spare1_rx = ((int16_t *)&QSPI_rx_buffer[8]); //Spare
static volatile int16_t *Spare2_rx = ((int16_t *)&QSPI_rx_buffer[8]+1); //Spare
static volatile int16_t *Spare3_rx = ((int16_t *)&QSPI_rx_buffer[9]); //Spare
static volatile int16_t *Spare4_rx = ((int16_t *)&QSPI_rx_buffer[9]+1); //Spare
static volatile int16_t *Spare5_rx = ((int16_t *)&QSPI_rx_buffer[10]); //Spare
static volatile int16_t *Spare6_rx = ((int16_t *)&QSPI_rx_buffer[10]+1); //Spare
static volatile int16_t *Spare7_rx = ((int16_t *)&QSPI_rx_buffer[11]); //Spare
static volatile int16_t *Spare8_rx = ((int16_t *)&QSPI_rx_buffer[11]+1); //Spare
static volatile int16_t *Spare9_rx = ((int16_t *)&QSPI_rx_buffer[12]); //Spare
static volatile int16_t *Spare10_rx = ((int16_t *)&QSPI_rx_buffer[12]+1); //Spare
static volatile int16_t *Spare11_rx = ((int16_t *)&QSPI_rx_buffer[13]); //Spare
static volatile int16_t *Spare12_rx = ((int16_t *)&QSPI_rx_buffer[13]+1); //Spare
static volatile int16_t *Spare13_rx = ((int16_t *)&QSPI_rx_buffer[14]); //Spare
static volatile int16_t *Spare14_rx = ((int16_t *)&QSPI_rx_buffer[14]+1); //Spare
static volatile int16_t *Spare15_rx = ((int16_t *)&QSPI_rx_buffer[15]); //Spare
static volatile int16_t *Spare16_rx = ((int16_t *)&QSPI_rx_buffer[15]+1); //Spare
///* Motor 3*/
static volatile uint8_t *M3_Control_mode = ((uint8_t *)&QSPI_rx_buffer[8]);
static volatile uint8_t *M3_Control_set = (((uint8_t *)&QSPI_rx_buffer[8])+1);
static volatile int16_t *M3_Desired_pos = ((int16_t *)&QSPI_rx_buffer[8]+1);
static volatile int16_t *M3_Desired_speed = ((int16_t *)&QSPI_rx_buffer[9]);
static volatile int16_t *M3_Desired_current = ((int16_t *)&QSPI_rx_buffer[9]+1);
static volatile int16_t *M3_Max_pos = ((int16_t *)&QSPI_rx_buffer[10]);
static volatile int16_t *M3_Max_velocity = ((int16_t *)&QSPI_rx_buffer[10]+1);
static volatile int16_t *M3_Max_current = ((int16_t *)&QSPI_rx_buffer[11]);
static volatile int16_t *M3_Spare = ((int16_t *)&QSPI_rx_buffer[11]+1); //Spare
static volatile uint8_t *M3_Control_mode = ((uint8_t *)&QSPI_rx_buffer[16]);
static volatile uint8_t *M3_Control_set = (((uint8_t *)&QSPI_rx_buffer[16])+1);
static volatile int16_t *M3_Desired_pos = ((int16_t *)&QSPI_rx_buffer[16]+1);
static volatile int16_t *M3_Desired_speed = ((int16_t *)&QSPI_rx_buffer[17]);
static volatile int16_t *M3_Desired_current = ((int16_t *)&QSPI_rx_buffer[17]+1);
static volatile int16_t *M3_Max_pos = ((int16_t *)&QSPI_rx_buffer[18]);
static volatile int16_t *M3_Max_velocity = ((int16_t *)&QSPI_rx_buffer[18]+1);
static volatile int16_t *M3_Max_current = ((int16_t *)&QSPI_rx_buffer[19]);
static volatile int16_t *M3_Spare = ((int16_t *)&QSPI_rx_buffer[19]+1); //Spare
///* Motor 4*/
static volatile uint8_t *M4_Control_mode = ((uint8_t *)&QSPI_rx_buffer[12]);
static volatile uint8_t *M4_Control_set = (((uint8_t *)&QSPI_rx_buffer[12])+1);
static volatile int16_t *M4_Desired_pos = ((int16_t *)&QSPI_rx_buffer[12]+1);
static volatile int16_t *M4_Desired_speed = ((int16_t *)&QSPI_rx_buffer[13]);
static volatile int16_t *M4_Desired_current = ((int16_t *)&QSPI_rx_buffer[13]+1);
static volatile int16_t *M4_Max_pos = ((int16_t *)&QSPI_rx_buffer[14]);
static volatile int16_t *M4_Max_velocity = ((int16_t *)&QSPI_rx_buffer[14]+1);
static volatile int16_t *M4_Max_current = ((int16_t *)&QSPI_rx_buffer[15]);
static volatile int16_t *M4_Spare = ((int16_t *)&QSPI_rx_buffer[15]+1);//Spare
static volatile uint8_t *M4_Control_mode = ((uint8_t *)&QSPI_rx_buffer[20]);
static volatile uint8_t *M4_Control_set = (((uint8_t *)&QSPI_rx_buffer[20])+1);
static volatile int16_t *M4_Desired_pos = ((int16_t *)&QSPI_rx_buffer[20]+1);
static volatile int16_t *M4_Desired_speed = ((int16_t *)&QSPI_rx_buffer[21]);
static volatile int16_t *M4_Desired_current = ((int16_t *)&QSPI_rx_buffer[21]+1);
static volatile int16_t *M4_Max_pos = ((int16_t *)&QSPI_rx_buffer[22]);
static volatile int16_t *M4_Max_velocity = ((int16_t *)&QSPI_rx_buffer[22]+1);
static volatile int16_t *M4_Max_current = ((int16_t *)&QSPI_rx_buffer[23]);
static volatile int16_t *M4_Spare = ((int16_t *)&QSPI_rx_buffer[23]+1); //Spare
static void update_telemetry(void)
{

View File

@@ -45,44 +45,51 @@ static volatile int16_t *EMG_CH5 = (((int16_t *)&QSPI_tx_buffer[12]));
static volatile int16_t *EMG_CH6 = (((int16_t *)&QSPI_tx_buffer[12])+1);
static volatile int16_t *EMG_CH7 = (((int16_t *)&QSPI_tx_buffer[13]));
static volatile int16_t *EMG_CH8 = (((int16_t *)&QSPI_tx_buffer[13])+1);
/* Reserved space */
static volatile int16_t *Spare1_tx = (((int16_t *)&QSPI_tx_buffer[14]));
static volatile int16_t *Spare2_tx = (((int16_t *)&QSPI_tx_buffer[14])+1);
static volatile int16_t *Spare3_tx = (((int16_t *)&QSPI_tx_buffer[15]));
static volatile int16_t *Spare4_tx = (((int16_t *)&QSPI_tx_buffer[15])+1);
/* Motor 3*/
static volatile uint8_t *M3_Status = (uint8_t *)&QSPI_tx_buffer[14];
static volatile uint8_t *M3_Mode = (((uint8_t *)&QSPI_tx_buffer[14])+1);
static volatile int16_t *M3_Joint_rel_position = (((int16_t *)&QSPI_tx_buffer[14])+1);
static volatile int16_t *M3_Joint_abs_position = ((int16_t *)&QSPI_tx_buffer[15]);
static volatile int16_t *M3_Motor_speed = (((int16_t *)&QSPI_tx_buffer[15])+1);
static volatile int16_t *M3_Motor_current_bus = ((int16_t *)&QSPI_tx_buffer[16]);
static volatile int16_t *M3_Motor_currentPhA = (((int16_t *)&QSPI_tx_buffer[16])+1);
static volatile int16_t *M3_Motor_currentPhB = ((int16_t *)&QSPI_tx_buffer[17]);
static volatile int16_t *M3_Motor_currentPhC = (((int16_t *)&QSPI_tx_buffer[17])+1);
static volatile int16_t *M3_Motor__hallState = ((int16_t *)&QSPI_tx_buffer[18]);
static volatile int16_t *M3_Motor_dutyCycle = (((int16_t *)&QSPI_tx_buffer[18])+1);
static volatile uint8_t *M3_Status = (uint8_t *)&QSPI_tx_buffer[16];
static volatile uint8_t *M3_Mode = (((uint8_t *)&QSPI_tx_buffer[16])+1);
static volatile int16_t *M3_Joint_rel_position = (((int16_t *)&QSPI_tx_buffer[16])+1);
static volatile int16_t *M3_Joint_abs_position = ((int16_t *)&QSPI_tx_buffer[17]);
static volatile int16_t *M3_Motor_speed = (((int16_t *)&QSPI_tx_buffer[17])+1);
static volatile int16_t *M3_Motor_current_bus = ((int16_t *)&QSPI_tx_buffer[18]);
static volatile int16_t *M3_Motor_currentPhA = (((int16_t *)&QSPI_tx_buffer[18])+1);
static volatile int16_t *M3_Motor_currentPhB = ((int16_t *)&QSPI_tx_buffer[19]);
static volatile int16_t *M3_Motor_currentPhC = (((int16_t *)&QSPI_tx_buffer[19])+1);
static volatile int16_t *M3_Motor__hallState = ((int16_t *)&QSPI_tx_buffer[20]);
static volatile int16_t *M3_Motor_dutyCycle = (((int16_t *)&QSPI_tx_buffer[20])+1);
/* Motor 4*/
static volatile uint8_t *M4_Status = (uint8_t *)&QSPI_tx_buffer[19];
static volatile uint8_t *M4_Mode = (((uint8_t *)&QSPI_tx_buffer[19])+1);
static volatile int16_t *M4_Joint_rel_position = (((int16_t *)&QSPI_tx_buffer[19])+1);
static volatile int16_t *M4_Joint_abs_position = ((int16_t *)&QSPI_tx_buffer[20]);
static volatile int16_t *M4_Motor_speed = (((int16_t *)&QSPI_tx_buffer[20])+1);
static volatile int16_t *M4_Motor_current_bus = ((int16_t *)&QSPI_tx_buffer[21]);
static volatile int16_t *M4_Motor_currentPhA = (((int16_t *)&QSPI_tx_buffer[21])+1);
static volatile int16_t *M4_Motor_currentPhB = ((int16_t *)&QSPI_tx_buffer[22]);
static volatile int16_t *M4_Motor_currentPhC = (((int16_t *)&QSPI_tx_buffer[22])+1);
static volatile int16_t *M4_Motor__hallState = ((int16_t *)&QSPI_tx_buffer[23]);
static volatile int16_t *M4_Motor_dutyCycle = (((int16_t *)&QSPI_tx_buffer[23])+1);
static volatile uint8_t *M4_Status = (uint8_t *)&QSPI_tx_buffer[21];
static volatile uint8_t *M4_Mode = (((uint8_t *)&QSPI_tx_buffer[21])+1);
static volatile int16_t *M4_Joint_rel_position = (((int16_t *)&QSPI_tx_buffer[21])+1);
static volatile int16_t *M4_Joint_abs_position = ((int16_t *)&QSPI_tx_buffer[22]);
static volatile int16_t *M4_Motor_speed = (((int16_t *)&QSPI_tx_buffer[22])+1);
static volatile int16_t *M4_Motor_current_bus = ((int16_t *)&QSPI_tx_buffer[23]);
static volatile int16_t *M4_Motor_currentPhA = (((int16_t *)&QSPI_tx_buffer[23])+1);
static volatile int16_t *M4_Motor_currentPhB = ((int16_t *)&QSPI_tx_buffer[24]);
static volatile int16_t *M4_Motor_currentPhC = (((int16_t *)&QSPI_tx_buffer[24])+1);
static volatile int16_t *M4_Motor__hallState = ((int16_t *)&QSPI_tx_buffer[25]);
static volatile int16_t *M4_Motor_dutyCycle = (((int16_t *)&QSPI_tx_buffer[25])+1);
/* IMU */
static volatile int16_t *q_x0 = (((int16_t *)&QSPI_tx_buffer[24]));
static volatile int16_t *q_y0 = (((int16_t *)&QSPI_tx_buffer[24])+1);
static volatile int16_t *q_z0 = (((int16_t *)&QSPI_tx_buffer[25]));
static volatile int16_t *q_w0 = (((int16_t *)&QSPI_tx_buffer[25])+1);
static volatile int16_t *q_x0 = (((int16_t *)&QSPI_tx_buffer[26]));
static volatile int16_t *q_y0 = (((int16_t *)&QSPI_tx_buffer[26])+1);
static volatile int16_t *q_z0 = (((int16_t *)&QSPI_tx_buffer[27]));
static volatile int16_t *q_w0 = (((int16_t *)&QSPI_tx_buffer[27])+1);
/* EMG */
static volatile int16_t *FSR_CH1 = (((int16_t *)&QSPI_tx_buffer[26]));
static volatile int16_t *FSR_CH2 = (((int16_t *)&QSPI_tx_buffer[26])+1);
static volatile int16_t *FSR_CH3 = (((int16_t *)&QSPI_tx_buffer[27]));
static volatile int16_t *FSR_CH4 = (((int16_t *)&QSPI_tx_buffer[27])+1);
static volatile int16_t *FSR_CH5 = (((int16_t *)&QSPI_tx_buffer[28]));
static volatile int16_t *Pressure_CH1 = (((int16_t *)&QSPI_tx_buffer[28])+1);
static volatile int16_t *Pressure_CH2 = (((int16_t *)&QSPI_tx_buffer[29]));
static volatile int16_t *Pressure_CH3 = (((int16_t *)&QSPI_tx_buffer[29])+1);
static volatile int16_t *FSR_CH1 = (((int16_t *)&QSPI_tx_buffer[28]));
static volatile int16_t *FSR_CH2 = (((int16_t *)&QSPI_tx_buffer[28])+1);
static volatile int16_t *FSR_CH3 = (((int16_t *)&QSPI_tx_buffer[29]));
static volatile int16_t *FSR_CH4 = (((int16_t *)&QSPI_tx_buffer[29])+1);
static volatile int16_t *FSR_CH5 = (((int16_t *)&QSPI_tx_buffer[30]));
static volatile int16_t *Pressure_CH1 = (((int16_t *)&QSPI_tx_buffer[30])+1);
static volatile int16_t *Pressure_CH2 = (((int16_t *)&QSPI_tx_buffer[31]));
static volatile int16_t *Pressure_CH3 = (((int16_t *)&QSPI_tx_buffer[31])+1);
//Read From Ecat Total (XX Bytes)
//QSPI_rx_buffer
@@ -106,26 +113,46 @@ static volatile int16_t *M2_Max_pos = ((int16_t *)&QSPI_rx_buffer[6]);
static volatile int16_t *M2_Max_velocity = ((int16_t *)&QSPI_rx_buffer[6]+1);
static volatile int16_t *M2_Max_current = ((int16_t *)&QSPI_rx_buffer[7]);
static volatile int16_t *M2_Desired_dc = ((int16_t *)&QSPI_rx_buffer[7]+1); //Spare
/* Reserved space */
/* 64 bytes reserved for each */
static volatile int16_t *Spare1_rx = ((int16_t *)&QSPI_rx_buffer[8]); //Spare
static volatile int16_t *Spare2_rx = ((int16_t *)&QSPI_rx_buffer[8]+1); //Spare
static volatile int16_t *Spare3_rx = ((int16_t *)&QSPI_rx_buffer[9]); //Spare
static volatile int16_t *Spare4_rx = ((int16_t *)&QSPI_rx_buffer[9]+1); //Spare
static volatile int16_t *Spare5_rx = ((int16_t *)&QSPI_rx_buffer[10]); //Spare
static volatile int16_t *Spare6_rx = ((int16_t *)&QSPI_rx_buffer[10]+1); //Spare
static volatile int16_t *Spare7_rx = ((int16_t *)&QSPI_rx_buffer[11]); //Spare
static volatile int16_t *Spare8_rx = ((int16_t *)&QSPI_rx_buffer[11]+1); //Spare
static volatile int16_t *Spare9_rx = ((int16_t *)&QSPI_rx_buffer[12]); //Spare
static volatile int16_t *Spare10_rx = ((int16_t *)&QSPI_rx_buffer[12]+1); //Spare
static volatile int16_t *Spare11_rx = ((int16_t *)&QSPI_rx_buffer[13]); //Spare
static volatile int16_t *Spare12_rx = ((int16_t *)&QSPI_rx_buffer[13]+1); //Spare
static volatile int16_t *Spare13_rx = ((int16_t *)&QSPI_rx_buffer[14]); //Spare
static volatile int16_t *Spare14_rx = ((int16_t *)&QSPI_rx_buffer[14]+1); //Spare
static volatile int16_t *Spare15_rx = ((int16_t *)&QSPI_rx_buffer[15]); //Spare
static volatile int16_t *Spare16_rx = ((int16_t *)&QSPI_rx_buffer[15]+1); //Spare
///* Motor 3*/
static volatile uint8_t *M3_Control_mode = ((uint8_t *)&QSPI_rx_buffer[8]);
static volatile uint8_t *M3_Control_set = (((uint8_t *)&QSPI_rx_buffer[8])+1);
static volatile int16_t *M3_Desired_pos = ((int16_t *)&QSPI_rx_buffer[8]+1);
static volatile int16_t *M3_Desired_speed = ((int16_t *)&QSPI_rx_buffer[9]);
static volatile int16_t *M3_Desired_current = ((int16_t *)&QSPI_rx_buffer[9]+1);
static volatile int16_t *M3_Max_pos = ((int16_t *)&QSPI_rx_buffer[10]);
static volatile int16_t *M3_Max_velocity = ((int16_t *)&QSPI_rx_buffer[10]+1);
static volatile int16_t *M3_Max_current = ((int16_t *)&QSPI_rx_buffer[11]);
static volatile int16_t *M3_Spare = ((int16_t *)&QSPI_rx_buffer[11]+1); //Spare
static volatile uint8_t *M3_Control_mode = ((uint8_t *)&QSPI_rx_buffer[16]);
static volatile uint8_t *M3_Control_set = (((uint8_t *)&QSPI_rx_buffer[16])+1);
static volatile int16_t *M3_Desired_pos = ((int16_t *)&QSPI_rx_buffer[16]+1);
static volatile int16_t *M3_Desired_speed = ((int16_t *)&QSPI_rx_buffer[17]);
static volatile int16_t *M3_Desired_current = ((int16_t *)&QSPI_rx_buffer[17]+1);
static volatile int16_t *M3_Max_pos = ((int16_t *)&QSPI_rx_buffer[18]);
static volatile int16_t *M3_Max_velocity = ((int16_t *)&QSPI_rx_buffer[18]+1);
static volatile int16_t *M3_Max_current = ((int16_t *)&QSPI_rx_buffer[19]);
static volatile int16_t *M3_Spare = ((int16_t *)&QSPI_rx_buffer[19]+1); //Spare
///* Motor 4*/
static volatile uint8_t *M4_Control_mode = ((uint8_t *)&QSPI_rx_buffer[12]);
static volatile uint8_t *M4_Control_set = (((uint8_t *)&QSPI_rx_buffer[12])+1);
static volatile int16_t *M4_Desired_pos = ((int16_t *)&QSPI_rx_buffer[12]+1);
static volatile int16_t *M4_Desired_speed = ((int16_t *)&QSPI_rx_buffer[13]);
static volatile int16_t *M4_Desired_current = ((int16_t *)&QSPI_rx_buffer[13]+1);
static volatile int16_t *M4_Max_pos = ((int16_t *)&QSPI_rx_buffer[14]);
static volatile int16_t *M4_Max_velocity = ((int16_t *)&QSPI_rx_buffer[14]+1);
static volatile int16_t *M4_Max_current = ((int16_t *)&QSPI_rx_buffer[15]);
static volatile int16_t *M4_Spare = ((int16_t *)&QSPI_rx_buffer[15]+1);//Spare
static volatile uint8_t *M4_Control_mode = ((uint8_t *)&QSPI_rx_buffer[20]);
static volatile uint8_t *M4_Control_set = (((uint8_t *)&QSPI_rx_buffer[20])+1);
static volatile int16_t *M4_Desired_pos = ((int16_t *)&QSPI_rx_buffer[20]+1);
static volatile int16_t *M4_Desired_speed = ((int16_t *)&QSPI_rx_buffer[21]);
static volatile int16_t *M4_Desired_current = ((int16_t *)&QSPI_rx_buffer[21]+1);
static volatile int16_t *M4_Max_pos = ((int16_t *)&QSPI_rx_buffer[22]);
static volatile int16_t *M4_Max_velocity = ((int16_t *)&QSPI_rx_buffer[22]+1);
static volatile int16_t *M4_Max_current = ((int16_t *)&QSPI_rx_buffer[23]);
static volatile int16_t *M4_Spare = ((int16_t *)&QSPI_rx_buffer[23]+1); //Spare
static void update_telemetry(void)
{

View File

@@ -0,0 +1,215 @@
/*
* master_slave_IF.h
*
* Created: 8/18/2021 4:32:19 PM
* Author: ge37vez
*/
#ifndef MASTER_SLAVE_IF_H_
#define MASTER_SLAVE_IF_H_
#define MASTER_BUFFER_SIZE 64
static uint8_t SPI_rx_buffer[MASTER_BUFFER_SIZE] = {0};
static uint8_t SPI_tx_buffer[MASTER_BUFFER_SIZE] = {0};
//static uint8_t SPI_rx_buffer[SLAVE_BUFFER_SIZE] = {0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,
//18,19,20,21,22,23,24,25,26,27,28,29,30,31};
//tx_buffer
/* Motor 3*/
static volatile uint8_t *M3_Status = (uint8_t *)&SPI_rx_buffer[0]; //1 byte - 0 of 64
static volatile uint8_t *M3_Mode = (uint8_t *)&SPI_rx_buffer[1]; //1 byte - 1 of 64
static volatile int16_t *M3_Joint_rel_position = (int16_t *)&SPI_rx_buffer[2]; //2 byte - 2 of 64
static volatile int16_t *M3_Joint_abs_position = (int16_t *)&SPI_rx_buffer[4]; //2 byte - 4 of 64
static volatile int16_t *M3_Motor_speed = (int16_t *)&SPI_rx_buffer[6]; //2 byte - 6 of 64
static volatile int16_t *M3_Motor_current_bus = (int16_t *)&SPI_rx_buffer[8]; //2 byte - 8 of 64
static volatile int16_t *M3_Motor_currentPhA = (int16_t *)&SPI_rx_buffer[10]; //2 byte - 10 of 64
static volatile int16_t *M3_Motor_currentPhB = (int16_t *)&SPI_rx_buffer[12]; //2 byte - 12 of 64
static volatile int16_t *M3_Motor_currentPhC = (int16_t *)&SPI_rx_buffer[14]; //2 byte - 14 of 64
static volatile int16_t *M3_Motor__hallState = (int16_t *)&SPI_rx_buffer[16]; //2 byte - 16 of 64
static volatile int16_t *M3_Motor_dutyCycle = (int16_t *)&SPI_rx_buffer[18]; //2 byte - 18 of 64
/* Motor 4*/
static volatile uint8_t *M4_Status = (uint8_t *)&SPI_rx_buffer[20]; //1 byte - 20 of 64
static volatile uint8_t *M4_Mode = (uint8_t *)&SPI_rx_buffer[21]; //1 byte - 21 of 64
static volatile int16_t *M4_Joint_rel_position = (int16_t *)&SPI_rx_buffer[22]; //2 byte - 22 of 64
static volatile int16_t *M4_Joint_abs_position = (int16_t *)&SPI_rx_buffer[24]; //2 byte - 24 of 64
static volatile int16_t *M4_Motor_speed = (int16_t *)&SPI_rx_buffer[26]; //2 byte - 26 of 64
static volatile int16_t *M4_Motor_current_bus = (int16_t *)&SPI_rx_buffer[28]; //2 byte - 28 of 64
static volatile int16_t *M4_Motor_currentPhA = (int16_t *)&SPI_rx_buffer[30]; //2 byte - 30 of 64
static volatile int16_t *M4_Motor_currentPhB = (int16_t *)&SPI_rx_buffer[32]; //2 byte - 32 of 64
static volatile int16_t *M4_Motor_currentPhC = (int16_t *)&SPI_rx_buffer[34]; //2 byte - 34 of 64
static volatile int16_t *M4_Motor__hallState = (int16_t *)&SPI_rx_buffer[36]; //2 byte - 36 of 64
static volatile int16_t *M4_Motor_dutyCycle = (int16_t *)&SPI_rx_buffer[38]; //2 byte - 38 of 64
/* IMU */
static volatile int16_t *q_x0 = (int16_t *)&SPI_rx_buffer[40]; //2 byte - 40 of 64
static volatile int16_t *q_y0 = (int16_t *)&SPI_rx_buffer[42]; //2 byte - 42 of 64
static volatile int16_t *q_z0 = (int16_t *)&SPI_rx_buffer[44]; //2 byte - 44 of 64
static volatile int16_t *q_w0 = (int16_t *)&SPI_rx_buffer[46]; //2 byte - 46 of 64
/* EMG */
static volatile int16_t *FSR_CH1 = (int16_t *)&SPI_rx_buffer[48]; //2 byte - 48 of 64
static volatile int16_t *FSR_CH2 = (int16_t *)&SPI_rx_buffer[50]; //2 byte - 50 of 64
static volatile int16_t *FSR_CH3 = (int16_t *)&SPI_rx_buffer[52]; //2 byte - 52 of 64
static volatile int16_t *FSR_CH4 = (int16_t *)&SPI_rx_buffer[54]; //2 byte - 54 of 64
static volatile int16_t *FSR_CH5 = (int16_t *)&SPI_rx_buffer[56]; //2 byte - 56 of 64
static volatile int16_t *Pressure_CH1 = (int16_t *)&SPI_rx_buffer[58]; //2 byte - 58 of 64
static volatile int16_t *Pressure_CH2 = (int16_t *)&SPI_rx_buffer[60]; //2 byte - 60 of 64
static volatile int16_t *Pressure_CH3 = (int16_t *)&SPI_rx_buffer[62]; //2 byte - 62 of 64
//tx_buffer
///* Motor 3*/
static volatile uint8_t *M3_Control_mode = (uint8_t *)&SPI_tx_buffer[0]; //1 byte - 0 of 32
static volatile uint8_t *M3_Control_set = (uint8_t *)&SPI_tx_buffer[1]; //1 byte - 1 of 32
static volatile int16_t *M3_Desired_pos = (int16_t *)&SPI_tx_buffer[2]; //2 byte - 2 of 32
static volatile int16_t *M3_Desired_speed = (int16_t *)&SPI_tx_buffer[4]; //2 byte - 4 of 32
static volatile int16_t *M3_Desired_current = (int16_t *)&SPI_tx_buffer[6]; //2 byte - 6 of 32
static volatile int16_t *M3_Max_pos = (int16_t *)&SPI_tx_buffer[8]; //2 byte - 8 of 32
static volatile int16_t *M3_Max_velocity = (int16_t *)&SPI_tx_buffer[10]; //2 byte - 10 of 32
static volatile int16_t *M3_Max_current = (int16_t *)&SPI_tx_buffer[12]; //2 byte - 12 of 32
static volatile int16_t *M3_Spare = (int16_t *)&SPI_tx_buffer[14]; //2 byte - 14 of 32
///* Motor 4*/
static volatile uint8_t *M4_Control_mode = (int16_t *)&SPI_tx_buffer[16]; //1 byte - 16 of 32
static volatile uint8_t *M4_Control_set = (int16_t *)&SPI_tx_buffer[17]; //1 byte - 17 of 32
static volatile int16_t *M4_Desired_pos = (int16_t *)&SPI_tx_buffer[18]; //2 byte - 18 of 32
static volatile int16_t *M4_Desired_speed = (int16_t *)&SPI_tx_buffer[20]; //2 byte - 20 of 32
static volatile int16_t *M4_Desired_current = (int16_t *)&SPI_tx_buffer[22]; //2 byte - 22 of 32
static volatile int16_t *M4_Max_pos = (int16_t *)&SPI_tx_buffer[24]; //2 byte - 24 of 32
static volatile int16_t *M4_Max_velocity = (int16_t *)&SPI_tx_buffer[26]; //2 byte - 26 of 32
static volatile int16_t *M4_Max_current = (int16_t *)&SPI_tx_buffer[28]; //2 byte - 28 of 32
static volatile int16_t *M4_Spare = (int16_t *)&SPI_tx_buffer[30]; //2 byte - 30 of 32
static void update_telemetry(void)
{
inline int16_t convert_to_mA(volatile float32_t current_PU)
{
return (int16_t)(current_PU*1000.0f);
}
//
//*M3_Status = 0;
//*M3_Mode = 0;
/* Motor 1 */
*M3_Status = Motor1.motor_state.currentstate;
*M3_Joint_rel_position = Motor1.motor_status.Num_Steps;
//*M3_Joint_abs_position = ((int16_t *)&QSPI_rx_buffer[1];
//*M3_Motor_speed = (((int16_t *)&QSPI_rx_buffer[1]+1);
*M3_Motor_current_bus = convert_to_mA(Motor1.Iphase_pu.Bus);
*M3_Motor_currentPhA = convert_to_mA(Motor1.Iphase_pu.A);
*M3_Motor_currentPhB = convert_to_mA(Motor1.Iphase_pu.B);
*M3_Motor_currentPhC = convert_to_mA(Motor1.Iphase_pu.C);
*M3_Motor__hallState = Motor1.motor_status.currentHallPattern;
*M3_Motor_dutyCycle = Motor1.motor_status.duty_cycle;
*M3_Motor_speed = (int16_t)Motor1.motor_status.calc_rpm;
*M3_Joint_abs_position = Motor1.motor_status.actualDirection;
/* Motor 2 */
*M4_Status = Motor2.motor_state.currentstate;
*M4_Joint_rel_position = Motor2.motor_status.Num_Steps;
//*M3_Joint_abs_position = ((int16_t *)&QSPI_rx_buffer[1];
//*M3_Motor_speed = (((int16_t *)&QSPI_rx_buffer[1]+1);
*M4_Motor_current_bus = convert_to_mA( Motor2.Iphase_pu.Bus);
*M4_Motor_currentPhA = convert_to_mA( Motor2.Iphase_pu.A);
*M4_Motor_currentPhB = convert_to_mA( Motor2.Iphase_pu.B);
*M4_Motor_currentPhC = convert_to_mA(Motor2.Iphase_pu.C);
*M4_Motor__hallState = Motor2.motor_status.currentHallPattern;
*M4_Motor_dutyCycle = Motor2.motor_status.duty_cycle;
*M4_Motor_speed = (int16_t)Motor2.motor_status.calc_rpm;
*M4_Joint_abs_position = Motor2.motor_status.actualDirection;
}
static void update_setpoints(void)
{
Motor1.motor_setpoints.desired_position = *M3_Desired_pos;
Motor1.motor_setpoints.desired_speed = *M3_Desired_speed;
Motor1.motor_setpoints.desired_torque = *M3_Desired_current;
Motor1.motor_setpoints.max_current = *M3_Max_current;
Motor1.motor_setpoints.max_torque = *M3_Max_current;
Motor1.motor_setpoints.max_velocity = *M3_Max_velocity;
Motor2.motor_setpoints.desired_position = *M4_Desired_pos;
Motor2.motor_setpoints.desired_speed = *M4_Desired_speed;
Motor2.motor_setpoints.desired_torque = *M4_Desired_current;
Motor2.motor_setpoints.max_current = *M4_Max_current;
Motor2.motor_setpoints.max_torque = *M4_Max_current;
Motor2.motor_setpoints.max_velocity = *M4_Max_velocity;
//volatile uint8_t a = *M3_Control_mode;
//volatile uint8_t b = *M3_Control_set;
//volatile int16_t c = *M3_Desired_pos;
//volatile int16_t d = *M3_Desired_speed;
//volatile int16_t e = *M3_Desired_current;
//volatile int16_t f = *M3_Max_pos;
//volatile int16_t g = *M3_Max_velocity;
//volatile int16_t h = *M3_Max_current;
//volatile int16_t i = *M3_Spare;
//inline float32_t convert_int_to_PU(volatile int16_t input)
//{
//return ((float32_t)(input/1000.0f));
//}
////Motor1.des_mode = 0;
////Motor1.set = 0;
//Motor1.motor_setpoints.desired_position = *desired_position;
//Motor1.motor_setpoints.desired_speed = *desired_speed;
////Motor1.desired_speed = 1500;
//Motor1.motor_setpoints.desired_torque = convert_int_to_PU(*desired_torque);
////Motor1.controllerParam.I_kp = 0;
////Motor1.controllerParam.I_ki = 0;
////Motor1.controllerParam.V_kp = 0;
////Motor1.controllerParam.V_kd = 0;
////Motor1.controllerParam.V_kd = 0;
////Motor1.controllerParam.P_kp = 0;
////Motor1.controllerParam.P_ki = 0;
////Motor1.reductionRatio = 0;
//Motor1.motor_setpoints.max_velocity = *max_velocity;
//Motor1.motor_setpoints.max_current = convert_int_to_PU(*max_current);
//Motor1.motor_setpoints.max_torque = convert_int_to_PU(*max_torque);
////Motor1.Spare1 = 0;
////Motor1.Spare2 = 0;
////Motor1.Spare3 = 0;
////Motor1.Spare4 = 0;
}
static inline void comms_check(void)
{
/* Motor 1*/
*M3_Status = 1;
*M3_Mode = 2;
*M3_Joint_rel_position = -3;
*M3_Joint_abs_position = 4;
*M3_Motor_speed = -5;
*M3_Motor_current_bus = 6;
*M3_Motor_currentPhA = -7;
*M3_Motor_currentPhB = 8;
*M3_Motor_currentPhC = -9;
*M3_Motor__hallState = 10;
*M3_Motor_dutyCycle = -11;
/* Motor 2*/
*M4_Status = 12;
*M4_Mode = 13;
*M4_Joint_rel_position = 14;
*M4_Joint_abs_position = -15;
*M4_Motor_speed = 16;
*M4_Motor_current_bus = -17;
*M4_Motor_currentPhA = 18;
*M4_Motor_currentPhB = -19;
*M4_Motor_currentPhC = 20;
*M4_Motor__hallState = -21;
*M4_Motor_dutyCycle = 22;
/* IMU */
*q_x0 = 23;
*q_y0 = -24;
*q_z0 = 25;
*q_w0 = -26;
/* EMG */
*FSR_CH1 = 27;
*FSR_CH2 = -28;
*FSR_CH3 = 29;
*FSR_CH4 = -30;
*FSR_CH5 = 31;
*Pressure_CH1 = -32;
*Pressure_CH2 = 33;
*Pressure_CH3 = -34;
}
#endif /* MASTER_SLAVE_IF_H_ */

View File

@@ -63,6 +63,7 @@
<AcmeProjectActionInfo Action="File" Source="hal/include/hal_qspi_dma.h" IsConfig="false" Hash="Z34LPTgquoHUOOWcEGA5XA" />
<AcmeProjectActionInfo Action="File" Source="hal/include/hal_sleep.h" IsConfig="false" Hash="KuZDwgrLdU+fuMG82ZFTqg" />
<AcmeProjectActionInfo Action="File" Source="hal/include/hal_spi_m_async.h" IsConfig="false" Hash="kNWiys4SwzwGn2qCqzFQlA" />
<AcmeProjectActionInfo Action="File" Source="hal/include/hal_spi_m_dma.h" IsConfig="false" Hash="MRP9iaBaY97VrZIf+yI+nQ" />
<AcmeProjectActionInfo Action="File" Source="hal/include/hal_spi_m_sync.h" IsConfig="false" Hash="2oma6hRMCcowUy2wVveqMg" />
<AcmeProjectActionInfo Action="File" Source="hal/include/hpl_adc_dma.h" IsConfig="false" Hash="ZNWJ5APLfPqPLqI7LDqlMA" />
<AcmeProjectActionInfo Action="File" Source="hal/include/hpl_cmcc.h" IsConfig="false" Hash="mDAHEzTxsniAe2HtqO43oA" />
@@ -150,11 +151,11 @@
<AcmeProjectActionInfo Action="File" Source="hri/hri_usb_e51.h" IsConfig="false" Hash="x6M7vYgNCS2oECqykr5+yw" />
<AcmeProjectActionInfo Action="File" Source="hri/hri_wdt_e51.h" IsConfig="false" Hash="o9Rg/hyuMzwOCphVc7uG1w" />
<AcmeProjectActionInfo Action="File" Source="main.c" IsConfig="false" Hash="k0AH7j+BrmdFhBPzCCMptA" />
<AcmeProjectActionInfo Action="File" Source="driver_init.c" IsConfig="false" Hash="Yq1q1Sa7cd5/H8qv36yeFQ" />
<AcmeProjectActionInfo Action="File" Source="driver_init.h" IsConfig="false" Hash="Djt0mG2wi689XcXrLHKt0g" />
<AcmeProjectActionInfo Action="File" Source="driver_init.c" IsConfig="false" Hash="EY0TWjVpAZ1peiFc/X6XZQ" />
<AcmeProjectActionInfo Action="File" Source="driver_init.h" IsConfig="false" Hash="9Vb0j3AjI95MGRCecrCnLQ" />
<AcmeProjectActionInfo Action="File" Source="atmel_start_pins.h" IsConfig="false" Hash="ByCGTBpkOpAk+zk9txhJSA" />
<AcmeProjectActionInfo Action="File" Source="examples/driver_examples.h" IsConfig="false" Hash="kvd7eb1e9guBnXkzUfLueg" />
<AcmeProjectActionInfo Action="File" Source="examples/driver_examples.c" IsConfig="false" Hash="/OR9xzATKmeDfzhivaESBw" />
<AcmeProjectActionInfo Action="File" Source="examples/driver_examples.h" IsConfig="false" Hash="gLjWgjni3Z8tNpbOMxpapQ" />
<AcmeProjectActionInfo Action="File" Source="examples/driver_examples.c" IsConfig="false" Hash="M3T31wmDXMA5AqAp9Pm+7A" />
<AcmeProjectActionInfo Action="File" Source="hal/include/hal_adc_sync.h" IsConfig="false" Hash="ez1X5T9kpYwT+1+5x4Pxqg" />
<AcmeProjectActionInfo Action="File" Source="hal/include/hal_pwm.h" IsConfig="false" Hash="RXcBZcci/7vXKRJKNIq/Kw" />
<AcmeProjectActionInfo Action="File" Source="hal/include/hal_timer.h" IsConfig="false" Hash="5pZVthtMl40VMvofOld2ng" />
@@ -175,6 +176,7 @@
<AcmeProjectActionInfo Action="File" Source="hal/src/hal_ext_irq.c" IsConfig="false" Hash="l6Jmb4zu10+HvXQ0Iej4dQ" />
<AcmeProjectActionInfo Action="File" Source="hal/src/hal_pwm.c" IsConfig="false" Hash="ZFJmg7/0rhQ6JMKyxuk9kw" />
<AcmeProjectActionInfo Action="File" Source="hal/src/hal_spi_m_async.c" IsConfig="false" Hash="hErEkp5CHigcW3olA6Csrg" />
<AcmeProjectActionInfo Action="File" Source="hal/src/hal_spi_m_dma.c" IsConfig="false" Hash="KMrinO/3xx7qWxy2PsJB7g" />
<AcmeProjectActionInfo Action="File" Source="hal/src/hal_spi_m_sync.c" IsConfig="false" Hash="Q0IudnTEWeoIkfQIoYIqxA" />
<AcmeProjectActionInfo Action="File" Source="hal/src/hal_timer.c" IsConfig="false" Hash="F2MrEXhHq4umI9xpONnlGg" />
<AcmeProjectActionInfo Action="File" Source="hal/utils/include/parts.h" IsConfig="false" Hash="zv0TWdxXtsu5Y1B88PQgiA" />
@@ -198,7 +200,7 @@
<AcmeProjectActionInfo Action="File" Source="hpl/port/hpl_gpio_base.h" IsConfig="false" Hash="YjSLMahiT5jdYvqMYVQ8zg" />
<AcmeProjectActionInfo Action="File" Source="hpl/qspi/hpl_qspi.c" IsConfig="false" Hash="woXbbCFkSWus6J14PHJlHw" />
<AcmeProjectActionInfo Action="File" Source="hpl/ramecc/hpl_ramecc.c" IsConfig="false" Hash="pMdmwVWBg16VG8HOwA3DPw" />
<AcmeProjectActionInfo Action="File" Source="hpl/sercom/hpl_sercom.c" IsConfig="false" Hash="MLflsL/S4ZuAfydm9ax0cA" />
<AcmeProjectActionInfo Action="File" Source="hpl/sercom/hpl_sercom.c" IsConfig="false" Hash="z3dKgPu8whuFF0HDwi0isw" />
<AcmeProjectActionInfo Action="File" Source="hpl/tc/hpl_tc.c" IsConfig="false" Hash="CwAdaARrfhpCcFm3bk4PtA" />
<AcmeProjectActionInfo Action="File" Source="hpl/tc/hpl_tc_base.h" IsConfig="false" Hash="gjj5IyaZPy6sUReifzS1GQ" />
<AcmeProjectActionInfo Action="File" Source="hpl/tc/tc_lite.c" IsConfig="false" Hash="035J+hUWZyoUFfzslZgZwg" />
@@ -210,7 +212,7 @@
<AcmeProjectActionInfo Action="File" Source="config/hpl_adc_config.h" IsConfig="true" Hash="XAOTvk5xMalucgzL/ILTWw" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_ccl_config.h" IsConfig="true" Hash="Q1yijLwNXjFOsGrwEEma+g" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_cmcc_config.h" IsConfig="true" Hash="bmtxQ8rLloaRtAo2HeXZRQ" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_dmac_config.h" IsConfig="true" Hash="xCXhbdBwXKUe304TPFonTw" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_dmac_config.h" IsConfig="true" Hash="JdAljBjm3ndwImqgZ6Oc5w" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_eic_config.h" IsConfig="true" Hash="xKw8xm4k4XPALg++/jSPcw" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_evsys_config.h" IsConfig="true" Hash="/3bNiu/UgpvPbmvfRA+w3g" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_gclk_config.h" IsConfig="true" Hash="fvc5nhPTGTNHCTNlzs6nhA" />
@@ -219,7 +221,7 @@
<AcmeProjectActionInfo Action="File" Source="config/hpl_oscctrl_config.h" IsConfig="true" Hash="Uje5LXAS+nQpGryt9t0fYA" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_port_config.h" IsConfig="true" Hash="rMTNR+5FXtu+wfT1NbfRRA" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_qspi_config.h" IsConfig="true" Hash="CwZ360eeEYs7T9SYFSvDug" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_sercom_config.h" IsConfig="true" Hash="Es2tGk0V59kfHKXDA1geTw" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_sercom_config.h" IsConfig="true" Hash="x9H2b9FAETnTpR8cbaWLOg" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_tc_config.h" IsConfig="true" Hash="T93Kr6C+WDuufZob89oPeg" />
<AcmeProjectActionInfo Action="File" Source="config/hpl_tcc_config.h" IsConfig="true" Hash="2LU7afZ/3Yx7FE2KzF9dSQ" />
<AcmeProjectActionInfo Action="File" Source="config/peripheral_clk_config.h" IsConfig="true" Hash="rqTY1slZEq9V5moV+8Q+hw" />
@@ -648,6 +650,9 @@
<Compile Include="hal\include\hal_spi_m_async.h">
<SubType>compile</SubType>
</Compile>
<Compile Include="hal\include\hal_spi_m_dma.h">
<SubType>compile</SubType>
</Compile>
<Compile Include="hal\include\hal_spi_m_sync.h">
<SubType>compile</SubType>
</Compile>
@@ -807,6 +812,9 @@
<Compile Include="hal\src\hal_spi_m_async.c">
<SubType>compile</SubType>
</Compile>
<Compile Include="hal\src\hal_spi_m_dma.c">
<SubType>compile</SubType>
</Compile>
<Compile Include="hal\src\hal_spi_m_sync.c">
<SubType>compile</SubType>
</Compile>
@@ -1127,6 +1135,9 @@
<None Include="hal\documentation\spi_master_async.rst">
<SubType>compile</SubType>
</None>
<None Include="hal\documentation\spi_master_dma.rst">
<SubType>compile</SubType>
</None>
<None Include="hal\documentation\spi_master_sync.rst">
<SubType>compile</SubType>
</None>

View File

@@ -35,11 +35,11 @@ void motor_StateMachine(BLDCMotor_t* const motor)
case MOTOR_IDLE:
//hri_tcc_write_PATTBUF_reg(motor->motor_param->pwm_desc->device.hw, DISABLE_PATTERN);
motor->motor_state.previousstate = motor->motor_state.currentstate;
motor->motor_state.currentstate = MOTOR_PVI_CTRL_STATE;
motor->motor_state.currentstate = MOTOR_IDLE;
break;
case MOTOR_OPEN_LOOP_STATE:
BLDC_runOpenLoop(motor, *M1_Desired_dc);
calculate_motor_speed(motor);
//calculate_motor_speed(motor);
motor->motor_state.previousstate = motor->motor_state.currentstate;
break;
case MOTOR_V_CTRL_STATE:

View File

@@ -16,13 +16,15 @@
#include "bldc.h"
#include "interrupts.h"
// ----------------------------------------------------------------------
// ADC DMA Initialization
// M1_IA=ADC1_AIN[9], M1_IB=ADC1_AIN[8], M2_IA=ADC1_AIN[7], M2_IB=ADC1_AIN[6]
// ----------------------------------------------------------------------
#define DMAC_CHANNEL_ADC_SEQ 2U
#define DMAC_CHANNEL_ADC_SRAM 3U
// ----------------------------------------------------------------------
// M1_IA=ADC1_AIN[9], M1_IB=ADC1_AIN[8], M2_IA=ADC1_AIN[7], M2_IB=ADC1_AIN[6]
// ----------------------------------------------------------------------
/* Single Ended */
//const uint32_t adc_seq_regs[4] = {0x1807, 0x1806, 0x1809, 0x1808};
/* Differential */
@@ -32,6 +34,9 @@ volatile int16_t adc_res[4] = {0};
struct _dma_resource *adc_sram_dma_resource;
struct _dma_resource *adc_dmac_sequence_resource;
// ----------------------------------------------------------------------
// PWM Timer Initialization
// ----------------------------------------------------------------------
inline static void configure_tcc_pwm(void)
{
//gpio_set_pin_pull_mode(M1_HALLA, GPIO_PULL_UP);
@@ -138,6 +143,19 @@ inline void adc_sram_dmac_init()
_dma_enable_transaction(DMAC_CHANNEL_ADC_SRAM, false);
}
// ----------------------------------------------------------------------
// Init SPI DMA communication between Master & Slave Board
// ----------------------------------------------------------------------
void boardToBoardTransferInit(void)
{
struct io_descriptor *io;
spi_m_dma_get_io_descriptor(&SPI_1_MSIF, &io);
spi_m_dma_register_callback(&SPI_1_MSIF, SPI_M_DMA_CB_RX_DONE, b2bTransferComplete_cb);
//SERCOM4->SPI.CTRLC.bit.DATA32B = true;
gpio_set_pin_level(SPI1_CS, true);
spi_m_dma_enable(&SPI_1_MSIF);
}
#endif /* CONFIGURATION_H_ */

View File

@@ -14,7 +14,6 @@
#include <hpl_adc_base.h>
#include <hpl_adc_base.h>
struct spi_m_sync_descriptor SPI_1;
struct spi_m_sync_descriptor SPI_3;
struct timer_descriptor TIMER_0;
@@ -24,6 +23,8 @@ struct adc_sync_descriptor ADC_1;
struct qspi_dma_descriptor ECAT_QSPI;
struct spi_m_dma_descriptor SPI_1_MSIF;
struct spi_m_async_descriptor SPI_2;
struct pwm_descriptor PWM_0;
@@ -410,7 +411,7 @@ void ECAT_QSPI_init(void)
ECAT_QSPI_PORT_init();
}
void SPI_1_PORT_init(void)
void SPI_1_MSIF_PORT_init(void)
{
gpio_set_pin_level(SPI1_MOSI,
@@ -451,7 +452,7 @@ void SPI_1_PORT_init(void)
gpio_set_pin_function(SPI1_MISO, PINMUX_PB23C_SERCOM1_PAD3);
}
void SPI_1_CLOCK_init(void)
void SPI_1_MSIF_CLOCK_init(void)
{
hri_gclk_write_PCHCTRL_reg(GCLK, SERCOM1_GCLK_ID_CORE, CONF_GCLK_SERCOM1_CORE_SRC | (1 << GCLK_PCHCTRL_CHEN_Pos));
hri_gclk_write_PCHCTRL_reg(GCLK, SERCOM1_GCLK_ID_SLOW, CONF_GCLK_SERCOM1_SLOW_SRC | (1 << GCLK_PCHCTRL_CHEN_Pos));
@@ -459,11 +460,11 @@ void SPI_1_CLOCK_init(void)
hri_mclk_set_APBAMASK_SERCOM1_bit(MCLK);
}
void SPI_1_init(void)
void SPI_1_MSIF_init(void)
{
SPI_1_CLOCK_init();
spi_m_sync_init(&SPI_1, SERCOM1);
SPI_1_PORT_init();
SPI_1_MSIF_CLOCK_init();
spi_m_dma_init(&SPI_1_MSIF, SERCOM1);
SPI_1_MSIF_PORT_init();
}
void SPI_2_PORT_init(void)
@@ -716,6 +717,16 @@ void system_init(void)
// GPIO on PB22
gpio_set_pin_level(SPI1_CS,
// <y> Initial level
// <id> pad_initial_level
// <false"> Low
// <true"> High
true);
// Set pin direction to output
gpio_set_pin_direction(SPI1_CS, GPIO_DIRECTION_OUT);
gpio_set_pin_function(SPI1_CS, GPIO_PIN_FUNCTION_OFF);
ADC_0_init();
@@ -730,7 +741,7 @@ void system_init(void)
ECAT_QSPI_init();
SPI_1_init();
SPI_1_MSIF_init();
SPI_2_init();

View File

@@ -33,7 +33,7 @@ extern "C" {
#include <hal_qspi_dma.h>
#include <hal_spi_m_sync.h>
#include <hal_spi_m_dma.h>
#include <hal_spi_m_async.h>
#include <hal_spi_m_sync.h>
@@ -52,8 +52,9 @@ extern struct adc_sync_descriptor ADC_0;
extern struct adc_sync_descriptor ADC_1;
extern struct qspi_dma_descriptor ECAT_QSPI;
extern struct spi_m_sync_descriptor SPI_1;
extern struct qspi_dma_descriptor ECAT_QSPI;
extern struct spi_m_dma_descriptor SPI_1_MSIF;
extern struct spi_m_async_descriptor SPI_2;
extern struct spi_m_sync_descriptor SPI_3;
@@ -79,9 +80,9 @@ void ECAT_QSPI_PORT_init(void);
void ECAT_QSPI_CLOCK_init(void);
void ECAT_QSPI_init(void);
void SPI_1_PORT_init(void);
void SPI_1_CLOCK_init(void);
void SPI_1_init(void);
void SPI_1_MSIF_PORT_init(void);
void SPI_1_MSIF_CLOCK_init(void);
void SPI_1_MSIF_init(void);
void SPI_2_PORT_init(void);
void SPI_2_CLOCK_init(void);

View File

@@ -101,17 +101,29 @@ void ECAT_QSPI_example(void)
}
/**
* Example of using SPI_1 to write "Hello World" using the IO abstraction.
* Example of using SPI_1_MSIF to write "Hello World" using the IO abstraction.
*
* Since the driver is asynchronous we need to use statically allocated memory for string
* because driver initiates transfer and then returns before the transmission is completed.
*
* Once transfer has been completed the tx_cb function will be called.
*/
static uint8_t example_SPI_1[12] = "Hello World!";
void SPI_1_example(void)
static uint8_t example_SPI_1_MSIF[12] = "Hello World!";
static void tx_complete_cb_SPI_1_MSIF(struct _dma_resource *resource)
{
/* Transfer completed */
}
void SPI_1_MSIF_example(void)
{
struct io_descriptor *io;
spi_m_sync_get_io_descriptor(&SPI_1, &io);
spi_m_dma_get_io_descriptor(&SPI_1_MSIF, &io);
spi_m_sync_enable(&SPI_1);
io_write(io, example_SPI_1, 12);
spi_m_dma_register_callback(&SPI_1_MSIF, SPI_M_DMA_CB_TX_DONE, tx_complete_cb_SPI_1_MSIF);
spi_m_dma_enable(&SPI_1_MSIF);
io_write(io, example_SPI_1_MSIF, 12);
}
/**

View File

@@ -22,6 +22,8 @@ void EXTERNAL_IRQ_0_example(void);
void ECAT_QSPI_example(void);
void SPI_1_MSIF_example(void);
void SPI_2_example(void);
void TIMER_0_example(void);

View File

@@ -0,0 +1,56 @@
The SPI Master DMA Driver
==================================
The serial peripheral interface (SPI) is a DMA serial communication
interface.
The SPI Master DMA driver uses DMA system to transfer data from
a memory buffer to SPI (Memory to Peripheral), and receive data
from SPI to a memory buffer (Peripheral to Memory).User must configure
DMA system driver accordingly. A callback is called when all the data
is transfered or all the data is received, if it is registered via
spi_m_dma_register_callback function.
Features
--------
* Initialization/de-initialization
* Enabling/disabling
* Control of the following settings:
* Baudrate
* SPI mode
* Character size
* Data order
* Data transfer: transmission, reception and full-duplex
* Notifications about transfer completion and errors via callbacks
Applications
------------
Send/receive/exchange data with a SPI slave device. E.g., serial flash, SD card,
LCD controller, etc.
Dependencies
------------
SPI master capable hardware and DMA hardware, with data sent/received.
Concurrency
-----------
N/A
Limitations
-----------
When only uses DMA channel to receive data, the transfer channel must enable to
send dummy data to the slave.
While read/write/transfer is in progress, the data buffer used must be kept
unchanged.
Known issues and workarounds
----------------------------
N/A

View File

@@ -0,0 +1,257 @@
/**
* \file
*
* \brief SPI DMA related functionality declaration.
*
* Copyright (c) 2016-2018 Microchip Technology Inc. and its subsidiaries.
*
* \asf_license_start
*
* \page License
*
* Subject to your compliance with these terms, you may use Microchip
* software and any derivatives exclusively with Microchip products.
* It is your responsibility to comply with third party license terms applicable
* to your use of third party software (including open source software) that
* may accompany Microchip software.
*
* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES,
* WHETHER EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE,
* INCLUDING ANY IMPLIED WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY,
* AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT WILL MICROCHIP BE
* LIABLE FOR ANY INDIRECT, SPECIAL, PUNITIVE, INCIDENTAL OR CONSEQUENTIAL
* LOSS, DAMAGE, COST OR EXPENSE OF ANY KIND WHATSOEVER RELATED TO THE
* SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP HAS BEEN ADVISED OF THE
* POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE FULLEST EXTENT
* ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS IN ANY WAY
* RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF ANY,
* THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE.
*
* \asf_license_stop
*
*/
#ifndef _HAL_SPI_M_DMA_H_INCLUDED
#define _HAL_SPI_M_DMA_H_INCLUDED
#include <hal_io.h>
#include <hpl_spi_m_dma.h>
/**
* \addtogroup doc_driver_hal_spi_master_dma
*
* @{
*/
#ifdef __cplusplus
extern "C" {
#endif
/* Forward declaration of spi_descriptor. */
struct spi_m_dma_descriptor;
/** The callback types */
enum spi_m_dma_cb_type {
/** Callback type for DMA transfer buffer done */
SPI_M_DMA_CB_TX_DONE,
/** Callback type for DMA receive buffer done */
SPI_M_DMA_CB_RX_DONE,
/** Callback type for DMA errors */
SPI_M_DMA_CB_ERROR,
SPI_M_DMA_CB_N
};
/**
* \brief SPI Master DMA callback type
*/
typedef void (*spi_m_dma_cb_t)(struct _dma_resource *resource);
/** \brief SPI HAL driver struct for DMA access
*/
struct spi_m_dma_descriptor {
struct _spi_m_dma_hpl_interface *func;
/** Pointer to SPI device instance */
struct _spi_m_dma_dev dev;
/** I/O read/write */
struct io_descriptor io;
/** DMA resource */
struct _dma_resource *resource;
};
/** \brief Set the SPI HAL instance function pointer for HPL APIs.
*
* Set SPI HAL instance function pointer for HPL APIs.
*
* \param[in] spi Pointer to the HAL SPI instance.
* \param[in] func Pointer to the HPL api structure.
*
*/
void spi_m_dma_set_func_ptr(struct spi_m_dma_descriptor *spi, void *const func);
/** \brief Initialize the SPI HAL instance and hardware for DMA mode
*
* Initialize SPI HAL with dma mode.
*
* \param[in] spi Pointer to the HAL SPI instance.
* \param[in] hw Pointer to the hardware base.
*
* \return Operation status.
* \retval ERR_NONE Success.
* \retval ERR_INVALID_DATA Error, initialized.
*/
int32_t spi_m_dma_init(struct spi_m_dma_descriptor *spi, void *const hw);
/** \brief Deinitialize the SPI HAL instance
*
* Abort transfer, disable and reset SPI, de-init software.
*
* \param[in] spi Pointer to the HAL SPI instance.
*
* \return Operation status.
* \retval ERR_NONE Success.
* \retval <0 Error code.
*/
void spi_m_dma_deinit(struct spi_m_dma_descriptor *spi);
/** \brief Enable SPI
*
* \param[in] spi Pointer to the HAL SPI instance.
*
* \return Operation status.
* \retval ERR_NONE Success.
* \retval <0 Error code.
*/
void spi_m_dma_enable(struct spi_m_dma_descriptor *spi);
/** \brief Disable SPI
*
* \param[in] spi Pointer to the HAL SPI instance.
*
* \return Operation status.
* \retval ERR_NONE Success.
* \retval <0 Error code.
*/
void spi_m_dma_disable(struct spi_m_dma_descriptor *spi);
/** \brief Set SPI baudrate
*
* Works if SPI is initialized as master.
* In the function a sanity check is used to confirm it's called in the correct mode.
*
* \param[in] spi Pointer to the HAL SPI instance.
* \param[in] baud_val The target baudrate value
* (See "baudrate calculation" for calculating the value).
*
* \return Operation status.
* \retval ERR_NONE Success.
* \retval ERR_BUSY Busy.
*
* note: This api should be used to write the baudrate register with the given baud_val
* paramter, the user has to calculate the baud_val for required baud rate and pass it as
* argument(baud_val) to this api
*/
int32_t spi_m_dma_set_baudrate(struct spi_m_dma_descriptor *spi, const uint32_t baud_val);
/** \brief Set SPI mode
*
* Set SPI transfer mode (\ref spi_transfer_mode),
* which controls clock polarity and clock phase:
* - Mode 0: leading edge is rising edge, data sample on leading edge.
* - Mode 1: leading edge is rising edge, data sample on trailing edge.
* - Mode 2: leading edge is falling edge, data sample on leading edge.
* - Mode 3: leading edge is falling edge, data sample on trailing edge.
*
* \param[in] spi Pointer to the HAL SPI instance.
* \param[in] mode The mode (\ref spi_transfer_mode).
*
* \return Operation status.
* \retval ERR_NONE Success.
* \retval ERR_BUSY Busy, CS activated.
*/
int32_t spi_m_dma_set_mode(struct spi_m_dma_descriptor *spi, const enum spi_transfer_mode mode);
/** \brief Set the SPI transfer character size in number of bits
*
* The character size (\ref spi_char_size) influence the way the data is
* sent/received.
* For char size <= 8-bit, data is stored byte by byte.
* For char size between 9-bit ~ 16-bit, data is stored in 2-byte length.
* Note that the default and recommended char size is 8-bit since it's
* supported by all system.
*
* \param[in] spi Pointer to the HAL SPI instance.
* \param[in] char_size The char size (\ref spi_char_size).
*
* \return Operation status.
* \retval ERR_NONE Success.
* \retval ERR_BUSY Busy, CS activated.
* \retval ERR_INVALID_ARG The char size is not supported.
*/
int32_t spi_m_dma_set_char_size(struct spi_m_dma_descriptor *spi, const enum spi_char_size char_size);
/** \brief Set SPI transfer data order
*
* \param[in] spi Pointer to the HAL SPI instance.
* \param[in] dord The data order: send LSB/MSB first.
*
* \return Operation status.
* \retval ERR_NONE Success.
* \retval ERR_BUSY Busy, CS activated.
* \retval ERR_INVALID The data order is not supported.
*/
int32_t spi_m_dma_set_data_order(struct spi_m_dma_descriptor *spi, const enum spi_data_order dord);
/** \brief Perform the SPI data transfer (TX and RX) with the DMA
*
* \param[in] spi Pointer to the HAL SPI instance.
* \param[in] txbuf Pointer to the transfer information.
* \param[out] rxbuf Pointer to the receiver information.
* \param[in] length SPI transfer data length.
*
* \return Operation status.
* \retval ERR_NONE Success.
* \retval ERR_BUSY Busy.
*/
int32_t spi_m_dma_transfer(struct spi_m_dma_descriptor *spi, uint8_t const *txbuf, uint8_t *const rxbuf,
const uint16_t length);
/** \brief Register a function as an SPI transfer completion callback
*
* Register a callback function specified by its \c type.
* - SPI_CB_COMPLETE: set the function that will be called on the SPI transfer
* completion including deactivating the CS.
* - SPI_CB_XFER: set the function that will be called on the SPI buffer transfer
* completion.
* Register a NULL function to not use the callback.
*
* \param[in] spi Pointer to the HAL SPI instance.
* \param[in] type Callback type (\ref spi_m_dma_cb_type).
* \param[in] func Pointer to callback function.
*/
void spi_m_dma_register_callback(struct spi_m_dma_descriptor *spi, const enum spi_m_dma_cb_type type,
spi_m_dma_cb_t func);
/**
* \brief Return I/O descriptor for this SPI instance
*
* This function will return an I/O instance for this SPI driver instance
*
* \param[in] spi An SPI master descriptor, which is used to communicate through
* SPI
* \param[in, out] io A pointer to an I/O descriptor pointer type
*
* \retval ERR_NONE
*/
int32_t spi_m_dma_get_io_descriptor(struct spi_m_dma_descriptor *const spi, struct io_descriptor **io);
/** \brief Retrieve the current driver version
*
* \return Current driver version.
*/
uint32_t spi_m_dma_get_version(void);
#ifdef __cplusplus
}
#endif
/**@}*/
#endif /* ifndef _HAL_SPI_M_DMA_H_INCLUDED */

View File

@@ -0,0 +1,183 @@
/**
* \file
*
* \brief I/O SPI DMA related functionality implementation.
*
* Copyright (c) 2016-2018 Microchip Technology Inc. and its subsidiaries.
*
* \asf_license_start
*
* \page License
*
* Subject to your compliance with these terms, you may use Microchip
* software and any derivatives exclusively with Microchip products.
* It is your responsibility to comply with third party license terms applicable
* to your use of third party software (including open source software) that
* may accompany Microchip software.
*
* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES,
* WHETHER EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE,
* INCLUDING ANY IMPLIED WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY,
* AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT WILL MICROCHIP BE
* LIABLE FOR ANY INDIRECT, SPECIAL, PUNITIVE, INCIDENTAL OR CONSEQUENTIAL
* LOSS, DAMAGE, COST OR EXPENSE OF ANY KIND WHATSOEVER RELATED TO THE
* SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP HAS BEEN ADVISED OF THE
* POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE FULLEST EXTENT
* ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS IN ANY WAY
* RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF ANY,
* THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE.
*
* \asf_license_stop
*
*/
#include "hal_atomic.h"
#include "hal_spi_m_dma.h"
#include <utils_assert.h>
#include <utils.h>
/**
* \brief Driver version
*/
#define SPI_DRIVER_VERSION 0x00000001u
static int32_t _spi_m_dma_io_write(struct io_descriptor *const io, const uint8_t *const buf, const uint16_t length);
static int32_t _spi_m_dma_io_read(struct io_descriptor *const io, uint8_t *const buf, const uint16_t length);
/**
* \brief Initialize the SPI HAL instance function pointer for HPL APIs.
*/
void spi_m_dma_set_func_ptr(struct spi_m_dma_descriptor *spi, void *const func)
{
ASSERT(spi);
spi->func = (struct _spi_m_dma_hpl_interface *)func;
}
int32_t spi_m_dma_init(struct spi_m_dma_descriptor *spi, void *const hw)
{
int32_t rc = 0;
ASSERT(spi && hw);
spi->dev.prvt = (void *)hw;
rc = _spi_m_dma_init(&spi->dev, hw);
if (rc) {
return rc;
}
spi->io.read = _spi_m_dma_io_read;
spi->io.write = _spi_m_dma_io_write;
return ERR_NONE;
}
void spi_m_dma_deinit(struct spi_m_dma_descriptor *spi)
{
ASSERT(spi);
_spi_m_dma_deinit(&spi->dev);
}
void spi_m_dma_enable(struct spi_m_dma_descriptor *spi)
{
ASSERT(spi);
_spi_m_dma_enable(&spi->dev);
}
void spi_m_dma_disable(struct spi_m_dma_descriptor *spi)
{
ASSERT(spi);
_spi_m_dma_disable(&spi->dev);
}
int32_t spi_m_dma_set_baudrate(struct spi_m_dma_descriptor *spi, const uint32_t baud_val)
{
ASSERT(spi);
return _spi_m_dma_set_baudrate(&spi->dev, baud_val);
}
int32_t spi_m_dma_set_mode(struct spi_m_dma_descriptor *spi, const enum spi_transfer_mode mode)
{
ASSERT(spi);
return _spi_m_dma_set_mode(&spi->dev, mode);
}
int32_t spi_m_dma_set_char_size(struct spi_m_dma_descriptor *spi, const enum spi_char_size char_size)
{
ASSERT(spi);
return _spi_m_dma_set_char_size(&spi->dev, char_size);
}
int32_t spi_m_dma_set_data_order(struct spi_m_dma_descriptor *spi, const enum spi_data_order dord)
{
ASSERT(spi);
return _spi_m_dma_set_data_order(&spi->dev, dord);
}
/** \brief Do SPI read in background
*
* It never blocks and return quickly, user check status or set callback to
* know when data is ready to process.
*
* \param[in, out] spi Pointer to the HAL SPI instance.
* \param[out] p_buf Pointer to the buffer to store read data.
* \param[in] size Size of the data in number of characters.
* \return ERR_NONE on success, or an error code on failure.
* \retval ERR_NONE Success, transfer started.
* \retval ERR_BUSY Busy.
*/
static int32_t _spi_m_dma_io_read(struct io_descriptor *io, uint8_t *const buf, const uint16_t length)
{
ASSERT(io);
struct spi_m_dma_descriptor *spi = CONTAINER_OF(io, struct spi_m_dma_descriptor, io);
return _spi_m_dma_transfer(&spi->dev, NULL, buf, length);
}
/** \brief Do SPI data write in background
*
* The data read back is discarded.
*
* It never blocks and return quickly, user check status or set callback to
* know when data is sent.
*
* \param[in, out] spi Pointer to the HAL SPI instance.
* \param[in] p_buf Pointer to the buffer to store data to write.
* \param[in] size Size of the data in number of characters.
*
* \return ERR_NONE on success, or an error code on failure.
* \retval ERR_NONE Success, transfer started.
* \retval ERR_BUSY Busy.
*/
static int32_t _spi_m_dma_io_write(struct io_descriptor *io, const uint8_t *const buf, const uint16_t length)
{
ASSERT(io);
struct spi_m_dma_descriptor *spi = CONTAINER_OF(io, struct spi_m_dma_descriptor, io);
return _spi_m_dma_transfer(&spi->dev, buf, NULL, length);
}
int32_t spi_m_dma_transfer(struct spi_m_dma_descriptor *spi, uint8_t const *txbuf, uint8_t *const rxbuf,
const uint16_t length)
{
ASSERT(spi);
return _spi_m_dma_transfer(&spi->dev, txbuf, rxbuf, length);
}
void spi_m_dma_register_callback(struct spi_m_dma_descriptor *spi, const enum spi_m_dma_cb_type type,
spi_m_dma_cb_t func)
{
ASSERT(spi);
_spi_m_dma_register_callback(&spi->dev, (enum _spi_dma_dev_cb_type)type, func);
}
int32_t spi_m_dma_get_io_descriptor(struct spi_m_dma_descriptor *const spi, struct io_descriptor **io)
{
ASSERT(spi && io);
*io = &spi->io;
return 0;
}
uint32_t spi_m_dma_get_version(void)
{
return SPI_DRIVER_VERSION;
}

View File

@@ -31,6 +31,7 @@
* \asf_license_stop
*
*/
#include <hpl_spi_m_dma.h>
#include <hpl_dma.h>
#include <hpl_i2c_m_async.h>
#include <hpl_i2c_m_sync.h>
@@ -3018,3 +3019,428 @@ void _spi_s_async_set_irq_state(struct _spi_async_dev *const device, const enum
{
_spi_m_async_set_irq_state(device, type, state);
}
#ifndef CONF_SERCOM_0_SPI_M_DMA_TX_CHANNEL
#define CONF_SERCOM_0_SPI_M_DMA_TX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_0_SPI_M_DMA_RX_CHANNEL
#define CONF_SERCOM_0_SPI_M_DMA_RX_CHANNEL 1
#endif
#ifndef CONF_SERCOM_1_SPI_M_DMA_TX_CHANNEL
#define CONF_SERCOM_1_SPI_M_DMA_TX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_1_SPI_M_DMA_RX_CHANNEL
#define CONF_SERCOM_1_SPI_M_DMA_RX_CHANNEL 1
#endif
#ifndef CONF_SERCOM_2_SPI_M_DMA_TX_CHANNEL
#define CONF_SERCOM_2_SPI_M_DMA_TX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_2_SPI_M_DMA_RX_CHANNEL
#define CONF_SERCOM_2_SPI_M_DMA_RX_CHANNEL 1
#endif
#ifndef CONF_SERCOM_3_SPI_M_DMA_TX_CHANNEL
#define CONF_SERCOM_3_SPI_M_DMA_TX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_3_SPI_M_DMA_RX_CHANNEL
#define CONF_SERCOM_3_SPI_M_DMA_RX_CHANNEL 1
#endif
#ifndef CONF_SERCOM_4_SPI_M_DMA_TX_CHANNEL
#define CONF_SERCOM_4_SPI_M_DMA_TX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_4_SPI_M_DMA_RX_CHANNEL
#define CONF_SERCOM_4_SPI_M_DMA_RX_CHANNEL 1
#endif
#ifndef CONF_SERCOM_5_SPI_M_DMA_TX_CHANNEL
#define CONF_SERCOM_5_SPI_M_DMA_TX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_5_SPI_M_DMA_RX_CHANNEL
#define CONF_SERCOM_5_SPI_M_DMA_RX_CHANNEL 1
#endif
#ifndef CONF_SERCOM_6_SPI_M_DMA_TX_CHANNEL
#define CONF_SERCOM_6_SPI_M_DMA_TX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_6_SPI_M_DMA_RX_CHANNEL
#define CONF_SERCOM_6_SPI_M_DMA_RX_CHANNEL 1
#endif
#ifndef CONF_SERCOM_7_SPI_M_DMA_TX_CHANNEL
#define CONF_SERCOM_7_SPI_M_DMA_TX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_7_SPI_M_DMA_RX_CHANNEL
#define CONF_SERCOM_7_SPI_M_DMA_RX_CHANNEL 1
#endif
#ifndef CONF_SERCOM_0_SPI_RX_CHANNEL
#define CONF_SERCOM_0_SPI_RX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_1_SPI_RX_CHANNEL
#define CONF_SERCOM_1_SPI_RX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_2_SPI_RX_CHANNEL
#define CONF_SERCOM_2_SPI_RX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_3_SPI_RX_CHANNEL
#define CONF_SERCOM_3_SPI_RX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_4_SPI_RX_CHANNEL
#define CONF_SERCOM_4_SPI_RX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_5_SPI_RX_CHANNEL
#define CONF_SERCOM_5_SPI_RX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_6_SPI_RX_CHANNEL
#define CONF_SERCOM_6_SPI_RX_CHANNEL 0
#endif
#ifndef CONF_SERCOM_7_SPI_RX_CHANNEL
#define CONF_SERCOM_7_SPI_RX_CHANNEL 0
#endif
/** \internal Enable SERCOM SPI RX
*
* \param[in] hw Pointer to the hardware register base.
*
* \return Enabling status
*/
static int32_t _spi_sync_rx_enable(void *const hw)
{
if (hri_sercomspi_is_syncing(hw, SERCOM_SPI_SYNCBUSY_CTRLB)) {
return ERR_BUSY;
}
hri_sercomspi_set_CTRLB_RXEN_bit(hw);
return ERR_NONE;
}
/** \internal Disable SERCOM SPI RX
*
* \param[in] hw Pointer to the hardware register base.
*
* \return Disabling status
*/
static int32_t _spi_sync_rx_disable(void *const hw)
{
if (hri_sercomspi_is_syncing(hw, SERCOM_SPI_SYNCBUSY_CTRLB)) {
return ERR_BUSY;
}
hri_sercomspi_clear_CTRLB_RXEN_bit(hw);
return ERR_NONE;
}
static int32_t _spi_m_dma_rx_enable(struct _spi_m_dma_dev *dev)
{
ASSERT(dev && dev->prvt);
return _spi_sync_rx_enable(dev->prvt);
}
static int32_t _spi_m_dma_rx_disable(struct _spi_m_dma_dev *dev)
{
ASSERT(dev && dev->prvt);
return _spi_sync_rx_disable(dev->prvt);
}
/**
* \brief Get the spi source address for DMA
* \param[in] dev Pointer to the SPI device instance
*
* \return The spi source address
*/
static uint32_t _spi_m_get_source_for_dma(void *const hw)
{
return (uint32_t) & (((Sercom *)hw)->SPI.DATA);
}
/**
* \brief Get the spi destination address for DMA
* \param[in] dev Pointer to the SPI device instance
*
* \return The spi destination address
*/
static uint32_t _spi_m_get_destination_for_dma(void *const hw)
{
return (uint32_t) & (((Sercom *)hw)->SPI.DATA);
}
/**
* \brief Return the SPI TX DMA channel index
* \param[in] hw_addr The hardware register base address
*
* \return SPI TX DMA channel index.
*/
static uint8_t _spi_get_tx_dma_channel(const void *const hw)
{
uint8_t index = _sercom_get_hardware_index(hw);
switch (index) {
case 0:
return CONF_SERCOM_0_SPI_M_DMA_TX_CHANNEL;
case 1:
return CONF_SERCOM_1_SPI_M_DMA_TX_CHANNEL;
case 2:
return CONF_SERCOM_2_SPI_M_DMA_TX_CHANNEL;
case 3:
return CONF_SERCOM_3_SPI_M_DMA_TX_CHANNEL;
case 4:
return CONF_SERCOM_4_SPI_M_DMA_TX_CHANNEL;
case 5:
return CONF_SERCOM_5_SPI_M_DMA_TX_CHANNEL;
case 6:
return CONF_SERCOM_6_SPI_M_DMA_TX_CHANNEL;
case 7:
return CONF_SERCOM_7_SPI_M_DMA_TX_CHANNEL;
default:
return CONF_SERCOM_0_SPI_M_DMA_TX_CHANNEL;
}
}
/**
* \brief Return whether SPI RX DMA channel is enabled or not
* \param[in] hw_addr The hardware register base address
*
* \return one if enabled.
*/
static uint8_t _spi_is_rx_dma_channel_enabled(const void *const hw)
{
uint8_t index = _sercom_get_hardware_index(hw);
switch (index) {
case 0:
return CONF_SERCOM_0_SPI_RX_CHANNEL;
case 1:
return CONF_SERCOM_1_SPI_RX_CHANNEL;
case 2:
return CONF_SERCOM_2_SPI_RX_CHANNEL;
case 3:
return CONF_SERCOM_3_SPI_RX_CHANNEL;
case 4:
return CONF_SERCOM_4_SPI_RX_CHANNEL;
case 5:
return CONF_SERCOM_5_SPI_RX_CHANNEL;
case 6:
return CONF_SERCOM_6_SPI_RX_CHANNEL;
case 7:
return CONF_SERCOM_7_SPI_RX_CHANNEL;
default:
return false;
}
}
/**
* \brief Return the SPI RX DMA channel index
* \param[in] hw_addr The hardware register base address
*
* \return SPI RX DMA channel index.
*/
static uint8_t _spi_get_rx_dma_channel(const void *const hw)
{
uint8_t index = _sercom_get_hardware_index(hw);
switch (index) {
case 0:
return CONF_SERCOM_0_SPI_M_DMA_RX_CHANNEL;
case 1:
return CONF_SERCOM_1_SPI_M_DMA_RX_CHANNEL;
case 2:
return CONF_SERCOM_2_SPI_M_DMA_RX_CHANNEL;
case 3:
return CONF_SERCOM_3_SPI_M_DMA_RX_CHANNEL;
case 4:
return CONF_SERCOM_4_SPI_M_DMA_RX_CHANNEL;
case 5:
return CONF_SERCOM_5_SPI_M_DMA_RX_CHANNEL;
case 6:
return CONF_SERCOM_6_SPI_M_DMA_RX_CHANNEL;
case 7:
return CONF_SERCOM_7_SPI_M_DMA_RX_CHANNEL;
default:
return CONF_SERCOM_0_SPI_M_DMA_TX_CHANNEL;
}
}
/**
* \brief Callback for RX
* \param[in, out] dev Pointer to the DMA resource.
*/
static void _spi_dma_rx_complete(struct _dma_resource *resource)
{
struct _spi_m_dma_dev *dev = (struct _spi_m_dma_dev *)resource->back;
if (dev->callbacks.rx) {
dev->callbacks.rx(resource);
}
}
/**
* \brief Callback for TX
* \param[in, out] dev Pointer to the DMA resource.
*/
static void _spi_dma_tx_complete(struct _dma_resource *resource)
{
struct _spi_m_dma_dev *dev = (struct _spi_m_dma_dev *)resource->back;
if (dev->callbacks.tx) {
dev->callbacks.tx(resource);
}
}
/**
* \brief Callback for ERROR
* \param[in, out] dev Pointer to the DMA resource.
*/
static void _spi_dma_error_occured(struct _dma_resource *resource)
{
struct _spi_m_dma_dev *dev = (struct _spi_m_dma_dev *)resource->back;
if (dev->callbacks.error) {
dev->callbacks.error(resource);
}
}
int32_t _spi_m_dma_init(struct _spi_m_dma_dev *dev, void *const hw)
{
const struct sercomspi_regs_cfg *regs = _spi_get_regs((uint32_t)hw);
ASSERT(dev && hw);
if (regs == NULL) {
return ERR_INVALID_ARG;
}
if (!hri_sercomspi_is_syncing(hw, SERCOM_SPI_SYNCBUSY_SWRST)) {
uint32_t mode = regs->ctrla & SERCOM_SPI_CTRLA_MODE_Msk;
if (hri_sercomspi_get_CTRLA_reg(hw, SERCOM_SPI_CTRLA_ENABLE)) {
hri_sercomspi_clear_CTRLA_ENABLE_bit(hw);
hri_sercomspi_wait_for_sync(hw, SERCOM_SPI_SYNCBUSY_ENABLE);
}
hri_sercomspi_write_CTRLA_reg(hw, SERCOM_SPI_CTRLA_SWRST | mode);
}
hri_sercomspi_wait_for_sync(hw, SERCOM_SPI_SYNCBUSY_SWRST);
dev->prvt = hw;
_spi_load_regs_master(hw, regs);
/* If enabled, initialize DMA rx channel */
if (_spi_is_rx_dma_channel_enabled(hw)) {
_dma_get_channel_resource(&dev->resource, _spi_get_rx_dma_channel(hw));
dev->resource->back = dev;
dev->resource->dma_cb.transfer_done = _spi_dma_rx_complete;
dev->resource->dma_cb.error = _spi_dma_error_occured;
}
/* Initialize DMA tx channel */
_dma_get_channel_resource(&dev->resource, _spi_get_tx_dma_channel(hw));
dev->resource->back = dev;
dev->resource->dma_cb.transfer_done = _spi_dma_tx_complete;
dev->resource->dma_cb.error = _spi_dma_error_occured;
return ERR_NONE;
}
int32_t _spi_m_dma_deinit(struct _spi_m_dma_dev *dev)
{
return _spi_deinit(dev->prvt);
}
int32_t _spi_m_dma_enable(struct _spi_m_dma_dev *dev)
{
ASSERT(dev && dev->prvt);
return _spi_sync_enable(dev->prvt);
}
int32_t _spi_m_dma_disable(struct _spi_m_dma_dev *dev)
{
ASSERT(dev && dev->prvt);
return _spi_sync_disable(dev->prvt);
}
int32_t _spi_m_dma_set_mode(struct _spi_m_dma_dev *dev, const enum spi_transfer_mode mode)
{
ASSERT(dev && dev->prvt);
return _spi_set_mode(dev->prvt, mode);
}
int32_t _spi_m_dma_set_baudrate(struct _spi_m_dma_dev *dev, const uint32_t baud_val)
{
ASSERT(dev && dev->prvt);
return _spi_set_baudrate(dev->prvt, baud_val);
}
int32_t _spi_m_dma_set_data_order(struct _spi_m_dma_dev *dev, const enum spi_data_order dord)
{
ASSERT(dev && dev->prvt);
return _spi_set_data_order(dev->prvt, dord);
}
int32_t _spi_m_dma_set_char_size(struct _spi_m_dma_dev *dev, const enum spi_char_size char_size)
{
uint8_t size;
ASSERT(dev && dev->prvt);
_spi_set_char_size(dev->prvt, char_size, &size);
return size;
}
void _spi_m_dma_register_callback(struct _spi_m_dma_dev *dev, enum _spi_dma_dev_cb_type type, _spi_dma_cb_t func)
{
switch (type) {
case SPI_DEV_CB_DMA_TX:
dev->callbacks.tx = func;
_dma_set_irq_state(_spi_get_tx_dma_channel(dev->prvt), DMA_TRANSFER_COMPLETE_CB, func != NULL);
break;
case SPI_DEV_CB_DMA_RX:
dev->callbacks.rx = func;
_dma_set_irq_state(_spi_get_rx_dma_channel(dev->prvt), DMA_TRANSFER_COMPLETE_CB, func != NULL);
break;
case SPI_DEV_CB_DMA_ERROR:
dev->callbacks.error = func;
_dma_set_irq_state(_spi_get_rx_dma_channel(dev->prvt), DMA_TRANSFER_ERROR_CB, func != NULL);
_dma_set_irq_state(_spi_get_tx_dma_channel(dev->prvt), DMA_TRANSFER_ERROR_CB, func != NULL);
break;
case SPI_DEV_CB_DMA_N:
break;
}
}
int32_t _spi_m_dma_transfer(struct _spi_m_dma_dev *dev, uint8_t const *txbuf, uint8_t *const rxbuf,
const uint16_t length)
{
const struct sercomspi_regs_cfg *regs = _spi_get_regs((uint32_t)dev->prvt);
uint8_t rx_ch = _spi_get_rx_dma_channel(dev->prvt);
uint8_t tx_ch = _spi_get_tx_dma_channel(dev->prvt);
if (rxbuf) {
/* Enable spi rx */
_spi_m_dma_rx_enable(dev);
_dma_set_source_address(rx_ch, (void *)_spi_m_get_source_for_dma(dev->prvt));
_dma_set_destination_address(rx_ch, rxbuf);
_dma_set_data_amount(rx_ch, length);
_dma_enable_transaction(rx_ch, false);
} else {
/* Disable spi rx */
_spi_m_dma_rx_disable(dev);
}
if (txbuf) {
/* Enable spi tx */
_dma_set_source_address(tx_ch, txbuf);
_dma_set_destination_address(tx_ch, (void *)_spi_m_get_destination_for_dma(dev->prvt));
_dma_srcinc_enable(tx_ch, true);
_dma_set_data_amount(tx_ch, length);
} else {
_dma_set_source_address(tx_ch, &regs->dummy_byte);
_dma_set_destination_address(tx_ch, (void *)_spi_m_get_destination_for_dma(dev->prvt));
_dma_srcinc_enable(tx_ch, false);
_dma_set_data_amount(tx_ch, length);
}
_dma_enable_transaction(tx_ch, false);
return ERR_NONE;
}

View File

@@ -9,6 +9,17 @@
#ifndef INTERRUPTS_H_
#define INTERRUPTS_H_
// ----------------------------------------------------------------------
// Master/Slave IF Callback
// ----------------------------------------------------------------------
static void b2bTransferComplete_cb(struct _dma_resource *resource)
{
gpio_set_pin_level(SPI1_CS, true);
}
// ----------------------------------------------------------------------
// ADC Callback for Motor Phase Current Measurement.
// Phase A & B Sampled and converted from LSB to Process Unit PU(Amps)

View File

@@ -7,10 +7,31 @@
#include "bldc_types.h"
#include "EtherCAT_QSPI.h"
#include "EtherCAT_SlaveDef.h"
//#include "MSIF_master.h"
#include "configuration.h"
#include "interrupts.h"
#include "statemachine.h"
#define MASTER_BUFFER_SIZE 64
struct SPI_slaveboard {
struct spi_m_dma_descriptor *SPI_Mn;
uint8_t state;
uint32_t SS_pin;
uint32_t *tx_buffer;
uint32_t *rx_buffer;
};
struct SPI_slaveboard Slave_1 = {
.SPI_Mn = &SPI_1_MSIF,
.state = 0,
.SS_pin = SPI1_CS,
.tx_buffer = &QSPI_tx_buffer[16],
.rx_buffer = &QSPI_rx_buffer[16],
};
void process_currents()
{
@@ -56,6 +77,13 @@ static void One_ms_cycle_callback(const struct timer_task *const timer_task)
update_telemetry();
update_setpoints();
/*Master Slave Transfer */
//tx_buffer[0] += 1;
//tx_buffer[31] += 1;
//gpio_set_pin_level(SPI1_CS, false);
//spi_m_dma_transfer(&SPI_1_MSIF, (uint8_t*)Slave_1.tx_buffer, (uint8_t*)Slave_1.rx_buffer, MASTER_BUFFER_SIZE);
//run_ECAT = true;
}
@@ -173,6 +201,7 @@ int main(void)
configure_tcc_pwm();
adc_sync_enable_channel(&ADC_1, 6);
adc_init_dma();
boardToBoardTransferInit();
ECAT_STATE_MACHINE();
One_ms_timer_init();
custom_logic_enable();