__task void serial_process() { UART_Configuration config; int32_t len_data = 0; void *msg; while (1) { // Check our mailbox to see if we need to set anything up with the UART // before we do any sending or receiving if (os_mbx_wait(&serial_mailbox, &msg, 0) == OS_R_OK) { switch((SERIAL_MSG)(unsigned)msg) { case SERIAL_INITIALIZE: uart_initialize(); break; case SERIAL_UNINITIALIZE: uart_uninitialize(); break; case SERIAL_RESET: uart_reset(); break; case SERIAL_SET_CONFIGURATION: serial_get_configuration(&config); uart_set_configuration(&config); break; default: break; } } len_data = USBD_CDC_ACM_DataFree(); if (len_data > SIZE_DATA) { len_data = SIZE_DATA; } if (len_data) { len_data = uart_read_data(data, len_data); } if (len_data) { if(USBD_CDC_ACM_DataSend(data , len_data)) { main_blink_cdc_led(MAIN_LED_OFF); } } len_data = uart_write_free(); if (len_data > SIZE_DATA) { len_data = SIZE_DATA; } if (len_data) { len_data = USBD_CDC_ACM_DataRead(data, len_data); } if (len_data) { if (uart_write_data(data, len_data)) { main_blink_cdc_led(MAIN_LED_OFF); } } } }
int32_t uart_initialize (void) { NVIC_DisableIRQ(UART_IRQn); LPC_SYSCON->SYSAHBCLKCTRL |= ((1UL << 6) | // enable clock for GPIO (1UL << 16) ); // enable clock for IOCON // enable clk for usart LPC_SYSCON->SYSAHBCLKCTRL |= (1UL << 12); // usart clk divider = 1 LPC_SYSCON->UARTCLKDIV = (1UL << 0); // alternate function USART and PullNone LPC_IOCON->PIO0_18 |= 0x01; LPC_IOCON->PIO0_19 |= 0x01; // enable FIFOs (trigger level 1) and clear them LPC_USART->FCR = 0x87; // Transmit Enable LPC_USART->TER = 0x80; // reset uart uart_reset(); // enable rx and tx interrupt LPC_USART->IER |= (1 << 0) | (1 << 1); NVIC_EnableIRQ(UART_IRQn); return 1; }
/********************************************************************* Function: Fwl_UartSetBaudrate Description: change uart baudrate. Input: T_U32 baudrate. Return: true = initialization sucess; false = initialization error. Author: liangxiong Data: 2012-11-20 **********************************************************************/ T_BOOL Fwl_UartSetBaudrate(T_U32 baudrate) { #if 1 return uart_reset(SERIAL_UART, baudrate); #else return AK_TRUE; #endif }
int32_t uart_uninitialize (void) { // disable interrupt LPC_USART->IER &= ~(0x7); NVIC_DisableIRQ(UART_IRQn); // reset uart uart_reset(); return 1; }
int32_t uart_initialize (void) { RCC->APB2ENR |= ( 1UL << 0); /* enable clock Alternate Function */ AFIO->MAPR &= ~( 1UL << 2); /* clear USART1 remap */ RCC->APB2ENR |= ( 1UL << 2); /* enable GPIOA clock */ GPIOA->CRH &= ~(0xFFUL << 4); /* clear PA9, PA10 */ GPIOA->CRH |= (0x0BUL << 4); /* USART1 Tx (PA9) output push-pull*/ GPIOA->CRH |= (0x04UL << 8); /* USART1 Rx (PA10) input floating */ RCC->APB2ENR |= ( 1UL << 14); /* enable USART1 clock */ uart_reset (); NVIC_EnableIRQ(USART1_IRQn); /* Enable USART interrupt */ return 1; }
/* CENTRAL: Callback handling NUS Client events. Handling events from the ble_nus_c module. This function is called to notify the application of NUS client events. Parameters: p_ble_nus_c NUS Client Handle. This identifies the NUS client p_ble_nus_evt Pointer to the NUS Client event. */ static void ble_nus_c_evt_handler(ble_nus_c_t * p_ble_nus_c, const ble_nus_c_evt_t * p_ble_nus_evt) { uint32_t err_code; switch (p_ble_nus_evt->evt_type) { case BLE_NUS_C_EVT_FOUND_NUS_TX_CHARACTERISTIC: { /* TX characteristic found */ break; } case BLE_NUS_C_EVT_FOUND_NUS_RX_CHARACTERISTIC: { /* RX characteristic found: enable notification on that */ err_code = ble_nus_c_rx_notif_enable(p_ble_nus_c); APP_ERROR_CHECK(err_code); break; } case BLE_NUS_C_EVT_NUS_RX_EVT: { /* send received data from NUS to uart interface */ for (uint32_t i = 0; i < p_ble_nus_evt->data_len; i++) { while(app_uart_put( p_ble_nus_evt->p_data[i]) != NRF_SUCCESS); } app_uart_put('.'); break; } case BLE_NUS_C_EVT_DISCONNECTED: { /* clear related connection handle */ active_conn_handles[pending_nus_conn_index] = BLE_CONN_HANDLE_INVALID; /* reset pending NUS connection index */ pending_nus_conn_index = 0xFF; /* reset uart */ uart_reset(); /* set "connection" pin as disconnected */ nrf_gpio_pin_write(CONN_PIN_NUMBER, DISCONNECTED_PIN_STATE); /* send confirmation string */ uart_send_string((uint8_t *)"OK.", 3); break; } } }
struct uart_softc * uart_init(uart_intr_func_t intr_assert, uart_intr_func_t intr_deassert, void *arg) { struct uart_softc *sc; sc = calloc(1, sizeof(struct uart_softc)); sc->arg = arg; sc->intr_assert = intr_assert; sc->intr_deassert = intr_deassert; pthread_mutex_init(&sc->mtx, NULL); uart_reset(sc); return (sc); }
void enter_power_down() { int i; unsigned int uboot_cmd_flag=readl(P_AO_RTI_STATUS_REG2);//u-boot suspend cmd flag unsigned int vcin_state = 0; int voltage = 0; int axp_ocv = 0; int wdt_flag; // First, we disable all memory accesses. f_serial_puts("step 1\n"); asm(".long 0x003f236f"); //add sync instruction. store_restore_plls(0); f_serial_puts("ddr self-refresh\n"); wait_uart_empty(); ddr_self_refresh(); f_serial_puts("CPU off...\n"); wait_uart_empty(); cpu_off(); f_serial_puts("CPU off done\n"); wait_uart_empty(); #ifdef CONFIG_CEC_WAKEUP hdmi_cec_func_config = readl(P_AO_DEBUG_REG0); f_serial_puts("CEC M8:uboot: P_AO_DEBUG_REG0:\n"); serial_put_hex(hdmi_cec_func_config,32); f_serial_puts("\n"); #endif if(p_arc_pwr_op->power_off_at_24M) p_arc_pwr_op->power_off_at_24M(); #ifdef CONFIG_M201_COSTDOWN /* for led */ clrbits_le32(P_AO_GPIO_O_EN_N,1<<18); setbits_le32(P_AO_GPIO_O_EN_N,1<<29); #endif // while(readl(0xc8100000) != 0x13151719) // {} //non 32k crystal oscillator platform DONT enter 32k in suspend mode #ifndef CONFIG_NON_32K switch_24M_to_32K(); #endif if(p_arc_pwr_op->power_off_at_32K_1) p_arc_pwr_op->power_off_at_32K_1(); if(p_arc_pwr_op->power_off_at_32K_2) p_arc_pwr_op->power_off_at_32K_2(); // gate off: bit0: REMOTE; bit3: UART #ifndef CONFIG_NON_32K writel(readl(P_AO_RTI_GEN_CNTL_REG0)&(~(0x8)),P_AO_RTI_GEN_CNTL_REG0); #endif if(uboot_cmd_flag == 0x87654321)//u-boot suspend cmd flag { if(p_arc_pwr_op->power_off_ddr15) p_arc_pwr_op->power_off_ddr15(); } wdt_flag=readl(P_WATCHDOG_TC)&(1<<19); if(wdt_flag) writel(readl(P_WATCHDOG_TC)&(~(1<<19)),P_WATCHDOG_TC); #if 1 vcin_state = p_arc_pwr_op->detect_key(uboot_cmd_flag); #else for(i=0;i<10;i++) { udelay__(1000); //udelay(1000); } #endif if(uboot_cmd_flag == 0x87654321)//u-boot suspend cmd flag { if(p_arc_pwr_op->power_on_ddr15) p_arc_pwr_op->power_on_ddr15(); } if(wdt_flag) writel((6*7812|((1<<16)-1))|(1<<19),P_WATCHDOG_TC); // gate on: bit0: REMOTE; bit3: UART writel(readl(P_AO_RTI_GEN_CNTL_REG0)|0x8,P_AO_RTI_GEN_CNTL_REG0); if(p_arc_pwr_op->power_on_at_32K_2) p_arc_pwr_op->power_on_at_32K_2(); if(p_arc_pwr_op->power_on_at_32K_1) p_arc_pwr_op->power_on_at_32K_1(); #ifndef CONFIG_NON_32K switch_32K_to_24M(); #endif // power on even more domains if(p_arc_pwr_op->power_on_at_24M) p_arc_pwr_op->power_on_at_24M(); uart_reset(); f_serial_puts("step 8: ddr resume\n"); wait_uart_empty(); ddr_resume(); #ifdef CONFIG_M201_COSTDOWN /* for led */ clrbits_le32(P_AO_GPIO_O_EN_N,1<<29); setbits_le32(P_AO_GPIO_O_EN_N,1<<18); #endif f_serial_puts("restore pll\n"); wait_uart_empty(); store_restore_plls(1);//Before switch back to clk81, we need set PLL if (uboot_cmd_flag == 0x87654321 && (vcin_state == FLAG_WAKEUP_PWROFF)) { /* * power off system before ARM is restarted */ f_serial_puts("no extern power shutdown\n"); wait_uart_empty(); p_arc_pwr_op->shut_down(); do { udelay__(2000 * 100); f_serial_puts("wait shutdown...\n"); wait_uart_empty(); }while(1); } #ifdef CONFIG_MESON_TRUSTZONE copy_reboot_code(temp_arm_base); #else copy_reboot_code(NULL); #endif writel(vcin_state,P_AO_RTI_STATUS_REG2); f_serial_puts("restart arm\n"); wait_uart_empty(); restart_arm(); if (uboot_cmd_flag == 0x87654321) { writel(0,P_AO_RTI_STATUS_REG2); writel(readl(P_AO_RTI_PWR_CNTL_REG0)|(1<<4),P_AO_RTI_PWR_CNTL_REG0); clrbits_le32(P_HHI_SYS_CPU_CLK_CNTL,1<<19); //writel(10,0xc1109904); writel(1<<19|1<<24|10,0xc1109900); do{udelay__(200);f_serial_puts("wait reset...\n");wait_uart_empty();}while(1); } }
/** @brief Vitual COM Port reset * * The function resets the internal states of the port used * as the Virtual COM Port. * * @return 0 Function failed. * @return 1 Function succeeded. */ int32_t USBD_CDC_ACM_PortReset(void) { uart_reset(); return 1; }
void enter_power_down() { int i; unsigned v1,v2,v; unsigned rtc_ctrl; unsigned power_key; //******************************************* //* power down flow //******************************************* f_serial_puts("\n"); wait_uart_empty(); // disable jtag setbits_le32(P_AO_RTI_PIN_MUX_REG, 1<<13); clrbits_le32(P_AO_RTI_PIN_MUX_REG, 1<<14); // turn off mali clock clrbits_le32(P_HHI_MALI_CLK_CNTL, 1 << 8); // disable all memory accesses. disable_mmc_req(); //save registers for clk and ddr store_restore_plls(1); //mmc enter sleep mmc_sleep(); // delay_ms(20); // save ddr power APB_Wr(MMC_PHY_CTRL, APB_Rd(MMC_PHY_CTRL)|(1<<0)|(1<<8)|(1<<13)); APB_Wr(PCTL_PHYCR_ADDR, APB_Rd(PCTL_PHYCR_ADDR)|(1<<6)); APB_Wr(PCTL_DLLCR9_ADDR, APB_Rd(PCTL_DLLCR9_ADDR)|(1<<31)); // delay_ms(20); // power down DDR writel(readl(P_HHI_DDR_PLL_CNTL)|(1<<15),P_HHI_DDR_PLL_CNTL); // enable retention enable_retention(); writel(0,P_AO_RTI_STATUS_REG1); // reset A9 // setbits_le32(P_A9_CFG2, 7<<16); clrbits_le32(P_HHI_SYS_CPU_CLK_CNTL, 1<<4); // disable APB_CLK clrbits_le32(P_HHI_SYS_CPU_CLK_CNTL, 1<<5); // disable AT_CLK setbits_le32(P_HHI_SYS_CPU_CLK_CNTL,1<<19); udelay(10); // enable iso ee for A9 writel(readl(P_AO_RTI_PWR_CNTL_REG0)&(~(1<<4)),P_AO_RTI_PWR_CNTL_REG0); udelay(1000); #ifdef POWER_OFF_HDMI_VCC reg7_off(); #endif #ifdef POWER_OFF_AVDD33 reg5_off(); #endif #ifdef POWER_OFF_EE //iso EE from AO //comment isolate EE. otherwise cannot detect power key. // writel(readl(P_AO_RTI_PWR_CNTL_REG0)&(~(1<<0)),P_AO_RTI_PWR_CNTL_REG0); writel(readl(P_AO_RTI_PWR_CNTL_REG0)&(~(1<<2)),P_AO_RTI_PWR_CNTL_REG0); writel(readl(P_AO_RTI_PWR_CNTL_REG0)&(~(1<<3)),P_AO_RTI_PWR_CNTL_REG0); //?? Gate off clk81 to EE domain writel(readl(P_AO_RTI_GEN_CNTL_REG0)&(~(1<<12)),P_AO_RTI_GEN_CNTL_REG0); //------------------------------- //turn off EE voltage //v = readl(0xC8100024); //v &= ~(1<<9); //v &= ~(1<<25); //writel(v,0xC8100024); #else // ee use 32k writel(readl(P_HHI_MPEG_CLK_CNTL)|(1<<9),P_HHI_MPEG_CLK_CNTL); #endif // change RTC filter for 32k rtc_ctrl = readl(0xC810074c); //writel(0x00800000,0xC810074c); writel(0,0xC810074c); // switch to 32k writel(readl(P_AO_RTI_PWR_CNTL_REG0)|(1<<8),P_AO_RTI_PWR_CNTL_REG0); udelay(100); #ifdef POWER_OFF_VDDIO vddio_off(); #endif #ifdef POWER_OFF_AVDD25 reg6_off(); #endif #ifdef POWER_OFF_VCC power_off_VCC(0); #endif udelay(100); #if (defined(POWER_DOWN_VCC12) || defined(POWER_DOWN_DDR)) switch_voltage(1); #endif #ifdef POWER_DOWN_DDR powerdown_ddr(); #endif #ifdef POWER_DOWN_VCC12 powerdown_vcc12(); #endif // gate off REMOTE, UART //writel(readl(P_AO_RTI_GEN_CNTL_REG0)&(~(0xF)),P_AO_RTI_GEN_CNTL_REG0); // wait key #if 1 //backup the remote config (on arm) backup_remote_register(); //set the ir_remote to 32k mode at ARC init_custom_trigger(); //set the detect gpio //setbits_le32(P_AO_GPIO_O_EN_N,(1<<3)); while(1) { //detect remote key power_key=readl(P_AO_IR_DEC_FRAME); if(power_key==0xf50a7748) break; //detect IO key /*power_key=readl(P_AO_GPIO_I); power_key=power_key&(1<<3); if(!power_key) break; */ #ifdef RTC_AUTO_WAKE_UP power_key = readl(0xc8100744); if((power_key&8) != 0) break; #endif } #elif 1 power_key = readl(0Xc8100744); while (((power_key&4) != 0)&&((power_key&8) == 0)) { power_key = readl(0Xc8100744); } #else for(i=0;i<64;i++) { udelay(1000); //udelay(1000); } #endif // gate on REMOTE, I2C s/m, UART //writel(readl(P_AO_RTI_GEN_CNTL_REG0)|0xF, P_AO_RTI_GEN_CNTL_REG0); udelay(10); #ifdef POWER_DOWN_DDR powerup_ddr(); #endif #ifdef POWER_DOWN_VCC12 powerup_vcc12(); #endif #if (defined(POWER_DOWN_VCC12) || defined(POWER_DOWN_DDR)) switch_voltage(0); #endif #ifdef POWER_OFF_VCC power_off_VCC(1); #endif #ifdef POWER_OFF_AVDD25 reg6_on(); #endif #ifdef POWER_OFF_VDDIO vddio_on(); #endif udelay(100); // switch to clk81 writel(readl(P_AO_RTI_PWR_CNTL_REG0)&(~(0x1<<8)),P_AO_RTI_PWR_CNTL_REG0); udelay(100); // restore RTC filter writel(rtc_ctrl,0xC810074c); // set AO interrupt mask writel(0xFFFF,P_AO_IRQ_STAT_CLR); #ifdef POWER_OFF_EE //turn on EE voltage //v = readl(0xC8100024); //v &= ~(1<<9); //v |= (1<<25); //writel(v,0xC8100024); //delay_ms(200); // un-iso AO domain from EE bit0=signals, bit1=reset, bit2=irq, bit3=test_mode writel(readl(P_AO_RTI_PWR_CNTL_REG0)|(0xD<<0),P_AO_RTI_PWR_CNTL_REG0); //un isolate the reset in the EE writel(readl(P_AO_RTI_PWR_CNTL_REG0)|(0x1<<5),P_AO_RTI_PWR_CNTL_REG0); writel(readl(P_AO_RTI_PWR_CNTL_REG0)|(0x1<<5)|(1<<3)|(1<<2)|(1<<1)|(1<<0), \ P_AO_RTI_PWR_CNTL_REG0); #else // ee go back to clk81 writel(readl(P_HHI_MPEG_CLK_CNTL)&(~(0x1<<9)),P_HHI_MPEG_CLK_CNTL); #endif #ifdef POWER_OFF_AVDD33 reg5_on(); #endif #ifdef POWER_OFF_HDMI_VCC reg7_on(); #endif store_restore_plls(0); init_ddr_pll(); udelay(1000); uart_reset(); reset_mmc(); // initialize mmc and put it to sleep init_pctl(); mmc_sleep(); // disable retention disable_retention(); // Next, we wake up mmc_wakeup(); // Next, we enable all requests enable_mmc_req(); // f_serial_puts("restart arm...\n"); //0. make sure a9 reset setbits_le32(P_A9_CFG2,1<<17); // release APB reset udelay(1000); setbits_le32(P_A9_CFG2,1<<16); // release AXI reset udelay(1000); setbits_le32(P_A9_CFG2,1<<18); // release A9DBG reset udelay(1000); setbits_le32(P_HHI_SYS_CPU_CLK_CNTL,1<<19); udelay(1000); //1. write flag if (power_key&8) writel(0xabcd1234,P_AO_RTI_STATUS_REG2); else writel(0x1234abcd,P_AO_RTI_STATUS_REG2); //2. remap AHB SRAM writel(3,P_AO_REMAP_REG0); writel(2,P_AHB_ARBDEC_REG); //3. turn off romboot clock writel(readl(P_HHI_GCLK_MPEG1)&0x7fffffff,P_HHI_GCLK_MPEG1); //4. Release ISO for A9 domain. setbits_le32(P_AO_RTI_PWR_CNTL_REG0,1<<4); udelay(1000); writel( (0 << 9) | // select xtal as clock source (0 << 0) , P_HHI_MALI_CLK_CNTL); delay_ms(1); setbits_le32(P_HHI_SYS_CPU_CLK_CNTL, (1<<14)|(1<<15)); // soft reset udelay(10); clrbits_le32(P_HHI_SYS_CPU_CLK_CNTL, (1<<14)|(1<<15)); // soft reset udelay(1000); //reset A9 writel(0xF,P_RESET4_REGISTER);// -- reset arm.ww writel(1<<14,P_RESET2_REGISTER);// -- reset arm.mali udelay(1000); clrbits_le32(P_A9_CFG2,1<<17); // release APB reset udelay(1000); clrbits_le32(P_A9_CFG2,1<<16); // release AXI reset udelay(1000); clrbits_le32(P_A9_CFG2,1<<18); // release A9DBG reset udelay(1000); setbits_le32(P_HHI_SYS_CPU_CLK_CNTL, 1<<4); // enable APB_CLK udelay(10); clrbits_le32(P_HHI_SYS_CPU_CLK_CNTL,1<<19); // release A9 reset udelay(1000); //reset the IR REMOTE resume_remote_register(); // delay_1s(); // delay_1s(); // delay_1s(); }
/* Function for handling the Application's BLE Stack events. Parameters: p_ble_evt Bluetooth stack event. */ static void on_ble_evt(ble_evt_t * p_ble_evt) { uint32_t err_code; uint8_t index = 0; const ble_gap_evt_t * p_gap_evt = &p_ble_evt->evt.gap_evt; switch (p_ble_evt->header.evt_id) { case BLE_GAP_EVT_ADV_REPORT: { const ble_gap_evt_adv_report_t *p_adv_report = &p_gap_evt->params.adv_report; index = get_devices_list_id(p_adv_report->peer_addr); /* id device has been already found or list is full */ if( index != 0xFF) { /* device already found */ /* new adv update */ target_name_if_present(p_adv_report, found_devices[index].name, &found_devices[index].name_length); } else { /* if UUID is present */ if (is_uuid_present(&m_nus_uuid, p_adv_report)) { /* get last free index */ index = devices_list_index; /* increment last free index */ devices_list_index++; /* insert the new device into the list: copy address */ strncpy((char *)(found_devices[index].gap_addr.addr), (char *)(p_adv_report->peer_addr.addr), (size_t)6); /* copy address type */ found_devices[index].gap_addr.addr_type = p_adv_report->peer_addr.addr_type; } } break; } case BLE_GAP_EVT_CONNECTED: { /* if pending connection index of central role is valid */ if(pending_nus_conn_index < NUM_OF_CONNECTIONS) { /* store related connection handle */ active_conn_handles[pending_nus_conn_index] = p_ble_evt->evt.gap_evt.conn_handle; /* set current handle as this one */ m_ble_nus_c.conn_handle = p_ble_evt->evt.gap_evt.conn_handle; /* reset pending NUS connection index */ pending_nus_conn_index = 0xFF; /* reset uart */ uart_reset(); /* set "connection" pin as connected */ nrf_gpio_pin_write(CONN_PIN_NUMBER, CONNECTED_PIN_STATE); /* send confirmation string */ uart_send_string((uint8_t *)"OK.", 3); /* start discovery of services. The NUS Client waits for a discovery result */ err_code = ble_db_discovery_start(&m_ble_db_discovery, p_ble_evt->evt.gap_evt.conn_handle); APP_ERROR_CHECK(err_code); } else { /* internal error: do nothing */ } break; } case BLE_GAP_EVT_DISCONNECTED: { /* it should not pass here */ break; } case BLE_GAP_EVT_TIMEOUT: { if (p_gap_evt->params.timeout.src == BLE_GAP_TIMEOUT_SRC_SCAN) { /* scan timed out */ uart_send_string((uint8_t *)"TIMEOUT.", 8); } else if (p_gap_evt->params.timeout.src == BLE_GAP_TIMEOUT_SRC_CONN) { /* connection request timed out: do nothing */ } else { /* do nothing */ } break; } case BLE_GAP_EVT_SEC_PARAMS_REQUEST: { /* ATTENTION: Pairing not supported at the moment */ err_code = sd_ble_gap_sec_params_reply(p_ble_evt->evt.gap_evt.conn_handle, BLE_GAP_SEC_STATUS_PAIRING_NOT_SUPP, NULL, NULL); APP_ERROR_CHECK(err_code); break; } case BLE_GAP_EVT_CONN_PARAM_UPDATE_REQUEST: { /* Accepting parameters requested by peer. */ err_code = sd_ble_gap_conn_param_update(p_gap_evt->conn_handle, &p_gap_evt->params.conn_param_update_request.conn_params); APP_ERROR_CHECK(err_code); break; } default: break; } }
int32_t uart_set_configuration (UART_Configuration *config) { uint8_t DivAddVal = 0; uint8_t MulVal = 1; uint16_t dlv; uint8_t mv, dav, hit = 0, data_bits = 8, parity, stop_bits = 0; float ratio, err, calcbaud; // disable interrupt NVIC_DisableIRQ (UART_IRQn); // reset uart uart_reset(); dll = SystemCoreClock / (16 * config->Baudrate); baudrate = config->Baudrate; // First we check to see if the basic divide with no DivAddVal/MulVal // ratio gives us an integer result. If it does, we set DivAddVal = 0, // MulVal = 1. Otherwise, we search the valid ratio value range to find // the closest match. This could be more elegant, using search methods // and/or lookup tables, but the brute force method is not that much // slower, and is more maintainable. if ((SystemCoreClock % (16 * config->Baudrate)) != 0) { // Checking for zero remainder float err_best = (float) config->Baudrate; unsigned short dlmax = dll; for (dlv = dlmax/2; (dlv <= dlmax) && !hit; dlv++) { for ( mv = 1; mv <= 15; mv++) { for ( dav = 1; dav < mv; dav++) { ratio = 1.0 + ((float) dav / (float) mv); calcbaud = (float)SystemCoreClock / (16.0 * (float) dlv * ratio); err = ((config->Baudrate - calcbaud) > 0) ? (config->Baudrate - calcbaud) : -(config->Baudrate - calcbaud); if (err < err_best) { dll = dlv; DivAddVal = dav; MulVal = mv; err_best = err; if (err < 10) { hit = 1; } } } } } } // set LCR[DLAB] to enable writing to divider registers LPC_USART->LCR |= (1 << 7); // set divider values LPC_USART->DLM = (dll >> 8) & 0xFF; LPC_USART->DLL = (dll >> 0) & 0xFF; LPC_USART->FDR = (uint32_t) DivAddVal << 0 | (uint32_t) MulVal << 4; // clear LCR[DLAB] LPC_USART->LCR &= ~(1 << 7); // set data bits, stop bits, parity if ((config->DataBits < 5) || (config->DataBits > 8)) { data_bits = 8; } data_bits -= 5; if (config->StopBits != 1 && config->StopBits != 2) { stop_bits = 1; } stop_bits -= 1; switch (config->Parity) { case UART_PARITY_ODD: parity = 0x01; break; // Parity Odd case UART_PARITY_EVEN: parity = 0x03; break; // Parity Even case UART_PARITY_MARK: parity = 0x05; break; // Parity Mark case UART_PARITY_SPACE: parity = 0x07; break; // Parity Space case UART_PARITY_NONE: // Parity None default: parity = 0x00; break; } LPC_USART->LCR = (data_bits << 0) | (stop_bits << 2) | (parity << 3) | (LPC_USART->LCR & 0x40); // Enable UART interrupt NVIC_EnableIRQ (UART_IRQn); return 1; }
void uart_init() { uart_reset(); uart_baud_set(); }