/** @brief I2C Set clock duty cycle @param[in] i2c Unsigned int32. I2C register base address @ref i2c_reg_base. @param[in] dutycycle Unsigned int32. I2C duty cycle @ref i2c_duty_cycle. */ void i2c_set_dutycycle(u32 i2c, u32 dutycycle) { if (dutycycle == I2C_CCR_DUTY_DIV2) I2C_CCR(i2c) &= ~I2C_CCR_DUTY; else I2C_CCR(i2c) |= I2C_CCR_DUTY; }
void i2c_set_ccr(uint32_t i2c, uint16_t freq) { uint16_t reg16; reg16 = I2C_CCR(i2c) & 0xf000; /* Clear bits [11:0]. */ reg16 |= freq; I2C_CCR(i2c) = reg16; }
void i2c_set_ccr(u32 i2c, u16 freq) { u16 reg16; reg16 = I2C_CCR(i2c) & 0xf000; /* Clear bits [11:0]. */ reg16 |= freq; I2C_CCR(i2c) = reg16; }
/** @brief I2C Set clock duty cycle @param[in] i2c Unsigned int32. I2C register base address @ref i2c_reg_base. @param[in] dutycycle Unsigned int32. I2C duty cycle @ref i2c_duty_cycle. */ void i2c_set_dutycycle(uint32_t i2c, uint32_t dutycycle) { if (dutycycle == I2C_CCR_DUTY_DIV2) { I2C_CCR(i2c) &= ~I2C_CCR_DUTY; } else { I2C_CCR(i2c) |= I2C_CCR_DUTY; } }
static void init_i2c2(void) { *RCC_APB1ENR |= RCC_APB1ENR_I2C2EN; /* Enable I2C2 Clock */ *RCC_AHB1ENR |= RCC_AHB1ENR_GPIOBEN; /* Enable GPIOB Clock */ /* Set PB8 and PB9 to alternative function I2C * See stm32f4_ref.pdf pg 141 and stm32f407.pdf pg 51 */ /* I2C2_SCL */ gpio_moder(GPIOB, I2C2_SCL, GPIO_MODER_ALT); gpio_afr(GPIOB, I2C2_SCL, GPIO_AF_I2C); gpio_otyper(GPIOB, I2C2_SCL, GPIO_OTYPER_OD); gpio_pupdr(GPIOB, I2C2_SCL, GPIO_PUPDR_NONE); gpio_ospeedr(GPIOB, I2C2_SCL, GPIO_OSPEEDR_50M); /* I2C2_SDA */ gpio_moder(GPIOB, I2C2_SDA, GPIO_MODER_ALT); gpio_afr(GPIOB, I2C2_SDA, GPIO_AF_I2C); gpio_otyper(GPIOB, I2C2_SDA, GPIO_OTYPER_OD); gpio_pupdr(GPIOB, I2C2_SDA, GPIO_PUPDR_NONE); gpio_ospeedr(GPIOB, I2C2_SDA, GPIO_OSPEEDR_50M); /* Configure peripheral */ *I2C_CR2(2) |= I2C_CR2_FREQ(42); /* Set I2C to 300kHz */ *I2C_CCR(2) |= I2C_CCR_CCR(140); *I2C_TRISE(2) = 43; /* Enable */ *I2C_CR1(2) |= I2C_CR1_PE; /* Pre-initialized */ //init_semaphore(&i2c2_semaphore); i2c2.ready = 1; }
void i2c_set_standard_mode(uint32_t i2c) { I2C_CCR(i2c) &= ~I2C_CCR_FS; }
void i2c_set_fast_mode(uint32_t i2c) { I2C_CCR(i2c) |= I2C_CCR_FS; }
void i2c_set_standard_mode(u32 i2c) { I2C_CCR(i2c) &= ~I2C_CCR_FS; }
void i2c_set_fast_mode(u32 i2c) { I2C_CCR(i2c) |= I2C_CCR_FS; }
void i2c_setbitrate(struct i2c_periph *periph, int bitrate) { // If NOT Busy if (i2c_idle(periph)) { volatile int devider; volatile int risetime; uint32_t i2c = (uint32_t) periph->reg_addr; /***************************************************** Bitrate: -CR2 + CCR + TRISE registers -only change when PE=0 e.g. 10kHz: 36MHz + Standard 0x708 + 0x25 70kHz: 36MHz + Standard 0x101 + 400kHz: 36MHz + Fast 0x1E + 0xb // 1) Program peripheral input clock CR2: to get correct timings // 2) Configure clock control registers // 3) Configure rise time register ******************************************************/ if (bitrate < 3000) bitrate = 3000; // 36MHz, fast scl: 2counts low 1 count high -> / 3: devider = 18000 / (bitrate/1000); // never allow faster than 600kbps if (devider < 20) devider = 20; // no overflow either if (devider >=4095) devider = 4095; // risetime can be up to 1/6th of the period risetime = 1000000 / (bitrate/1000) / 6 / 28; if (risetime < 10) risetime = 10; // more will overflow the register: for more you should lower the FREQ if (risetime >=31) risetime = 31; // we do not expect an interrupt as the interface should have been idle, but just in case... __disable_irq(); // this code is in user space: // CCR can only be written when PE is disabled // p731 note 5 I2C_CR1(i2c) &= ~ I2C_CR1_PE; // 1) I2C_CR2(i2c) = 0x0324; // 2) //I2C_CCR(i2c) = 0x8000 + devider; I2C_CCR(i2c) = 0x0000 + devider; // 3) I2C_TRISE(i2c) = risetime; // Re-Enable I2C_CR1(i2c) |= I2C_CR1_PE; __enable_irq(); #ifdef I2C_DEBUG_LED __disable_irq(); // this code is in user space: LED2_ON(); LED1_ON(); LED2_OFF(); LED1_OFF(); LED2_ON(); LED1_ON(); LED2_OFF(); LED1_OFF(); __enable_irq(); #endif } }