diff --git a/drivers/dac101c085.c b/drivers/dac101c085.c new file mode 100644 index 0000000..6c5662b --- /dev/null +++ b/drivers/dac101c085.c @@ -0,0 +1,46 @@ +/* + * dac101c085.c + * + * Created on: 21 Jul 2019 + * Author: maximilian + */ + +#include "dac101c085.h" + +static uint8_t i2c_initialized = 0; + +void init(void) +{ + if (!i2c_initialized) { + i2cInit(I2Cx_DAC); + i2c_initialized = 1; + } +} + +void setDAC(uint16_t new_value) +{ + uint8_t ub = (new_value >> 6) & 0x0F; + //uint8_t ub = 0x10; + uint8_t lb = (new_value << 2) & 0xFF; + init(); + osPrintf("Upper %d\n", ub); + osPrintf("Lower %d\n", lb); + i2cStartTransmission(I2Cx_DAC, I2C_Direction_Transmitter, DAC_ADDR); + i2cWrite(I2Cx_DAC, &ub); + i2cWrite(I2Cx_DAC, &lb); + i2cEndTransmission(I2Cx_DAC); +} + +uint16_t readDAC(void) +{ + uint16_t dac_val = 1; + i2cStartTransmission(I2Cx_DAC, I2C_Direction_Receiver, DAC_ADDR); + i2cAckOn(I2Cx_DAC); + dac_val = i2cRead(I2Cx_DAC); + i2cAckOff(I2Cx_DAC); + dac_val = (dac_val<<8); + dac_val |= i2cRead(I2Cx_DAC); + i2cEndTransmission(I2Cx_DAC); + return dac_val>>2; +} + diff --git a/drivers/dac101c085.h b/drivers/dac101c085.h new file mode 100644 index 0000000..468da2c --- /dev/null +++ b/drivers/dac101c085.h @@ -0,0 +1,32 @@ +/* + * dac101c085.h + * + * Created on: 21 Jul 2019 + * Author: maximilian + */ + +#ifndef DRIVERS_DAC101C085_H_ +#define DRIVERS_DAC101C085_H_ + +#include +#include "../platform/i2c.h" +#include "../os/error.h" + +#define DAC_ADDR 78 +#define I2Cx_DAC I2C1 + +/** Enum for power down mode. + * + */ +typedef enum +{ + S_PD_2K5, + S_PD_100K, + S_HIGH_IMP +} powerDown_t; + +void setDAC(uint16_t new_value); +uint16_t readDAC(void); +void powerDown(powerDown_t state); + +#endif /* DRIVERS_DAC101C085_H_ */ diff --git a/main.c b/main.c index 762904d..9cd602f 100644 --- a/main.c +++ b/main.c @@ -1,6 +1,7 @@ #include #include #include "platform/porting.h" +#include "drivers/dac101c085.h" #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wunused-parameter" @@ -12,15 +13,25 @@ static char* args_task_3= "task 3"; void task3(void* ptr) { static uint32_t wakeup = 0; + static int cnt = 0; char* args = (char*)ptr; wakeup = osSchedulerGetSysT(); - DEBUG_MSG("This is %s\n\r", args); - osTaskDelayUntil(wakeup, MS_2_TICKS(3000)); + if (cnt*10 >= 1023) { + cnt = 0; + } else { + cnt += 10; + } + osPrintf("Writing DAC: %d\n\r", cnt*10); + setDAC(cnt*10); + uint16_t dac_val = readDAC(); + osPrintf("Reading DAC: %d\n\r", dac_val); + osPrintf("This is %s\n\r", args); + osTaskDelayUntil(wakeup, MS_2_TICKS(1000)); } -int -main(int argc, char* argv[]) +int main(int argc, char* argv[]) { + char args[] = "number 3"; initClock(); initAliveLED(); usart2Init(); @@ -28,7 +39,7 @@ main(int argc, char* argv[]) RCC_GetClocksFreq (&RCC_Clocks); osPrintf("System Core Clock: %d\n\r", SystemCoreClock); osPrintf("HCLK: %d\n\r", RCC_Clocks.HCLK_Frequency); - osTaskCreate(*task3, "Task 3", args_task_3, 10, NULL); + osTaskCreate(*task3, "task 3", args, 1, NULL); while (1); // Infinite loop, never return. } diff --git a/os/error.h b/os/error.h index 0b81d4d..546fad9 100644 --- a/os/error.h +++ b/os/error.h @@ -40,7 +40,7 @@ //--------------Funtions----------------- -/** Creating a error message string from inter alia an error code. +/** Creating a error message string from internal alias, an error code. * * @param ifile Filename where error occurs. * @param iline Line where error occurs. diff --git a/os/ossettings.h b/os/ossettings.h index 1e4c110..8f91de3 100644 --- a/os/ossettings.h +++ b/os/ossettings.h @@ -22,7 +22,7 @@ /* Timing */ // TODO: Adjust this: -#define SYS_TICK_MS 50 +#define SYS_TICK_MS 100 /* Don't adjust this ;) */ #if (SYS_TICK_MS <= 100) #define SYS_TICK_PERIOD_MS SYS_TICK_MS @@ -58,6 +58,6 @@ #define STD_STRING_BUFFER_SIZE 128 /* Debugging ON == 1 or OFF == 0 */ -#define DEBUG_MODE OFF +#define DEBUG_MODE ON #endif /* OS_SETTINGS_H */ diff --git a/os/ostypes.h b/os/ostypes.h index 5a85cf0..af6312f 100644 --- a/os/ostypes.h +++ b/os/ostypes.h @@ -63,6 +63,7 @@ typedef enum E_WRONG_USAGE_OF_PRINTF, E_USART_RX_BUFFER_OVERLOW, E_USART_TX_BUFFER_OVERLOW, + E_I2C_NON_EXISTANT, E_PRINTF_WENT_WRONG } osError_t; diff --git a/platform/i2c.c b/platform/i2c.c index c91128a..81e7f57 100644 --- a/platform/i2c.c +++ b/platform/i2c.c @@ -1,48 +1,121 @@ -#include - -void initI2C(I2C_TypeDef* i2cx , uint32_t speed, uint16_t own_address) -{ - GPIO_InitTypeDef GPIO_InitStructure; - I2C_InitTypeDef I2C_InitStructure; - // Enable GPIOB clocks - RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE); - // Configure I2C clock and GPIO - GPIO_StructInit (& GPIO_InitStructure); - if (i2cx == I2C1){ - // I2C1 clock enable - RCC_APB1PeriphClockCmd (RCC_APB1Periph_I2C1 , ENABLE); - // I2C1 SDA and SCL configuration - GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6 | GPIO_Pin_7 ; - GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz ; - GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_OD ; - GPIO_Init(GPIOB, &GPIO_InitStructure ); - // I2C1 Reset - RCC_APB1PeriphResetCmd(RCC_APB1Periph_I2C1, ENABLE); - RCC_APB1PeriphResetCmd(RCC_APB1Periph_I2C1, DISABLE); +#include "i2c.h" +#include "stm32f10x_i2c.h" +#include "stm32f10x_gpio.h" +#include "porting.h" + +void i2cInit(I2C_TypeDef* I2Cx) +{ + if (I2Cx == I2C1) { + i2c1Init(); } - else { // I2C2 ... + else { + THROW_ERROR(E_I2C_NON_EXISTANT); } - // I2C configuration - I2C_StructInit(&I2C_InitStructure); - I2C_InitStructure.I2C_Mode = I2C_Mode_I2C; - I2C_InitStructure.I2C_DutyCycle = I2C_DutyCycle_2; - I2C_InitStructure.I2C_OwnAddress1 = own_address; - I2C_InitStructure.I2C_Ack = I2C_Ack_Enable; - I2C_InitStructure.I2C_AcknowledgedAddress = I2C_AcknowledgedAddress_7bit; - I2C_InitStructure.I2C_ClockSpeed = speed; - I2C_Init(i2cx, &I2C_InitStructure); - I2C_Cmd(i2cx, ENABLE); -} - -//uint8_t pingI2C (I2C_TypeDef* i2cx, uint8_t SlaveAddress) -//{ -// __IO uint32_t Timeout = 0; -// Timed ( I2C_GetFlagStatus (I2Cx , I2C_FLAG_BUSY )); -// // Intiate Start Sequence -// I2C_GenerateSTART (I2Cx , ENABLE ); -// Timed (! I2C_CheckEvent (I2Cx , I2C_EVENT_MASTER_MODE_SELECT)); -// // Send Address EV5 -// I2C_Send7bitAddress (I2Cx , SlaveAddress, I2C_Direction_Transmitter); -// Timed (! I2C_CheckEvent (I2Cx, I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)); -// return 0; -//} +} + +void i2c1Init(void) +{ + // Initialization structs + GPIO_InitTypeDef i2c_gpio; + I2C_InitTypeDef i2c; + // Turn on clocks + RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE); + RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE); + RCC_APB1PeriphClockCmd(RCC_APB1Periph_I2C1, ENABLE); + //Configure I2C module + i2c.I2C_ClockSpeed = 100000; + i2c.I2C_Mode = I2C_Mode_I2C; + i2c.I2C_DutyCycle = I2C_DutyCycle_2; + i2c.I2C_OwnAddress1 = 0x15; + i2c.I2C_Ack = I2C_Ack_Enable; + i2c.I2C_AcknowledgedAddress = I2C_AcknowledgedAddress_7bit; + I2C_Init(I2C1, &i2c); + //Additionally we need to initialize corresponding GPIOs + i2c_gpio.GPIO_Pin = GPIO_Pin_6 | GPIO_Pin_7; + i2c_gpio.GPIO_Mode = GPIO_Mode_AF_OD; // Open drain only if you have pull-up resistors + i2c_gpio.GPIO_Speed = GPIO_Speed_50MHz; + GPIO_Init(GPIOB, &i2c_gpio); + // Enable I2C 1 + I2C_Cmd(I2C1, ENABLE); + DEBUG_MSG("I2C1 initialized."); +} + +uint8_t i2cPing(I2C_TypeDef* I2Cx, uint8_t slave_addr) +{ + DEBUG_MSG("Searching for: %d\n", slave_addr); + // Wait until I2Cx is not busy anymore + while (I2C_GetFlagStatus(I2Cx, I2C_FLAG_BUSY)); + // Generate start condition + I2C_GenerateSTART(I2Cx, ENABLE); + while (!I2C_CheckEvent(I2Cx, I2C_EVENT_MASTER_MODE_SELECT)); + // Send slave address + I2C_Send7bitAddress(I2Cx, slave_addr<<1, I2C_Direction_Transmitter); + // Wait for I2C EV5. + volatile uint32_t timeout = 0xFFFF; + while(!I2C_CheckEvent(I2Cx, I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)) { + if (timeout == 0) { + break; + } else { + timeout--; + } + } + I2C_GenerateSTOP(I2Cx, ENABLE); + if (timeout > 0) { + DEBUG_MSG("Slave found\n\r"); + return 1; + } else { + DEBUG_MSG("Slave not found\n\r"); + } + return 0; +} + +void i2cStartTransmission(I2C_TypeDef* I2Cx, uint8_t dir, uint8_t slave_addr) +{ + // Wait for I2C module to become ready + while(I2C_GetFlagStatus(I2Cx, I2C_FLAG_BUSY)); + // Generate I2C start condition + I2C_GenerateSTART(I2Cx, ENABLE); + // Waiting for EV5 + while(!I2C_CheckEvent(I2Cx, I2C_EVENT_MASTER_MODE_SELECT)); + // The 7 bit address needs to be shifted by 1 + I2C_Send7bitAddress(I2Cx, slave_addr<<1, dir); + // Depending on whether the master is reading or writing another event is triggered + if(dir== I2C_Direction_Transmitter) + { + while(!I2C_CheckEvent(I2Cx, I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)); + } + if(dir== I2C_Direction_Receiver) + { + while(!I2C_CheckEvent(I2Cx, I2C_EVENT_MASTER_RECEIVER_MODE_SELECTED)); + } +} + +void i2cWrite(I2C_TypeDef* I2Cx, uint8_t* data) +{ + I2C_SendData(I2Cx, *data); + while(!I2C_CheckEvent(I2Cx, I2C_EVENT_MASTER_BYTE_TRANSMITTED)); + //while(!I2C_GetFlagStatus(I2Cx, I2C_FLAG_BTF)); +} + +void i2cAckOn(I2C_TypeDef* I2Cx) +{ + I2C_AcknowledgeConfig(I2Cx, ENABLE); +} + +void i2cAckOff(I2C_TypeDef* I2Cx) +{ + I2C_AcknowledgeConfig(I2Cx, DISABLE); +} + +uint8_t i2cRead(I2C_TypeDef* I2Cx) +{ + while(!I2C_CheckEvent(I2Cx, I2C_EVENT_MASTER_BYTE_RECEIVED)); + uint8_t data = I2C_ReceiveData(I2Cx); + return data; +} + +void i2cEndTransmission(I2C_TypeDef* I2Cx) +{ + I2C_GenerateSTOP(I2Cx, ENABLE); + while(I2C_GetFlagStatus(I2C1, I2C_FLAG_STOPF)); +} diff --git a/platform/i2c.h b/platform/i2c.h index 3a8a069..55b9923 100644 --- a/platform/i2c.h +++ b/platform/i2c.h @@ -11,10 +11,11 @@ #include "stm32f10x.h" #include -# define Timed (x) Timeout = 0xFFFF; while (x) \ -{ if (Timeout -- == 0) goto errReturn ;} - -void initI2C(I2C_TypeDef* i2cx , uint32_t speed, uint16_t own_address); -//uint8_t pingI2C (I2C_TypeDef* i2cx, uint8_t SlaveAddress); +void i2cInit(I2C_TypeDef* I2Cx); +void i2c1Init(void); +void i2cStartTransmission(I2C_TypeDef* I2Cx, uint8_t dir, uint8_t slave_addr); +void i2cWrite(I2C_TypeDef* I2Cx, uint8_t* data); +uint8_t i2cRead(I2C_TypeDef* I2Cx); +void i2cEndTransmission(I2C_TypeDef* I2Cx); #endif /* PLATFORM_I2C_H_ */ diff --git a/platform/usart.c b/platform/usart.c index 1ab92f0..6e6b8c6 100644 --- a/platform/usart.c +++ b/platform/usart.c @@ -42,7 +42,7 @@ void usart2Init(void) /* Init. USART2 peripheral. */ USART_InitTypeDef USART_InitStructure ; USART_StructInit(&USART_InitStructure ); - USART_InitStructure.USART_BaudRate = 9600; + USART_InitStructure.USART_BaudRate = 230400; USART_InitStructure.USART_WordLength = USART_StopBits_1; USART_InitStructure.USART_Parity = USART_Parity_No; USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;