娇小w搡bbbb搡bbb,《第一次の人妻》,中国成熟妇女毛茸茸,边啃奶头边躁狠狠躁视频免费观看

歷史上的今天

今天是:2025年05月31日(星期六)

2018年05月31日 | stm8——串口printf的實現

發布者:chwwdch 來源: eefocus關鍵字:stm8  串口printf 手機看文章 掃描二維碼
隨時隨地手機看文章

串口通信單片機學習的一個最基本、最重要的功能之一。串口可以間接的當做調試接口使用,實現單片機與電腦之間的通信。還可以與一些模塊(比如藍牙、wifi)通信,也可以作為和其他單片機通信的工具。作為開發者,熟悉串口是必須的。


=========================================== 

STM8L的USART特性: 

這里寫圖片描述


我們在使用串口的時候,主要關心:波特率、停止位、奇偶校驗位。 

再次就是怎樣接收、發送數據。常用:阻塞式發送數據、中斷方式接收數據。


========================================== 

在單片機的調試過程中經常會要適時地輸出變量的值,這時printf函數是一個非常好的選擇;對于一般的單片機只有串口可以與外界進行通信,所以我們需要將printf函數重定向到串口。 

如何實現重定向c庫函數printf到USART1函數? 

不管printf函數多么復雜,最終調用的是purchar函數,所以我們只要重新定義putchar函數即可。


========================================== 

使用到的庫如下: 

這里寫圖片描述


外設在使用前,都必須使能對應的外設時鐘。為了cpu的低功耗,板子上默認的外設都是關閉的,否則板子一上電所有的外設都啟動了功耗相對就高了,因此我們在使用的時候,用到哪一個外設就開啟使能哪一個外設的時鐘。


usart.h:


#ifndef __USART_H

#define __USART_H


#include "stm8l15x.h"


#define BAUDRATE 115200

#define SIZE 128


/*定義一個結構體,存放串口相關變量*/

typedef struct uart_rxbuf_s

{

  uint8_t               buf[SIZE];  /* 串口接收數據的buffer*/

  uint32_t              len;      /* 數據的長度 */

}uart_rxbuf_t;


extern uart_rxbuf_t  g_uart_rxbuf;  /*定義一個結構體變量g_uart_rxbuf,會用以訪問結構體里的成員*/


extern void uart_init(void);  /*串口初始化函數聲明*/

extern void uart_send(char *buf, int len);/*串口發送函數聲明*/

extern int uart_getchar(void);/*接收*/


#endif


usart.c:


void uart_init(void)

{

  /*buffer先清零*/

  memset(&g_uart_rxbuf, 0, sizeof(g_uart_rxbuf));

  /*使能usart時鐘*/

  CLK_PeripheralClockConfig(CLK_Peripheral_USART1, ENABLE);

  /*TXD */

  GPIO_Init(GPIOC, GPIO_Pin_2, GPIO_Mode_Out_PP_High_Fast);

  /*RXD*/

  GPIO_Init(GPIOC, GPIO_Pin_3, GPIO_Mode_In_PU_No_IT);

  /*復位*/

  USART_DeInit(USART1);


  /*配置串口*/

  USART_Init(USART1, BAUDRATE, USART_WordLength_8b, USART_StopBits_1, USART_Parity_No, 

             (USART_Mode_TypeDef)(USART_Mode_Tx | USART_Mode_Rx));


  /*開啟總中斷,也可以放到main.c里*/

  enableInterrupts();

  /*開啟接收中斷*/

  USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);

  /*打開串口*/

  USART_Cmd(USART1, ENABLE);


  USART_SendData8(USART1, '\r');

  /*用于檢查串口UART1是否發送完成,完成時,TC中斷標志置位,退出輪詢等待*/

  while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET);


}


/*系統printf函數實現*/

int putchar(int c)

{

  if('\n' == (char)c)

  {

    USART_SendData8(USART1, '\r');

    while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET);

  }

  USART_SendData8(USART1, c);

  while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET);


  return (c);

}


void uart_send(char *buf, int len)

{

  int i;

  /*把要發送的數據放入緩沖區,然后將緩沖區的數據發送到寄存器DR*/

  for(i=0; i

  {

    USART1->DR = (unsigned char)buf[i];

    /*用于檢查串口UART1是否發送完成,完成時,TC中斷標志置位,退出輪詢等待*/

    while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET);  

  }

}


int uart_getchar(void)

{

  int c;


  /* 循環,直到讀取數據寄存器標志被設置 */

  while (USART_GetFlagStatus(USART1, USART_FLAG_RXNE) == RESET);  

  c = USART_ReceiveData8(USART1); 


  /* 返回接收的數據 */

   USART_SendData8(USART1, c); 

   while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET);    


  return (c);   

}


時鐘配置: 

sysclock.h:


#ifndef __SYSCLOCK_H

#define __SYSCLOCK_H


#include "stm8l15x.h"


void sys_clk_init();


#endif


sysclock.c:


#include "sysclock.h"

#include "stm8l15x_clk.h"

void sys_clk_init(void)

{

  CLK_SYSCLKDivConfig(CLK_SYSCLKDiv_1);/*高速內部時鐘分頻器:1  =>即16M*/

  /*選擇高速外部時鐘信號作為系統時鐘源*/

  CLK_SYSCLKSourceSwitchCmd(ENABLE);

  CLK_SYSCLKSourceConfig(CLK_SYSCLKSource_HSE);


  while (CLK_GetSYSCLKSource() != CLK_SYSCLKSource_HSE)

  {}

}


發送數據不需要中斷,但是接收數據需要利用中斷來處理,這樣效率比較高,我們只需要填充stm8l15x_it.c里的代碼。這個是中斷程序的源文件,在編寫應用的過程中,需要根據需求改動,以便在自己的程序中使用中斷功能。 

部分代碼:


/**

  * @brief USART1 RX / Timer5 Capture/Compare Interrupt routine.

  * @param  None

  * @retval None

  */

INTERRUPT_HANDLER(USART1_RX_TIM5_CC_IRQHandler, 28)

{

/* 緩沖區是否已滿,滿的話就丟棄 */

  if(g_uart_rxbuf.len>=sizeof(g_uart_rxbuf.buf))

  {

     USART_ReceiveData8(USART1); /* 丟掉 */

     return ;

  }


  g_uart_rxbuf.buf[g_uart_rxbuf.len++] = USART_ReceiveData8(USART1); /*接收數據*/

}


main.c: 

這里只做了簡單的printf打印:


#include "stm8l15x.h"

#include "usart.h"

#include "sysclock.h"

#include "stdio.h"



int main( void )

{

  sys_clk_init();

  uart_init();


  uart_send("abc", 3);

  int i;

  for(i=0; i<5; i++)

  {

    printf("\ntest,test\n");

  }

  printf("\ntest finshed!\n");


  return 0;

}


測試結果: 

這里寫圖片描述 

若有什么功能要在主函數的while(1)做的,可以再實現,這里只是測試一下printf,所以沒有寫while。


總結: 

程序從main.c進入 

1、引腳初始化; 

2、時鐘初始化; 

3、配置芯片的UART模塊; 

4、若有串口數據進來,會觸發中斷函數,執行中斷,把接收到的數據取出來,再通過發送函數發送出去;


關鍵字:stm8  串口printf 引用地址:stm8——串口printf的實現

上一篇:STM8S1003 模擬SPI 驅動 SI4432
下一篇:STM8L的printf函數實現

推薦閱讀

集微網消息(文/叨叨)聯發科最新一代移動處理器 Helio P22傳出首發的消息,首發機型將是 vivo 的 Y83。按照P22最快在6月份量產,預計 vivo Y83 也將同步上市。曦力 P22采用以低功耗著稱的臺積電12nm FinFET制程工藝,內置八個Arm Cortex A53核心,最高主頻可達2.0GHz,搭配智能管理各任務執行的CorePilot 4.0技術,實現性能和功耗的完美平衡...
成立于1995年的Marvell在巔峰的時候曾經位列全球半導體前五。在2013年中國4G牌照發放之時,Marvell領先于聯發科和展訊推出了首款千元智能手機的4G芯片,并在當年的市場上大殺四方。但在高通、聯發科和展訊等大舉殺入之后,Marvell在接下來的兩三年節節敗退。到了2016年,公司創始人,CEO周秀文和總裁戴偉立更是雙雙離職,讓外界對公司的未來充滿了疑問。Ma...
協作機器人夾爪制造商OnRobot推出2.5D視覺系統Eyes,適用于各家先進機器手臂,提供外加的深度感知和零件辨識功能。 據報導,機器手臂經常遇到的難題,就是無法拾放大小、形狀或擺放方向不一的物品,通常需要外加夾具、送料盤等其它硬件協助作業,但也因此增加作業成本和復雜度,局限了設備的應用范圍。 OnRobot新推出的2.5D視覺系統Eyes,只要照一張...
數字化轉型已經成為社會經濟共同探討、關注和推動的時代命題。而在宏觀的數字化轉型視野之下,每一項新技術、新解決方案、新商業模式,都需要有一部分企業去率先探索,勇做先鋒。這些先鋒的合力最終會推開一扇大門,迎來數字經濟的真正繁榮。 在數字化升級的確定性未來面前,園區網絡正在成為一個入口和契機。園區網絡是距離企業業務最近、直接承載企業數...

史海拾趣

小廣播
設計資源 培訓 開發板 精華推薦

最新單片機文章
何立民專欄 單片機及嵌入式寶典

北京航空航天大學教授,20余年來致力于單片機與嵌入式系統推廣工作。

 
EEWorld訂閱號

 
EEWorld服務號

 
汽車開發圈

 
機器人開發圈

電子工程世界版權所有 京ICP證060456號 京ICP備10001474號-1 電信業務審批[2006]字第258號函 京公網安備 11010802033920號 Copyright ? 2005-2025 EEWORLD.com.cn, Inc. All rights reserved
主站蜘蛛池模板: 高州市| 青海省| 新安县| 郎溪县| 靖远县| 梁平县| 宽甸| 崇州市| 道真| 安庆市| 扎兰屯市| 宣威市| 通化市| 独山县| 福州市| 蒙山县| 儋州市| 江安县| 石门县| 鹿泉市| 新龙县| 湄潭县| 巫溪县| 正镶白旗| 江安县| 怀柔区| 汶川县| 罗山县| 长乐市| 临漳县| 北宁市| 怀来县| 都安| 西盟| 华容县| 德安县| 乾安县| 游戏| 六盘水市| 大冶市| 长岭县|