基于亞博K210開發板——內存卡讀寫文件

開發板

亞博K210開發板
在這里插入圖片描述

實驗目的

本實驗主要學習 K210 通過 SPI 讀寫內存卡文件的功能

實驗準備

實驗元件

開發板自帶的 TF 卡、LCD 顯示屏
提前準備好 FAT32 格式的TF 卡。TF 插入 TF 卡槽的時候注意方向,TF 卡的金手指那一面需要面向開發板,如果方向插反了是無法讀寫數據的。TF卡尺寸小,性能好,傳輸速度快,最初是用于支持內存擴展的手機上,比較適合儲存高清攝像和高音質音頻內容,因而被廣泛應用于各種多媒體設備上)

硬件連接

K210 開發板出廠默認已經焊接 TF 卡槽,需要插入 TF 卡才可以使用,其中TF 卡槽的 TF_MISO 連接到 IO26,TF_CLK 連接到 IO27,TF_MOSI 連接到 IO28,TF_CSO連接 IO29。
在這里插入圖片描述

在這里插入圖片描述

SDK中相關API

SPI 是一種高速、高效率的串行接口技術。通常由一個主模塊和一個或多個從模塊組成,主模塊選擇一個從模塊進行同步通信,從而完成數據的交換。SPI是一個環形結構,通信時需要至少 4 根線(事實上在單向傳輸時 3 根線也可以),它們是 MISO(主設備數據輸入)、MOSI(主設備數據輸出)、SCLK(時鐘)、CS(片選)。

  • MISO– Master Input Slave Output,主設備數據輸入,從設備數據輸出;
  • MOSI– Master Output Slave Input,主設備數據輸出,從設備數據輸入;
  • SCLK – Serial Clock,時鐘信號,由主設備產生;
  • CS – Chip Select,從設備使能信號,由主設備控制。當有多個從設備的時候,因為每個從設備上都有一個片選引腳接入到主設備機中,當我們的主設備和某個從設備通信時將需要將從設備對應的片選引腳電平拉低或者是拉高。

在這里插入圖片描述

相關接口

spi_init:設置 SPI 工作模式、多線模式和位寬。
spi_init_non_standard:多線模式下設置指令長度、地址長度、等待時鐘數、指令地址傳輸模式。
spi_send_data_standard:SPI 標準模式傳輸數據。
spi_send_data_standard_dma:SPI 標準模式下使用 DMA 傳輸數據。
spi_receive_data_standard:標準模式下接收數據。
spi_receive_data_standard_dma:標準模式下通過 DMA 接收數據。
spi_send_data_multiple:多線模式發送數據。
spi_send_data_multiple_dma:多線模式使用 DMA 發送數據。
spi_receive_data_multiple:多線模式接收數據。
spi_receive_data_multiple_dma:多線模式通過 DMA 接收。
spi_fill_data_dma:通過 DMA 始終發送同一個數據,可以用于刷新數據。
spi_send_data_normal_dma:通過 DMA 發送數據。不用設置指令地址。
spi_set_clk_rate:設置 SPI 的時鐘頻率。
spi_handle_data_dma:SPI 通過 DMA 傳輸數據。

實驗原理

TF 有 4 個數據傳輸端,DAT0,DAT1,DAT2,DAT3。還有一個 CMD 腳,是用來讀取卡內信息的。
TF 卡主要管腳的功能:
CLK:時鐘信號,每個時鐘周期傳輸一個命令或數據位,頻率可在 0~25MHz之間變化,TF 卡的總線管理器可以不受任何限制的自由產生 0~25MHz 的頻率;
CMD:雙向命令和回復線,命令是主機到從卡操作的開始,命令可以是從主機到單卡尋址,也可以是到所有卡;回復是對之前命令的回答,回復可以來自單卡或所有卡;
DAT0~3:數據線,數據可以從 TF 卡傳向主機也可以從主機傳向 TF 卡。TF 卡傳輸數據一般有兩種模式,SD 模式和 SPI 模式,這里我們以 SPI 模式的方式傳輸數據。SPI 模式引腳如下:1:CS,2:DI,3:VSS,4:VDD,5:SCLK,6:VSS2,7:DO,8:RSV,9:RSV。
在這里插入圖片描述

實驗過程

  1. 首先初始化 K210 的硬件引腳和軟件功能使用的是 FPIOA 映射關系。
void hardware_init(void)
{/*** io26--miso--d1** io27--clk---sclk** io28--mosi--d0** io29--cs----cs*/fpioa_set_function(PIN_TF_MISO, FUNC_TF_SPI_MISO);fpioa_set_function(PIN_TF_CLK,  FUNC_TF_SPI_CLK);fpioa_set_function(PIN_TF_MOSI, FUNC_TF_SPI_MOSI);fpioa_set_function(PIN_TF_CS,   FUNC_TF_SPI_CS);
}
// 硬件IO口,與原理圖對應
#define PIN_TF_MISO            (26)
#define PIN_TF_CLK             (27)
#define PIN_TF_MOSI            (28)
#define PIN_TF_CS              (29)/*****************************SOFTWARE-GPIO********************************/
// 軟件GPIO口,與程序對應
#define TF_CS_GPIONUM          (2)/*****************************FUNC-GPIO************************************/
// GPIO口的功能,綁定到硬件IO口
#define FUNC_TF_SPI_MISO        (FUNC_SPI1_D1)
#define FUNC_TF_SPI_CLK         (FUNC_SPI1_SCLK)
#define FUNC_TF_SPI_MOSI        (FUNC_SPI1_D0)
#define FUNC_TF_SPI_CS          (FUNC_GPIOHS0 + TF_CS_GPIONUM)
  1. 設置系統時鐘頻率,由于 uarths 的時鐘來自 PLL0,所以設置 PLL0 之后需
    要重新初始化以下 uarths,否則 printf 可能會打印亂碼。
/* 設置系統時鐘頻率 */
sysctl_pll_set_freq(SYSCTL_PLL0, 800000000UL);
sysctl_pll_set_freq(SYSCTL_PLL1, 300000000UL);
sysctl_pll_set_freq(SYSCTL_PLL2, 45158400UL);
uarths_init();
  1. 檢測是否有 TF 卡,或者 TF 卡是否正常,如果不正常則退出。
if (check_sdcard())
{printf("SD card err\n");return -1;
}

如果初始化 TF 卡成功,則把 TF 的容量打印出來,單位為 G。

static int check_sdcard(void)
{uint8_t status;printf("/******************check_sdcard*****************/\n");status = sd_init();printf("sd init :%d\n", status);if (status != 0){return status;}printf("CardCapacity:%.1fG \n", (double)cardinfo.CardCapacity / 1024 / 1024 / 1024);printf("CardBlockSize:%d\n", cardinfo.CardBlockSize);return 0;
}
  1. 檢測 TF 卡的格式是否是 FAT32,如果不是則退出。
if (check_fat32())
{printf("FAT32 err\n");return -1;
}

如果檢測符合 FAT32 格式的 TF 卡,則把 TF 卡掛在到“0:”,并且把 TF 卡根
目錄下的文件和文件夾的名稱都打印出來。

static int check_fat32(void)
{static FATFS sdcard_fs;FRESULT status;DIR dj;FILINFO fno;printf("/********************check_fat32*******************/\n");status = f_mount(&sdcard_fs, _T("0:"), 1);printf("mount sdcard:%d\n", status);if (status != FR_OK)return status;printf("printf filename\n");status = f_findfirst(&dj, &fno, _T("0:"), _T("*"));while (status == FR_OK && fno.fname[0]){if (fno.fattrib & AM_DIR)printf("dir:%s\n", fno.fname);elseprintf("file:%s\n", fno.fname);status = f_findnext(&dj, &fno);}f_closedir(&dj);return 0;
}
  1. 向 TF 卡寫入文件,保存在 TF 卡跟目錄下的 test.txt,如果寫入失敗則退
    出。
sleep(1);
if (sd_write_file(_T("0:test.txt")))
{printf("SD write err\n");return -1;
}

在寫入文件之前需要先打開文件,如果文件不存在則需要創建新文件,寫入的數據都需要轉化成 uint8_t 類型,寫完數據后必須執行 f_close 關閉文件。

FRESULT sd_write_file(TCHAR *path)
{FIL file;FRESULT ret = FR_OK;printf("/*******************sd_write_file*******************/\n");uint32_t v_ret_len = 0;/* 打開文件,如果文件不存在,則新建 */if ((ret = f_open(&file, path, FA_CREATE_ALWAYS | FA_WRITE)) != FR_OK){printf("open file %s err[%d]\n", path, ret);return ret;}else{printf("Open %s ok\n", path);}/* 要寫入的數據 */uint8_t data[] = {'H','i',',','D','a','t','a',' ','W','r','i','t','e',' ','O','k','!'};/* 寫入數據 */ret = f_write(&file, data, sizeof(data), &v_ret_len);if (ret != FR_OK){printf("Write %s err[%d]\n", path, ret);}else{printf("Write %d bytes to %s ok\n", v_ret_len, path);}/* 關閉文件 */f_close(&file);return ret;
}
  1. 從 TF 卡讀取文件,文件為在 TF 卡根目錄下的 test.txt。
if (sd_read_file(_T("0:test.txt")))
{printf("SD read err\n");return -1;}

讀文件前需要判斷文件的狀態,并且打開文件,如果文件不存在或者出錯,則返回,如果正常則以只讀方式打開文件,并且把讀到的數據通過串口發送出來。

FRESULT sd_read_file(TCHAR *path)
{FIL file;FRESULT ret = FR_OK;printf("/*******************sd_read_file*******************/\n");uint32_t v_ret_len = 0;/* 檢測文件狀態 */FILINFO v_fileinfo;if ((ret = f_stat(path, &v_fileinfo)) == FR_OK){printf("%s length is %lld\n", path, v_fileinfo.fsize);}else{printf("%s fstat err [%d]\n", path, ret);return ret;}/* 只讀方式打開文件 */if ((ret = f_open(&file, path, FA_READ)) == FR_OK){char v_buf[64] = {0};ret = f_read(&file, (void *)v_buf, 64, &v_ret_len);if (ret != FR_OK){printf("Read %s err[%d]\n", path, ret);}else{printf("Read :> %s \n", v_buf);printf("total %d bytes lenth\n", v_ret_len);}/* 關閉文件 */f_close(&file);}return ret;
}
  1. 編譯調試,燒錄運行
    進入 build 目錄,運行以下命令編譯。
cmake .. -DPROJ=sdcard -G "MinGW Makefiles"
make

編譯完成后,在 build 文件夾下會生成 sdcard.bin 文件。使用type-C 數據線連接電腦與 K210開發板,打開kflash,選擇對應的設備,再將程序固件燒錄到 K210 開發板上。

實驗現象

燒錄完成固件后,系統會彈出一個終端界面,如果沒有彈出終端界面的可以打開串口助手顯示調試內容。
在這里插入圖片描述

實驗總結

1.TF 讀或寫文件前都必須先打開文件,讀寫操作結束后也必須關閉文件。
2.TF 卡通過 SPI 通訊的方式,讀寫數據以 uint8_t 為基本單位。
3.每次燒錄完固件后,都需要重新給 K210 開發板上電,否則會出現 TF 卡初始化
失敗而退出系統的問題。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/901942.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/901942.shtml
英文地址,請注明出處:http://en.pswp.cn/news/901942.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

51單片機實驗五:A/D和D/A轉換

一、實驗環境與實驗器材 環境:Keli,STC-ISP燒寫軟件,Proteus. 器材:TX-1C單片機(STC89C52RC)、電腦。 二、 實驗內容及實驗步驟 1.A/D轉換 概念:模數轉換是將連續的模擬信號轉換為離散的數字信…

C++ 常用的智能指針

C 智能指針 一、智能指針類型概覽 C 標準庫提供以下智能指針&#xff08;需包含頭文件 <memory>&#xff09;&#xff1a; unique_ptr&#xff1a;獨占所有權&#xff0c;不可復制&#xff0c; 可移動shared_ptr&#xff1a;共享所有權&#xff0c;用于引用計數weak_pt…

6.8.最小生成樹

一.復習&#xff1a; 1.生成樹&#xff1a; 對于一個連通的無向圖&#xff0c;假設圖中有n個頂點&#xff0c;如果能找到一個符合以下要求的子圖&#xff1a; 子圖中包含圖中所有的頂點&#xff0c;同時各個頂點保持連通&#xff0c; 而且子圖的邊的數量只有n-1條&#xff0…

Spring Boot 集成金蝶 API 演示

? Spring Boot 集成金蝶 API 演示&#xff1a;登錄 / 注銷 Cookie 保存 本文將通過 Spring Boot 完整實現一套金蝶接口集成模型&#xff0c;包括&#xff1a; ? 普通登錄? AppSecret 登錄? 注銷? Cookie 保存與復用 &#x1f4c5; 項目結構 src/ ├── controller/ │…

React 受控表單綁定基礎

React 中最常見的幾個需求是&#xff1a; 渲染一組列表綁定點擊事件表單數據與組件狀態之間的綁定 受控表單綁定是理解表單交互的關鍵之一。 &#x1f4cd;什么是受控組件&#xff1f; 在 React 中&#xff0c;所謂“受控組件”&#xff0c;指的是表單元素&#xff08;如 &l…

基于FPGA的AES加解密系統verilog實現,包含testbench和開發板硬件測試

目錄 1.課題概述 2.系統測試效果 3.核心程序與模型 4.系統原理簡介 4.1 字節替換&#xff08;SubBytes&#xff09; 4.2 行移位&#xff08;ShiftRows&#xff09; 4.3 列混合&#xff08;MixColumns&#xff09; 4.4 輪密鑰加&#xff08;AddRoundKey&#xff09; 4.…

6.5 GitHub監控系統實戰:雙通道采集+動態調度打造高效運維體系

GitHub Sentinel Agent 定期更新功能設計與實現 關鍵詞:GitHub API 集成、定時任務調度、Python 爬蟲開發、SMTP 郵件通知、系統穩定性保障 1. GitHub 項目數據獲取功能 1.1 雙通道數據采集架構設計 #mermaid-svg-ZHJIMXcMAyDHVhmV {font-family:"trebuchet ms",v…

Explorer++:輕量級高效文件管理器!!

項目簡介 Explorer 是一款專為Windows操作系統設計的輕量級且高效的文件管理器。作為Windows資源管理器的強大替代方案&#xff0c;它提供了豐富的特性和優化的用戶體驗&#xff0c;使得文件管理和組織變得更加便捷高效。無論是專業用戶還是普通用戶&#xff0c;都能從中受益&a…

7、生命周期:魔法的呼吸節奏——React 19 新版鉤子

一、魔法呼吸的本質 "每個組件都是活體魔法生物&#xff0c;呼吸節奏貫穿其生命始終&#xff0c;"鄧布利多的冥想盆中浮現三維相位圖&#xff0c;"React 19的呼吸式鉤子&#xff0c;讓組件能量流轉如尼可勒梅的煉金術&#xff01;" ——以霍格沃茨魔法生理…

理解計算篇--正則表達式轉NFA--理論部分

空正則表達式轉NFA單字符正則表達式轉NFA拼接正則表達式轉NFA選擇正則表達式轉NFA重復正則表達式轉NFA 正則表達式轉NFA–實戰部分 空正則表達式轉NFA 轉換步驟&#xff1a; 構建1個只有1個狀態的NFA起始狀態也是接受狀態沒有規則&#xff0c;即規則集為空 單字符正則表達式…

穩態模型下的異步電機調速【運動控制系統】

異步電動機&#xff1a; n1是同步轉速&#xff08;電機和磁芯同步時候的轉速&#xff09; n&#xff1a;電機的實際轉速 異步電動機恒壓頻比的概念&#xff0c;為什么基頻以下可以采取恒壓頻率&#xff0c;基頻以上不可以采用恒壓頻比&#xff1a; 異步電動機的恒壓頻比&…

【KWDB 創作者計劃】_算法篇---Stockwell變換

文章目錄 前言一、Stockwell變換原理詳解1.1 連續S變換定義1.2 離散S變換1.3簡介 二、S變換的核心特點2.1頻率自適應的時頻分辨率2.1.1高頻區域2.1.2低頻區域 2.2無交叉項干擾2.3完全可逆2.4相位保持2.5與傅里葉譜的直接關系 三、應用領域3.1地震信號分析3.2生物醫學信號處理3.…

云計算(Cloud Computing)概述——從AWS開始

李升偉 編譯 無需正式介紹亞馬遜網絡服務&#xff08;Amazon Web Services&#xff0c;簡稱AWS&#xff09;。作為行業領先的云服務提供商&#xff0c;AWS為全球開發者提供了超過170項隨時可用的服務。 例如&#xff0c;Adobe能夠獨立于IT團隊開發和更新軟件。通過AWS的服務&…

Python爬蟲第17節-動態渲染頁面抓取之Selenium使用下篇

目錄 引言 一、獲取節點信息 1.1 獲取屬性 1.2 獲取文本值 1.3 獲取ID、位置、標簽名、大小 二、切換Frame 三、延時等待 3.1 隱式等待 3.2 顯式等待 四、前進后退 五、Cookies 六、選項卡管理 七、異常處理 引言 這一節我們繼續講解Selenium的使用下篇&#xff0…

容器docker入門學習

這里寫目錄標題 容器容器的軟件廠商 dockerdocker引擎 虛擬化虛擬化技術 docker安裝詳解1、安裝檢查2、安裝yum相關的工具3、安裝docker-ce軟件4、查看docker版本5、啟動docker服務6、設置docker開機啟動7、查看有哪些docker容器運行進程8、查看容器里有哪些鏡像9、下載nginx軟…

文獻總結:NIPS2023——車路協同自動駕駛感知中的時間對齊(FFNet)

FFNet 一、文獻基本信息二、背景介紹三、相關研究1. 以自車為中心的3D目標檢測2. 車路協同3D目標檢測3. 特征流 四、FFNet網絡架構1. 車路協同3D目標檢測任務定義2. 特征流網絡2.1 特征流生成2.2 壓縮、傳輸與解壓縮2.3 車輛傳感器數據與基礎設施特征流融合 3. 特征流網絡訓練流…

git 出現 port 443 Connection timed out

梯子正常延遲不算嚴重&#xff0c;但在使用git push時反復出現 fatal: unable to access https://github.com/irvingwu5/xxxx.git/ Error in the HTTP2 framing layer Failed to connect to github.com port 443 after 136353 ms: Connection timed out 將git的網絡配置與梯子…

【2025年4月18日】android studiio最新設置沉浸式狀態欄教程

&#x1f62b;【2025年4月18日】搞了一整天&#xff0c;終于完美搞定 Android 沉浸式狀態欄&#xff08;WebView 本地HTML&#xff09; 最近在做一個個人項目&#xff0c;用 Android 加載本地 HTML 做個小工具。按理說用 WebView 加載頁面很簡單嘛——結果沉浸式狀態欄這個坑…

如何刪除 Launchpad 中 Chrome 的圖標

有一天突然在 Launchpad 中出現下面的圖標&#xff0c;在 Finder 的 Applications 中也沒有&#xff0c;不知道如何刪除。最終在《How to remove chrome app icons from launchpad?》中找到了答案。中文互聯網上并沒有搜到相關帖子&#xff0c;遂作記錄。 解決辦法很簡單&am…