#include "io4_comp.h" #include "commands.h" #include "hal.h" #include "defines.h" #include #include #include "stm32f4xx_conf.h" #include "hw/hw.h" #include "main.h" #include "common.h" HAL_COMP(io); HAL_PIN(fan); HAL_PIN(state); HAL_PIN(fault); //outputs HAL_PIN(out0); HAL_PIN(out1); HAL_PIN(out2); HAL_PIN(out_freq); HAL_PIN(out_arr); HAL_PIN(out_cnt); HAL_PIN(out_ccr1); HAL_PIN(in0); //input 0, analog HAL_PIN(in1); //input 1, analog HAL_PIN(ind0); //input 0, digital HAL_PIN(ind1); //input 1, digital HAL_PIN(ind0n); //input 0 inverted HAL_PIN(ind1n); //input 0 inverted HAL_PIN(th0); //voltage threshold in0 HAL_PIN(th1); //voltage threshold in1 HAL_PIN(CTX); HAL_PIN(CRX); HAL_PIN(C12); HAL_PIN(C36); HAL_PIN(C54); HAL_PIN(C78); HAL_PIN(cmd_remap); HAL_PIN(swd_remap); HAL_PIN(DIO); HAL_PIN(CK); //rj45 leds HAL_PIN(fb0g); HAL_PIN(fb0y); HAL_PIN(fb1g); HAL_PIN(fb1y); HAL_PIN(cmdg); HAL_PIN(cmdy); HAL_PIN(fb0); HAL_PIN(fb1); HAL_PIN(fbd0); HAL_PIN(fbd1); HAL_PIN(fbd0n); HAL_PIN(fbd1n); HAL_PIN(fbth0); HAL_PIN(fbth1); //a,b,z inputs of fb0 and fb1 HAL_PIN(fb0a); HAL_PIN(fb0b); HAL_PIN(fb0z); HAL_PIN(fb1a); HAL_PIN(fb1b); HAL_PIN(fb1z); HAL_PIN(fbsd); //fb shutdown HAL_PIN(master_arr); HAL_PIN(clock_scale); static void nrt_init(void *ctx_ptr, hal_pin_inst_t *pin_ptr) { struct io_pin_ctx_t *pins = (struct io_pin_ctx_t *)pin_ptr; PIN(th0) = 12.0; PIN(th1) = 12.0; PIN(fbth0) = 2.5; PIN(fbth1) = 2.5; PIN(out_freq) = 15000; PIN(master_arr) = TIM3->ARR; PIN(clock_scale) = 1.0; } static void hw_init(void *ctx_ptr, hal_pin_inst_t *pin_ptr) { // struct io_ctx_t * ctx = (struct io_ctx_t *)ctx_ptr; struct io_pin_ctx_t *pins = (struct io_pin_ctx_t *)pin_ptr; GPIO_InitTypeDef GPIO_InitStructure; ADC_InitTypeDef ADC_InitStructure; //**** ADC3 for analog input and fb temperature //TODO: ADC calibration? GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN; GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_Init(GPIOC, &GPIO_InitStructure); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; GPIO_Init(GPIOD, &GPIO_InitStructure); // out1, out2 pwm tim9 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5 | GPIO_Pin_6; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF; GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_Init(GPIOE, &GPIO_InitStructure); GPIO_PinAFConfig(GPIOE, GPIO_PinSource5, GPIO_AF_TIM9); GPIO_PinAFConfig(GPIOE, GPIO_PinSource6, GPIO_AF_TIM9); if(PIN(swd_remap) > 0) { GPIO_InitStructure.GPIO_Pin = GPIO_Pin_13 | GPIO_Pin_14; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; GPIO_Init(GPIOA, &GPIO_InitStructure); } RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC3, ENABLE); ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right; //data converted will be shifted to right ADC_InitStructure.ADC_Resolution = ADC_Resolution_12b; //Input voltage is converted into a 12bit number giving a maximum value of 4096 ADC_InitStructure.ADC_ContinuousConvMode = DISABLE; //the conversion is continuous, the input data is converted more than once ADC_InitStructure.ADC_ExternalTrigConv = TIM_MASTER_ADC; //trigger on rising edge of TIM_MASTER oc ADC_InitStructure.ADC_ExternalTrigConvEdge = ADC_ExternalTrigConvEdge_Rising; ADC_InitStructure.ADC_NbrOfConversion = 1; //ADC_ANZ;//I think this one is clear :p ADC_InitStructure.ADC_ScanConvMode = ENABLE; //The scan is configured in one channel ADC_InitStructure.ADC_ExternalTrigConvEdge = ADC_ExternalTrigConvEdge_None; ADC_Init(ADC3, &ADC_InitStructure); ADC_InjectedSequencerLengthConfig(ADC3, 4); ADC_InjectedChannelConfig(ADC3, ADC_Channel_10, 1, ADC_SampleTime_144Cycles); ADC_InjectedChannelConfig(ADC3, ADC_Channel_11, 2, ADC_SampleTime_144Cycles); ADC_InjectedChannelConfig(ADC3, ADC_Channel_12, 3, ADC_SampleTime_144Cycles); ADC_InjectedChannelConfig(ADC3, ADC_Channel_13, 4, ADC_SampleTime_144Cycles); ADC_Cmd(ADC3, ENABLE); ADC_SoftwareStartInjectedConv(ADC3); //**** ADC3 end GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; //fan GPIO_InitStructure.GPIO_Pin = GPIO_Pin_3; GPIO_Init(GPIOE, &GPIO_InitStructure); //red GPIO_InitStructure.GPIO_Pin = GPIO_Pin_3; GPIO_Init(GPIOD, &GPIO_InitStructure); //yellow GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4; GPIO_Init(GPIOD, &GPIO_InitStructure); //green GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5; GPIO_Init(GPIOD, &GPIO_InitStructure); //in1 led GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0; GPIO_Init(GPIOE, &GPIO_InitStructure); //in0 led GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1; GPIO_Init(GPIOE, &GPIO_InitStructure); //out0 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4; GPIO_Init(GPIOE, &GPIO_InitStructure); // //out1 // GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5; // GPIO_Init(GPIOE, &GPIO_InitStructure); // //out2 // GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6; // GPIO_Init(GPIOE, &GPIO_InitStructure); RCC->APB2ENR |= RCC_APB2ENR_TIM9EN; TIM9->ARR = 186000000 / 300 / 15000; // 15000Hz TIM9->PSC = 300 - 1; // 186e6 / 300 = 620000Hz max freq TIM9->CCMR1 = TIM_CCMR1_OC1M_1 | TIM_CCMR1_OC1M_2 | TIM_CCMR1_OC2M_1 | TIM_CCMR1_OC2M_2; // pwm mode 1 TIM9->CCER = TIM_CCER_CC1E | TIM_CCER_CC2E; // cc1, cc2 enable TIM9->CCR1 = 0; TIM9->CCR2 = 0; TIM9->CR1 = TIM_CR1_ARPE; // preloade TIM9->CR1 |= TIM_CR1_CEN; // counter enable //fb0 green GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8; GPIO_Init(GPIOD, &GPIO_InitStructure); //fb0 yellow GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9; GPIO_Init(GPIOD, &GPIO_InitStructure); //fb1 green GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7; GPIO_Init(GPIOE, &GPIO_InitStructure); //fb1 yellow GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8; GPIO_Init(GPIOE, &GPIO_InitStructure); //cmd // GPIO_InitStructure.GPIO_Pin = CMD_C_EN_PIN; // GPIO_Init(CMD_C_EN_PORT, &GPIO_InitStructure); // // GPIO_InitStructure.GPIO_Pin = CMD_D_EN_PIN; // GPIO_Init(CMD_D_EN_PORT, &GPIO_InitStructure); //cmd yellow GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6; GPIO_Init(GPIOD, &GPIO_InitStructure); //cmd green GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7; GPIO_Init(GPIOD, &GPIO_InitStructure); //fb 5v enable GPIO_SetBits(GPIOC, GPIO_Pin_13); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_13; GPIO_Init(GPIOC, &GPIO_InitStructure); if(PIN(cmd_remap) > 0) { // CMD EN GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; GPIO_InitStructure.GPIO_Pin = CMD_A_EN_PIN; GPIO_Init(CMD_A_EN_PORT, &GPIO_InitStructure); GPIO_InitStructure.GPIO_Pin = CMD_B_EN_PIN; GPIO_Init(CMD_B_EN_PORT, &GPIO_InitStructure); GPIO_InitStructure.GPIO_Pin = CMD_C_EN_PIN; GPIO_Init(CMD_C_EN_PORT, &GPIO_InitStructure); GPIO_SetBits(CMD_A_EN_PORT, CMD_A_EN_PIN); GPIO_SetBits(CMD_B_EN_PORT, CMD_B_EN_PIN); GPIO_SetBits(CMD_C_EN_PORT, CMD_C_EN_PIN); } } #include "../shared/hw_math.h" #define ARES 4096.0 #define AREF 3.3 static void frt_func(float period, void *ctx_ptr, hal_pin_inst_t *pin_ptr) { struct io_pin_ctx_t *pins = (struct io_pin_ctx_t *)pin_ptr; if(PIN(clock_scale) > 1.01){ TIM3->ARR = PIN(master_arr) + 1; } else if(PIN(clock_scale) < 0.99){ TIM3->ARR = PIN(master_arr) - 1; } else{ TIM3->ARR = PIN(master_arr); } } static void rt_func(float period, void *ctx_ptr, hal_pin_inst_t *pin_ptr) { // struct io_ctx_t * ctx = (struct io_ctx_t *)ctx_ptr; struct io_pin_ctx_t *pins = (struct io_pin_ctx_t *)pin_ptr; uint32_t red = 0; uint32_t green = 0; uint32_t yellow = 0; //TODO: unit conversion //TODO: check if adc sample complete? float in0 = V2(ADC2V(ADC_GetInjectedConversionValue(ADC3, ADC_InjectedChannel_1)), 3.3, 1000.0, 10000.0, 1000.0); float in1 = V2(ADC2V(ADC_GetInjectedConversionValue(ADC3, ADC_InjectedChannel_2)), 3.3, 1000.0, 10000.0, 1000.0); PIN(in0) = in0; PIN(in1) = in1; if(in0 > PIN(th0) + 0.1) { PIN(ind0) = 1.0; PIN(ind0n) = 0.0; GPIO_SetBits(GPIOE, GPIO_Pin_1); } else if(in0 < PIN(th0) - 0.1) { PIN(ind0) = 0.0; PIN(ind0n) = 1.0; GPIO_ResetBits(GPIOE, GPIO_Pin_1); } if(in1 > PIN(th1) + 0.1) { PIN(ind1) = 1.0; PIN(ind1n) = 0.0; GPIO_SetBits(GPIOE, GPIO_Pin_0); } else if(in1 < PIN(th1) - 0.1) { PIN(ind1) = 0.0; PIN(ind1n) = 1.0; GPIO_ResetBits(GPIOE, GPIO_Pin_0); } in0 = V3(ADC2V(ADC_GetInjectedConversionValue(ADC3, ADC_InjectedChannel_3)), 10000.0, 1000.0); in1 = V3(ADC2V(ADC_GetInjectedConversionValue(ADC3, ADC_InjectedChannel_4)), 10000.0, 1000.0); PIN(fb0) = in0; PIN(fb1) = in1; ADC_SoftwareStartInjectedConv(ADC3); if(in0 > PIN(fbth0) + 0.1) { PIN(fbd0) = 1.0; PIN(fbd0n) = 0.0; } else if(in0 < PIN(fbth0) - 0.1) { PIN(fbd0) = 0.0; PIN(fbd0n) = 1.0; } if(in1 > PIN(fbth1) + 0.1) { PIN(fbd1) = 1.0; PIN(fbd1n) = 0.0; } else if(in1 < PIN(fbth1) - 0.1) { PIN(fbd1) = 0.0; PIN(fbd1n) = 1.0; } if(PIN(swd_remap) > 0) { PIN(DIO) = GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_13); PIN(CK) = GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_14); } switch((state_t)PIN(state)) { case DISABLED: red = 0; green = 0; yellow = 1; break; case ENABLED: red = 0; green = 1; yellow = 0; break; case PHASING: red = 0; green = 1; yellow = 1; break; case SOFT_FAULT: red = BLINK((int)PIN(fault)); green = 0; yellow = 0; break; case HARD_FAULT: red = BLINK((int)PIN(fault)); green = BLINK((int)PIN(fault)); yellow = BLINK((int)PIN(fault)); break; case LED_TEST: red = 1; green = 1; yellow = 1; break; } if(red > 0) GPIO_SetBits(GPIOD, GPIO_Pin_3); else GPIO_ResetBits(GPIOD, GPIO_Pin_3); if(yellow > 0) GPIO_SetBits(GPIOD, GPIO_Pin_4); else GPIO_ResetBits(GPIOD, GPIO_Pin_4); if(green > 0) GPIO_SetBits(GPIOD, GPIO_Pin_5); else GPIO_ResetBits(GPIOD, GPIO_Pin_5); if(PIN(out0) > 0) GPIO_SetBits(GPIOE, GPIO_Pin_4); else GPIO_ResetBits(GPIOE, GPIO_Pin_4); // if(PIN(out1) > 0) // GPIO_SetBits(GPIOE, GPIO_Pin_5); // else // GPIO_ResetBits(GPIOE, GPIO_Pin_5); // if(PIN(out2) > 0) // GPIO_SetBits(GPIOE, GPIO_Pin_6); // else // GPIO_ResetBits(GPIOE, GPIO_Pin_6); TIM9->ARR = 186000000 / 300 / MAX(PIN(out_freq), 10); TIM9->CCR1 = CLAMP(PIN(out1), 0, 1) * TIM9->ARR; TIM9->CCR2 = CLAMP(PIN(out2), 0, 1) * TIM9->ARR; PIN(out_cnt) = TIM9->CNT; PIN(out_arr) = TIM9->ARR; PIN(out_ccr1) = TIM9->CCR1; if(PIN(fb0g) > 0) GPIO_SetBits(GPIOD, GPIO_Pin_8); else GPIO_ResetBits(GPIOD, GPIO_Pin_8); if(PIN(fb0y) > 0) GPIO_SetBits(GPIOD, GPIO_Pin_9); else GPIO_ResetBits(GPIOD, GPIO_Pin_9); if(PIN(fb1g) > 0) GPIO_SetBits(GPIOE, GPIO_Pin_7); else GPIO_ResetBits(GPIOE, GPIO_Pin_7); if(PIN(fb1y) > 0) GPIO_SetBits(GPIOE, GPIO_Pin_8); else GPIO_ResetBits(GPIOE, GPIO_Pin_8); // if(PIN(cmdc_en) > 0){ // GPIO_SetBits(CMD_C_EN_PORT, CMD_C_EN_PIN); // GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; // GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; // GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; // GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; // GPIO_InitStructure.GPIO_Pin = CMD_C_PIN; // GPIO_Init(CMD_C_PORT, &GPIO_InitStructure); // if(PIN(cmdc) > 0){ // GPIO_SetBits(CMD_C_PORT, CMD_C_PIN); // } // else{ // GPIO_ResetBits(CMD_C_PORT, CMD_C_PIN); // } // } // else{ // GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; // GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; // GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; // GPIO_InitStructure.GPIO_Pin = CMD_C_PIN; // GPIO_Init(CMD_C_PORT, &GPIO_InitStructure); // GPIO_ResetBits(CMD_C_EN_PORT, CMD_C_EN_PIN); // PIN(cmdc) = (CMD_C_PORT->IDR & CMD_C_PIN) > 0; // } // // if(PIN(cmdd_en) > 0){ // GPIO_SetBits(CMD_D_EN_PORT, CMD_D_EN_PIN); // GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; // GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; // GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; // GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; // GPIO_InitStructure.GPIO_Pin = CMD_C_PIN; // GPIO_Init(CMD_D_PORT, &GPIO_InitStructure); // if(PIN(cmdd) > 0){ // GPIO_SetBits(CMD_D_PORT, CMD_D_PIN); // } // else{ // GPIO_ResetBits(CMD_D_PORT, CMD_D_PIN); // } // } // else{ // GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; // GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; // GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; // GPIO_InitStructure.GPIO_Pin = CMD_D_PIN; // GPIO_Init(CMD_D_PORT, &GPIO_InitStructure); // GPIO_ResetBits(CMD_D_EN_PORT, CMD_D_EN_PIN); // PIN(cmdd) = (CMD_D_PORT->IDR & CMD_D_PIN) > 0; // } if(PIN(cmdy) > 0) GPIO_SetBits(GPIOD, GPIO_Pin_6); else GPIO_ResetBits(GPIOD, GPIO_Pin_6); if(PIN(cmdg) > 0) GPIO_SetBits(GPIOD, GPIO_Pin_7); else GPIO_ResetBits(GPIOD, GPIO_Pin_7); if(PIN(fan) > 0) GPIO_SetBits(GPIOE, GPIO_Pin_3); else GPIO_ResetBits(GPIOE, GPIO_Pin_3); if(PIN(fbsd) > 0) GPIO_ResetBits(GPIOC, GPIO_Pin_13); else GPIO_SetBits(GPIOC, GPIO_Pin_13); PIN(CRX) = GPIO_ReadInputDataBit(GPIOD, GPIO_Pin_0); PIN(CTX) = GPIO_ReadInputDataBit(GPIOD, GPIO_Pin_1); PIN(C12) = GPIO_ReadInputDataBit(CMD_A_PORT, CMD_A_PIN); PIN(C36) = GPIO_ReadInputDataBit(CMD_B_PORT, CMD_B_PIN); PIN(C54) = GPIO_ReadInputDataBit(CMD_C_PORT, CMD_C_PIN); PIN(C78) = GPIO_ReadInputDataBit(CMD_D_PORT, CMD_D_PIN); PIN(fb0a) = GPIO_ReadInputDataBit(FB0_A_PORT, FB0_A_PIN); PIN(fb0b) = GPIO_ReadInputDataBit(FB0_B_PORT, FB0_B_PIN); PIN(fb0z) = GPIO_ReadInputDataBit(FB0_Z_PORT, FB0_Z_PIN); PIN(fb1a) = GPIO_ReadInputDataBit(FB1_A_PORT, FB1_A_PIN); PIN(fb1b) = GPIO_ReadInputDataBit(FB1_B_PORT, FB1_B_PIN); PIN(fb1z) = GPIO_ReadInputDataBit(FB1_Z_PORT, FB1_Z_PIN); } hal_comp_t io_comp_struct = { .name = "io", .nrt = 0, .rt = rt_func, .frt = frt_func, .nrt_init = nrt_init, .hw_init = hw_init, .rt_start = 0, .frt_start = 0, .rt_stop = 0, .frt_stop = 0, .ctx_size = 0, .pin_count = sizeof(struct io_pin_ctx_t) / sizeof(struct hal_pin_inst_t), };