日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

学会阅读硬件的原理图、数据手册大全

發布時間:2023/12/10 编程问答 33 豆豆
生活随笔 收集整理的這篇文章主要介紹了 学会阅读硬件的原理图、数据手册大全 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

參考: 郭天祥:https://www.bilibili.com/video/BV1DW411a7mz?p=8
韋東山:https://www.bilibili.com/video/BV1ga4y1Y7PL?p=4
https://www.bilibili.com/video/BV17g411F7oR?spm_id_from=333.999.0.0
洋桃電子:https://www.bilibili.com/video/BV1eW411J7cf?p=2&spm_id_from=pageDriver

目錄

  • 硬件接口的四大類
      • 1. GPIO和門電路
      • 2. 協議類
      • 3. 類似內存的接口(ram-like)
      • 4. 模擬電路
  • GPIO與門電路
      • 1. GPIO的應用
      • 2. GPIO引腳操作
        • 2.1 設置引腳為GPIO功能
        • 2.2 設置引腳方向
        • 2.3 設置/讀取引腳數值
      • 3. 二極管
      • 4. 三極管
        • 4.1 NPN三極管
        • 4.2 PNP三極管
  • LED電路與操作
      • 1. LED實物
      • 2. LED電路
  • 同步與異步
      • 1. 概念
        • 1.1 同步信號示例
        • 1.2 異步信號示例
      • 2. 差別
  • 使用一線傳輸雙向數據
      • 1. 面臨的問題
      • 2. 解決方法
      • 3. 雙向傳輸示例
  • 如何高效閱讀英文數據手冊?
  • 類似內存的接口(2440開發板為例)
    • SDRAM
    • NOR FLASH
    • 網卡
    • 不同位寬外設的接線
    • 時序的閱讀及內存控制器的設置
  • 1602液晶驅動顯示
    • 閱讀手冊
    • LCD1602.h
    • LCD1602.c
  • IIC總線AT24C02芯片實驗(E2PROM)
    • IIC總線協議
    • 24C02芯片手冊閱讀
    • 編寫代碼

硬件接口的四大類

參考書籍:

  • 《微機原理》:側重于計算機結構
  • 《數字電子技術基礎 》:側重于門電路

1. GPIO和門電路

GPIO:general peripheral input/ouput,通用的外設輸入、輸出接口。

這類電路通常只使用一個引腳

  • 可以設置為輸出
    • 可以輸出高、低電平
    • 比如用來控制LED
  • 也可以設置為輸入
    • 可以讀取引腳電平,判斷當前是高電平還是低電平
    • 比如用來判斷按鍵是否被按下
  • 可以接上各類晶體管(二極管、三極管等)實現邏輯運算

門電路:與門、或門、非門

2. 協議類

比如:UART、I2C、SPI、Nand、TFT LCD。

如果兩個設備之間要傳輸的數據比較復雜,可以約定一些規則。這類接口被稱為"協議類"接口。

當然可以只使用一條GPIO引腳來傳輸復雜的數據,比如紅外遙控器、溫度傳感器等。也可使用多條線路來傳輸數據,比如UART、I2C、SPI等。比如TFT LCD的接口線將近30條。

例子:

  • I2C接口

    • 硬件連接

  • I2C協議

3. 類似內存的接口(ram-like)

比如:Nor Flash、SDRAM、DDR、網卡DM9000等。

  • 內存:可以讀寫某個地址上的數據,所以必定有這些信號
    • 地址總線
    • 數據總線
    • 讀/寫信號
    • 片選(cs):ram-like接口上可以接多個設備,互相之間不能干擾,選中哪個設備哪個設備才能響應
  • 很多設備也采用類似內存的接口,比如Nor Flash、8080接口的LCD
  • 例子

4. 模擬電路

數字電路上傳輸的電壓值只有2類取值,比如

  • 2.xV到3.3V,抽象為邏輯值1
  • 0V到1.xV,抽象為邏輯值0

模擬電路上傳輸的電壓可以是各種各樣的,比如以下兩個電路:

  • ADC電路中:可以讀取滑動電阻器上的觸點電壓值
  • DAC電路中:可以輸出不同的電壓值,用來控制LED的亮度(數字電路里LED只有亮、滅兩個狀態)

讀取滑動電阻器上的觸點電壓值

  • DAC電路中:可以輸出不同的電壓值,用來控制LED的亮度(數字電路里LED只有亮、滅兩個狀態)

GPIO與門電路

1. GPIO的應用

GPIO可以設置為輸出、輸入:

  • 輸出功能

    • LED

    • 發射紅外信號

    • 控制電機

    • 蜂鳴器

    • 數碼管

  • 輸入功能

    • 按鍵
    • 接收紅外信號
    • 人體感應
  • 實現各類協議

    • 讀取溫濕度傳感器數據
    • 其實UART等也是使用GPIO來實現的

2. GPIO引腳操作

怎么用一個GPIO來控制LED?換句話說,怎么讓一個GPIO輸出高、低電平?

2.1 設置引腳為GPIO功能

芯片內部有很多模塊,比如GPIO、UART(串口)。
一個引腳,可以接到模塊A,也可以接到模塊B,比如上圖中的引腳gpio0_0,可以接到GPIO group 0,也可以接到UART。
可以設置某些寄存器(比如io_mux),選擇引腳的功能。

2.2 設置引腳方向

假設一個引腳被設置成了GPIO功能,那么它是用作輸出,還是輸入?
在GPIO模塊內部,一般都有一個方向選擇寄存器,里面每一位用來控制一個引腳的方向。
比如GPIO group 0中有一個gpio0_dir_reg寄存器,

  • 它的bit 0寫入1,表示gpio0_0被設置為輸出
  • 它的bit 0寫入0,表示gpio0_0被設置為輸入

2.3 設置/讀取引腳數值

一個GPIO引腳被設置成輸出,那么怎樣設置它的輸出電平?
一個GPIO引腳被設置成輸入,那么怎樣讀取它的輸入電平?
在GPIO模塊內部,一般都有一個數據寄存器,里面每一位用來控制一個引腳的輸出電平。
比如GPIO group 0中有一個gpio0_data_reg寄存器,

  • 寫數據
    • 它的bit 0寫入1,表示gpio0_0輸出高電平
    • 它的bit 0寫入0,表示gpio0_0輸出低電平
  • 讀數據
    • 如果bit 0等于1,表示gpio0_0為高電平
    • 如果bit 0等于0,表示gpio0_0為低 電平

3. 二極管

參考資料:圖文詳解二極管原理

  • 二極管的箭頭表示正向電流的方向

  • 二極管的電流具有單向性

  • 假設正極、負極之間的電壓為V

    • 當V大于某個閾值(比如0.7V),二極管就導通,導通時電阻約等于0
    • 當V<0,二極管不會導通,電阻無窮大
  • 內部結構:由PN節組成,P代表正極(positive),N代表負極(negative)

  • 二極管中流動的是電子,電流方向是從正極到負極,電子流動的方向是從負極到正極

  • 使用二極管

    • 比如:使用二極管防止電源接反是燒壞電路

4. 三極管

參考資料:三極管工作原理分析精辟透徹看后你就懂

可以使用二極管的特性制作成三極管,組成開關電路。

三極管實物圖:

三極管可以分為:NPN三極管、PNP三極管。

4.1 NPN三極管

  • 擴散
    • 物質會從濃度大的地方擴散到濃度低的地方
    • 比如墨水滴入水中,墨水會四處散開
    • 比如臭味會四處散開
    • 電子也會有擴散作用
  • 三極管原理
    • 當be之間的PN節加上正向電壓,電子從e極的’N’大量往‘P’移動(所以e被稱為發射極)
    • 電子在’P’大量聚集,一部分通過b極流走,另一部分通過c極擴散出去(c起收集作用,所以被稱為集電極)
      • 電子流動方向如圖中紅色箭頭所示
      • 電流方向與電子流動方向相反:be之間電流從b到e,ce之間電流從c到e
  • 三極管的使用
    • 當Vcon等于0.7V左右,be之間的PN節打通,c極相當于直接連接e,V2=0
    • 當Vcon等于0V,be之間的PN節沒打通,c極相當于斷開,V2=V
    • 所以,可以用Vcon來控制V2

4.2 PNP三極管

  • 擴散
    • 物質會從濃度大的地方擴散到濃度低的地方
    • 比如墨水滴入水中,墨水會四處散開
    • 比如臭味會四處散開
    • 電子也會有擴散作用
  • 三極管原理
    • 當eb之間的PN節加上正向電壓,空穴從e極的’N’大量往‘P’移動(所以e被稱為發射極)
    • 空穴在’P’大量聚集,一部分通過b極流走,另一部分通過c極擴散出去(c起收集作用,所以被稱為集電極)
      • 空穴流動方向如圖中紅色箭頭所示
      • 電流方向與空穴流動方向相同:eb之間電流從e到b,ec之間電流從e到c
  • 三極管的使用
    • 當Vcon為高電壓(比如3.3V),eb之間的PN節打通,c極相當于直接連接e,V2=Vcon
    • 當Vcon等于0V,eb之間的PN節沒打通,c極相當于斷開,V2=0
    • 所以,可以用Vcon來控制V2

流從e到b,ec之間電流從e到c

  • 三極管的使用
    • 當Vcon為高電壓(比如3.3V),eb之間的PN節打通,c極相當于直接連接e,V2=Vcon
    • 當Vcon等于0V,eb之間的PN節沒打通,c極相當于斷開,V2=0
    • 所以,可以用Vcon來控制V2

LED電路與操作

1. LED實物

2. LED電路

  • 方式1
    • 芯片引腳輸出高電平,LED被點亮
    • 芯片引腳輸出低電平,LED被熄滅
    • 缺點:芯片引腳的驅動能力可能不夠,LED亮度低
  • 方式2
    • 芯片引腳輸出低電平,LED被點亮
    • 芯片引腳輸出高電平,LED被熄滅
    • 缺點:電流進入芯片過大時,可能燒毀芯片
  • 方式3
    • 芯片引腳輸出高電平,三極管導通,LED被點亮
    • 芯片引腳輸出低電平,三極管不導通,LED被熄滅
  • 方式4
    • 芯片引腳輸出低電平,第一個三極管不導通,第二個三極管導通,LED被點亮
    • 芯片引腳輸出高電平,第一個三極管導通,第二個三極管不導通,LED被熄滅

三極管導通,第二個三極管不導通,LED被熄滅

同步與異步

1. 概念

同步(synchronous)、異步(asynchronous),使用生活例子來說就是:

  • 同步:朋友打電話說到我家吃飯,我在家里等他們
  • 異步:朋友沒有提前打招呼,突然就到我家來了

1.1 同步信號示例

在電子產品中,使用同步信號進行傳輸時,一般涉及兩個信號:

  • 時鐘信號:用來通知對方要讀取數據了
  • 數據信號:用來傳輸數據

比如:

  • 時鐘信號:打電話,起約定作用
  • 數據信號:傳輸數據

1.2 異步信號示例

使用異步信號傳輸數據時,雙方遵守相同的約定:

  • 起始信號:發送方可以通知接收方"注意了,我要開始傳輸數據了"

  • 數據的表示

    • 怎么表示邏輯1
    • 怎么表示邏輯0

以紅外遙控器解碼器為例,它向單片機發出的數據格式如下:

  • 起始信號:解碼器發出一個9ms的低電平、4.5ms的高電平,用來同時對方說"開始了"

  • 表示一位數據

    • 邏輯1:0.56ms的低電平+1.69ms的高電平
    • 邏輯0:0.56ms的低電平+0.56ms的高電平

  • 接收方、發送方都遵守這樣的約定,就可以使用一條線傳輸數據

2. 差別

同步傳輸異步傳輸
信號線多:時鐘信號、數據信號少:只需要數據信號
速率可變,提高時鐘信號頻率即可雙方提前約定
抗干擾能力

使用一線傳輸雙向數據

1. 面臨的問題

兩個設備之間,只使用一條數據線,能否傳輸雙向的數據?

  • A發出高電平,B發出低電平
    • 電路可能被損壞
    • 電路上到底是高電平還是低電平?不能確定
  • 問題在于:有兩個設備試圖同時驅動電路

2. 解決方法

不讓雙方同時驅動電路,或者即使同時驅動也沒關系:

  • 不讓雙方同時驅動電路:雙方無法約定時間,此方法不可行
  • 即使同時驅動也沒關系:可行,電路如下:

真值表如下:

ABDATA
001(由上拉電阻決定)
010
100
110

從真值表和電路圖我們可以知道:

  • 當某一個芯片不想影響SDA線時,那就不驅動這個三極管
  • 想讓DATA輸出高電平,雙方都不驅動三極管(SDA通過上拉電阻變為高電平)
  • 想讓DATA輸出低電平,就驅動三極管

芯片內部的三極管,被稱為open collector,開集,也就是在芯片內部三極管的集電極是開放的。
芯片內部不驅動三極管是,集電極的電平由外面的上拉電阻決定。

這種電路實現了:

  • 雙方設備即使同時想輸出不同的電平:
    • 電路也不會被損壞
    • 電平也是確定的

3. 雙向傳輸示例

  • 初始狀態:一開始,雙方都不驅動三極管,DATA為高

  • 起始信號和回應:A想傳輸數據給B,發出開始信號、得到回應信號

    • A檢測DATA線,高表示對方沒有占用數據線
    • A驅動三極管,使得DATA為低,用來通知B:我就要傳輸數據了
    • A釋放三極管,DATA變為高
    • B驅動三極管,使得DATA為低,用來通知A:好的,我準備好了(這是一個回應信號)
    • B釋放三極管,DATA變為高
  • 傳輸:A發送數據給B,比如傳輸2位數據0、1

    • 雙方都使用同一套數據表示方法,比如使用60US來傳輸一位數據,數值由DATA電平決定
    • 在第1個60us,A設置DATA為低;在同一時間,B讀取DATA電平得到數據0
    • 在第2個60us,A設置DATA為高;在同一時間,B讀取DATA電平得到數據1
  • 結束:A釋放三極管,DATA變為高電平

    • 在第2個60us,A設置DATA為高;在同一時間,B讀取DATA電平得到數據1
  • 結束:A釋放三極管,DATA變為高電平

  • 這時候,B也可以使用一樣的方法給A傳輸數據

如何高效閱讀英文數據手冊?

博文參照鏈接

全英文的數據手冊少則十幾頁,多則上百頁也有,加上我們又是如此的愛國(英文水平差的借口),所以在閱讀全英文數據手冊的時候,根本做不到面面俱到,當然也是完全沒有必要,學會善用Ctrl+F搜索關鍵詞,按需所取,閱讀我們關注的部分即可。

我以一個DC-DC BUCK芯片舉例,列出了很多關鍵詞,其他的數據手冊也是同樣的道理。

▉ Title

首先是Title,這也是廠家秀肌肉的地方,會告訴你一些最重要的芯片信息,比如TPS56120x系列、輸入電壓范圍4.5~17V、最大輸出電流1A、同步降壓、封裝是6Pin的SOT-23等。

▉ Feature

如果你是選型,以上參數符合要求,你就會接著往下去看,feature展示了更多的參數,比如輸出電壓范圍、靜態功耗、關閉功耗、精度和頻率等。

▉ Description description

可以讓我們對這個芯片有個大概的了解。

▉ Table of Contents

有的數據手冊會有目錄,可以先了解大致有那些內容,幫助我們尋找關鍵字。

▉Pin Configuration and Functions

可以了解芯片的管腳排布,每個管腳對應的信號名,建立原理圖封裝時需要參考下方這個圖。

通過pin functions了解每個管腳的功能描述,以及設計電路時有什么需要注意的。

▉ Absolute Maximum

Absolute Maximum即絕對最大值,加在芯片上的參數(電壓、溫度、ESD等級等)絕對不能超過這個值,否則芯片會損壞。

▉ Electrical Characteristics

硬件工程師必關注的電氣參數,每個芯片的電氣參數也是不盡相同的。

▉ Typical Characteristics

典型的參數,指的是芯片廠商在特定的參數下,測量得出的一些芯片特性,比如下面的不同輸出電壓和開關頻率之間的關系,DC-DC效率和輸出電流之間的關系等等,這個是為了讓我們更好的了解芯片的性能。

▉ Functional Block Diagram

功能框圖非常重要,透過外部的管腳了解內部的組成,可以更好的理解芯片,如SW管腳接了兩個MOS管,這是為什么能輸出占空比的原因?OVP和UVP都是通過比較器來實現的等等。

▉ Feature Description

對芯片的某一些特性進行描述,讓我們更好的理解這個芯片的相關特性,如下DC-DC的如軟啟動、電流保護、UVLO等功能都有詳細的描述。

▉ Typical Application

對于芯片類的數據手冊來說,典型應用就是參考電路圖。

▉ Layout Guide

對于芯片類如DC-DC,還有layout指導。

▉ Packaging Information

package信息,指的是一盒里面的數量,如下可以看見QTY3000和QTY250的型號是不一樣的。

一個系列不同的型號多在后綴有差別,可能是封裝不同、package QTY的不同等,所以在order的時候需要寫完整的芯片型號。

▉ Package Outline

封裝尺寸信息,在建立PCB封裝時會用到。

▉ Example Layout

根據提供的參考layout建立我們自己的PCB封裝。

列了這么多關鍵詞,并不是教大家如何閱讀DC-DC數據手冊,而是在闡明一個點:不同的人看數據手冊的側重點是不一樣的,硬件工程師更關注電氣參數、封裝信息、參考設計等,軟件工程師更關注寄存器、協議等,提取關鍵字,高效的閱讀數據手冊,找到對我們有幫助的內容才是最重要的。

類似內存的接口(2440開發板為例)

SDRAM


2440芯片手冊講到片選地址映射圖:

NOR FLASH

網卡

不同位寬外設的接線

為什么NOR FLASH地址線從ADDR1開始?SDARM地址是從ADDR2開始的?



如果CPU要讀取32位數據,那么內存控制器會去讀兩次16位數據存起來,一次性交給CPU。

時序的閱讀及內存控制器的設置

例如查詢2440芯片手冊內存控制配置方法:

再查詢相應的外設手冊:

1602液晶驅動顯示

閱讀手冊

1602代表:顯示16個字符,可以顯示兩行。如下圖所示:



發現使用上表中的數值芯片不能正常驅動,查看原廠家芯片英文資料,實踐可以正常使用,具體數值如下圖所示:





LCD1602.h

#ifndef __LCD1602_H__ #define __LCD1602_H__//用戶調用函數: void LCD_Init(); void LCD_ShowChar(unsigned char Line,unsigned char Column,char Char); void LCD_ShowString(unsigned char Line,unsigned char Column,char *String); void LCD_ShowNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length); void LCD_ShowSignedNum(unsigned char Line,unsigned char Column,int Number,unsigned char Length); void LCD_ShowHexNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length); void LCD_ShowBinNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length);#endif

LCD1602.c

#include <REGX52.H>//引腳配置: sbit LCD_RS=P2^6; sbit LCD_RW=P2^5; sbit LCD_EN=P2^7; #define LCD_DataPort P0//main函數入口 void main() {LCD_Init();while(1);}//函數定義: /*** @brief LCD1602延時函數,12MHz調用可延時1ms* @param 無* @retval 無*/ void LCD_Delay() {unsigned char i, j;i = 2;j = 239;do{while (--j);} while (--i); }/*** @brief LCD1602寫命令* @param Command 要寫入的命令* @retval 無*/ void LCD_WriteCommand(unsigned char Command) {LCD_RS=0;LCD_RW=0;LCD_DataPort=Command;LCD_EN=1;LCD_Delay();LCD_EN=0;LCD_Delay(); }/*** @brief LCD1602寫數據* @param Data 要寫入的數據* @retval 無*/ void LCD_WriteData(unsigned char Data) {LCD_RS=1;LCD_RW=0;LCD_DataPort=Data;LCD_EN=1;LCD_Delay();LCD_EN=0;LCD_Delay(); }/*** @brief LCD1602設置光標位置* @param Line 行位置,范圍:1~2* @param Column 列位置,范圍:1~16* @retval 無*/ void LCD_SetCursor(unsigned char Line,unsigned char Column) {if(Line==1){LCD_WriteCommand(0x80|(Column-1));}else if(Line==2){LCD_WriteCommand(0x80|(Column-1+0x40));} }/*** @brief LCD1602初始化函數* @param 無* @retval 無*/ void LCD_Init() {LCD_WriteCommand(0x38);//八位數據接口,兩行顯示,5*7點陣LCD_WriteCommand(0x0c);//顯示開,光標關,閃爍關LCD_WriteCommand(0x06);//數據讀寫操作后,光標自動加一,畫面不動LCD_WriteCommand(0x01);//光標復位,清屏 }/*** @brief 在LCD1602指定位置上顯示一個字符* @param Line 行位置,范圍:1~2* @param Column 列位置,范圍:1~16* @param Char 要顯示的字符* @retval 無*/ void LCD_ShowChar(unsigned char Line,unsigned char Column,char Char) {LCD_SetCursor(Line,Column);LCD_WriteData(Char); }/*** @brief 在LCD1602指定位置開始顯示所給字符串* @param Line 起始行位置,范圍:1~2* @param Column 起始列位置,范圍:1~16* @param String 要顯示的字符串* @retval 無*/ void LCD_ShowString(unsigned char Line,unsigned char Column,char *String) {unsigned char i;LCD_SetCursor(Line,Column);for(i=0;String[i]!='\0';i++){LCD_WriteData(String[i]);} }/*** @brief 返回值=X的Y次方*/ int LCD_Pow(int X,int Y) {unsigned char i;int Result=1;for(i=0;i<Y;i++){Result*=X;}return Result; }/*** @brief 在LCD1602指定位置開始顯示所給數字* @param Line 起始行位置,范圍:1~2* @param Column 起始列位置,范圍:1~16* @param Number 要顯示的數字,范圍:0~65535* @param Length 要顯示數字的長度,范圍:1~5* @retval 無*/ void LCD_ShowNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length) {unsigned char i;LCD_SetCursor(Line,Column);for(i=Length;i>0;i--){LCD_WriteData(Number/LCD_Pow(10,i-1)%10+'0');} }/*** @brief 在LCD1602指定位置開始以有符號十進制顯示所給數字* @param Line 起始行位置,范圍:1~2* @param Column 起始列位置,范圍:1~16* @param Number 要顯示的數字,范圍:-32768~32767* @param Length 要顯示數字的長度,范圍:1~5* @retval 無*/ void LCD_ShowSignedNum(unsigned char Line,unsigned char Column,int Number,unsigned char Length) {unsigned char i;unsigned int Number1;LCD_SetCursor(Line,Column);if(Number>=0){LCD_WriteData('+');Number1=Number;}else{LCD_WriteData('-');Number1=-Number;}for(i=Length;i>0;i--){LCD_WriteData(Number1/LCD_Pow(10,i-1)%10+'0');} }/*** @brief 在LCD1602指定位置開始以十六進制顯示所給數字* @param Line 起始行位置,范圍:1~2* @param Column 起始列位置,范圍:1~16* @param Number 要顯示的數字,范圍:0~0xFFFF* @param Length 要顯示數字的長度,范圍:1~4* @retval 無*/ void LCD_ShowHexNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length) {unsigned char i,SingleNumber;LCD_SetCursor(Line,Column);for(i=Length;i>0;i--){SingleNumber=Number/LCD_Pow(16,i-1)%16;if(SingleNumber<10){LCD_WriteData(SingleNumber+'0');}else{LCD_WriteData(SingleNumber-10+'A');}} }/*** @brief 在LCD1602指定位置開始以二進制顯示所給數字* @param Line 起始行位置,范圍:1~2* @param Column 起始列位置,范圍:1~16* @param Number 要顯示的數字,范圍:0~1111 1111 1111 1111* @param Length 要顯示數字的長度,范圍:1~16* @retval 無*/ void LCD_ShowBinNum(unsigned char Line,unsigned char Column,unsigned int Number,unsigned char Length) {unsigned char i;LCD_SetCursor(Line,Column);for(i=Length;i>0;i--){LCD_WriteData(Number/LCD_Pow(2,i-1)%2+'0');} }

IIC總線AT24C02芯片實驗(E2PROM)

IIC總線協議















24C02芯片手冊閱讀


前面講了,器件前四位地址固定為1010,后三位在開發板里全部接地,因此器件地址確定為:0X1010 000.




編寫代碼

IIC.h

#ifndef __I2C_H__ #define __I2C_H__void I2C_Start(void); void I2C_Stop(void); void I2C_SendByte(unsigned char Byte); unsigned char I2C_ReceiveByte(void); void I2C_SendAck(unsigned char AckBit); unsigned char I2C_ReceiveAck(void);#endif

IIC.c

#include <REGX52.H>sbit I2C_SCL=P2^1; sbit I2C_SDA=P2^0;/*** @brief I2C開始* @param 無* @retval 無*/ void I2C_Start(void) {I2C_SDA=1;I2C_SCL=1;//前后要保證間隔4.7us,郭天祥老師在這里寫了個delay空函數(下同)I2C_SDA=0;I2C_SCL=0; }/*** @brief I2C停止* @param 無* @retval 無*/ void I2C_Stop(void) {I2C_SDA=0;I2C_SCL=1;I2C_SDA=1; }/*** @brief I2C發送一個字節* @param Byte 要發送的字節* @retval 無*/ void I2C_SendByte(unsigned char Byte) {unsigned char i;//單片機節省空間 不用inttemp = Byte;for(i=0;i<8;i++){temp = temp<<1;I2C_SDA = CY;//溢出位//I2C_SDA=Byte&(0x80>>i); 這種方法沒看懂I2C_SCL=1;I2C_SCL=0;//低電平可改變數據 下一循環送入新的數據} }/*** @brief I2C接收一個字節* @param 無* @retval 接收到的一個字節數據*/ unsigned char I2C_ReceiveByte(void) {unsigned char i,k,Byte=0x00;I2C_SDA=1;for(i=0;i<8;i++){I2C_SCL=1;j = I2C_SDA;k = (k<<1)|j;//if(I2C_SDA){Byte|=(0x80>>i);}I2C_SCL=0;}return k; }/*** @brief I2C發送應答* @param AckBit 應答位,0為應答,1為非應答* @retval 無*/ void I2C_SendAck(unsigned char AckBit) {I2C_SDA=AckBit;I2C_SCL=1;I2C_SCL=0; }/*** @brief I2C接收應答位* @param 無* @retval 接收到的應答位,0為應答,1為非應答*/ unsigned char I2C_ReceiveAck(void) {unsigned char AckBit;I2C_SDA=1;I2C_SCL=1;AckBit=I2C_SDA;I2C_SCL=0;return AckBit; }

AT24C02.h

#ifndef __AT24C02_H__ #define __AT24C02_H__void AT24C02_WriteByte(unsigned char WordAddress,Data); unsigned char AT24C02_ReadByte(unsigned char WordAddress);#endif

AT24C02.c

#include <REGX52.H> #include "I2C.h"#define AT24C02_ADDRESS 0xA0//地址高四位固定是1010為a 后三位為000 寫位為0/*** @brief AT24C02寫入一個字節* @param WordAddress 要寫入字節的地址* @param Data 要寫入的數據* @retval 無*/ void AT24C02_WriteByte(unsigned char WordAddress,Data) {I2C_Start();I2C_SendByte(AT24C02_ADDRESS);//發送器件地址寫I2C_ReceiveAck(); //收到應答I2C_SendByte(WordAddress); //要寫入字節的地址 自己隨便定I2C_ReceiveAck(); //收到應答I2C_SendByte(Data); //發送(寫入)數據I2C_ReceiveAck(); //收到應答I2C_Stop(); }/*** @brief AT24C02讀取一個字節* @param WordAddress 要讀出字節的地址* @retval 讀出的數據*/ unsigned char AT24C02_ReadByte(unsigned char WordAddress) {unsigned char Data;I2C_Start();I2C_SendByte(AT24C02_ADDRESS);//偽寫I2C_ReceiveAck();I2C_SendByte(WordAddress);I2C_ReceiveAck();I2C_Start();I2C_SendByte(AT24C02_ADDRESS|0x01);//代表要讀數據I2C_ReceiveAck();Data=I2C_ReceiveByte(); //讀到數據I2C_SendAck(1);I2C_Stop();return Data; }

總結

以上是生活随笔為你收集整理的学会阅读硬件的原理图、数据手册大全的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。