FPGA-Xilinx ZYNQ PS端实现SD卡文件数据读取-完整代码

FPGA-Xilinx ZYNQ PS端实现SD卡文件数据读取

本章节记录Xilinx ZYNQ PS端实现SD卡txt文件的数据读取。
踩坑记录,本章节主要内容参考原子哥
板子:xilinx zynq 7010


文章目录

  • FPGA-Xilinx ZYNQ PS端实现SD卡文件数据读取
  • 一、开发板引脚配置
  • 二、PS端导入FATFS文件系统所需xilffs库
  • 三、代码细节解释
  • 四、完整代码
  • 总结


一、开发板引脚配置

xilinx zynq 7010使用的sd卡的引脚,通过手册可知,
SD引脚为MIO40-45,card detect MIO47
所以采用SD 0,如下图:
sd卡槽

引脚配置
注意:直接跑原子哥的工程代码是行不通的,因为原子哥是7020板子,自己的是7010

二、PS端导入FATFS文件系统所需xilffs库

导入xilffs库,因为需要使用FATFS文件系统
配置
配置信息
如果代码无法识别到f_mount()函数,则需要的手动添加xilffs库,
如下图:

手动导入库
但我导入了这个之后,虽然可以识别到f_mount(),但无法使用ff.h中的f_gets()(已经include “ff.h”),不知道为什么,
如果有解决方法的,非常希望大家能够评论区给出。

三、代码细节解释

在copy原子哥代码时,需要注意xilffs的版本,版本不同函数有所改动,形参调用也不同。我的是xilinx zynq 7010,xilffs是3.7,原子哥是xilinx zynq 7020,xilffs是4.0.

//原子哥xilffs4.0代码:
status = f_mkfs(Path, FM_FAT32, 0, work, sizeof work);

//我xilffs3.7代码:
status = f_mkfs(Path, 1,sizeof work);

同时需要注意,因为使用的是SD 0 ,所以f_mount()函数需要选择挂载0口

status = f_mount(&fatfs, Path, 0); //挂载SD卡

同时注意,读取代码中的buffer[100]是用来获取一次100个数据的,temp_out_buffer[100]用于存储每一行的数据,用于输出或者处理,这样子分开两个数组进行分别操作,可以防止只使用一个数组出现数据覆盖的现象。
(因为txt每行的数据最多只有20个,所以buffer和temp_out_buffer数组定义只需要定义20个也是行得通的,但没试过,反正内存够)

每一行的数据获取结束标志位十分重要,这段代码不能丢!!!

temp_out_buffer[buffer_index] = '\0'; // 结束符号标志!重要!!

四、完整代码

#include "xparameters.h"
#include "xil_printf.h"
#include "ff.h"
#include "xdevcfg.h"
#include "stdio.h"

#define FILE_NAME "data.txt"                //定义文件名

const char src_str[30] = "www.openedv.com"; //定义文本内容
static FATFS fatfs;                         //文件系统

//初始化文件系统
int platform_init_fs()
{
	FRESULT status;
	TCHAR *Path = "0:/";
	BYTE work[512];

    //注册一个工作区(挂载分区文件系统)
    //在使用任何其它文件函数之前,必须使用f_mount函数为每个使用卷注册一个工作区
	status = f_mount(&fatfs, Path, 0);  //挂载SD卡
	if (status != FR_OK) {
		xil_printf("Volume is not FAT formated; formating FAT\r\n");
		//格式化SD卡
		status = f_mkfs(Path, 1,sizeof work);
		if (status != FR_OK) {
			xil_printf("Unable to format FATfs\r\n");
			return -1;
		}
		//格式化之后,重新挂载SD卡
		status = f_mount(&fatfs, Path, 1);
		if (status != FR_OK) {
			xil_printf("Unable to mount FATfs\r\n");
			return -1;
		}
	}
	return 0;
}

//挂载SD(TF)卡
int sd_mount()
{
    FRESULT status;
    //初始化文件系统(挂载SD卡,如果挂载不成功,则格式化SD卡)
    status = platform_init_fs();
    if(status){
        xil_printf("ERROR: f_mount returned %d!\n",status);
        return XST_FAILURE;
    }
    return XST_SUCCESS;
}

//SD卡写数据
int sd_write_data(char *file_name,u32 src_addr,u32 byte_len)
{
    FIL fil;         //文件对象
    UINT bw;         //f_write函数返回已写入的字节数

    //打开一个文件,如果不存在,则创建一个文件
    f_open(&fil,file_name,FA_CREATE_ALWAYS | FA_WRITE);
    //移动打开的文件对象的文件读/写指针     0:指向文件开头
    f_lseek(&fil, 0);
    //向文件中写入数据
    f_write(&fil,(void*) src_addr,byte_len,&bw);
    //关闭文件
    f_close(&fil);
    return 0;
}

//SD卡读数据
int sd_read_data(char *file_name,u32 src_addr,u32 byte_len)
{
	FIL fil;         //文件对象
    UINT br;         //f_read函数返回已读出的字节数

    //打开一个只读的文件
    f_open(&fil,file_name,FA_READ);
    //移动打开的文件对象的文件读/写指针     0:指向文件开头
    f_lseek(&fil,0);
    //从SD卡中读出数据
    f_read(&fil,(void*)src_addr,byte_len,&br);
    //关闭文件
    f_close(&fil);
    return 0;
}

// 定义结构体存储X和Y的数值
typedef struct {
    int x;
    int y;
} DataPoint;

int parse_line(char *line, int *x, int *y)
{
    return sscanf(line, "X: %d, Y: %d", x, y);
}

//main函数
int main()
{
    int status,len;
    char line[100]; // 适当的缓冲区大小以逐行读取数据

    status = sd_mount();           //挂载SD卡
    if(status != XST_SUCCESS){
		xil_printf("Failed to open SD card!\n");
		return 0;
    }
    else
        xil_printf("Success to open SD card!\n\n");



   //SD卡读数据
    FIL fil;         // 文件对象
    TCHAR buffer[100]; // 适当的缓冲区大小以读取数据
    TCHAR temp_out_buffer[100]={0};//用于临时存储一行数据并输出,会被下一行数据覆盖
    UINT bytesRead;
    int buffer_index = 0;
	if (f_open(&fil, FILE_NAME, FA_READ) == FR_OK)
	{
		while (f_read(&fil, buffer, sizeof(buffer), &bytesRead) == FR_OK && bytesRead > 0)
		{
			for (int i = 0; i < bytesRead; i++)
			{
//				printf("buffer[%d] = %c\n",i,buffer[i]);
				if (buffer[i] == '\n' || buffer[i] == '\r')
				{
					temp_out_buffer[buffer_index] = '\0';  // 结束符号标志!重要!!
					buffer_index = 0;

					DataPoint dataPoint;
					if (parse_line(temp_out_buffer, &dataPoint.x, &dataPoint.y) == 2)
					{
						xil_printf("X: %d, Y: %d\r\n", dataPoint.x, dataPoint.y);
					}
					else
					{
//						xil_printf("Error parsing line: %s\n", buffer);
					}
				}
				else
				{
					temp_out_buffer[buffer_index++] = buffer[i];
				}
			}
		}
		f_close(&fil);
	}
	else
	{
		printf("open file failed \n");
	}
    return 0;
  }




总结

本章节对于FPGA PS 端SD卡文件数据读取处理进行了记录,主要还是防坑记录,毕竟自己也是找了不少资料才完成。
还有一些待完善内容,包括:文件读取数据存DDR,从DDR读出来处理后再存回DDR,然后再把处理好的数据传给PL端进行操作。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/264332.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

嵌入式科普(5)ARM GNU Toolchain相关概念和逻辑

一、目的/概述 二、资料来源 三、逻辑和包含关系 四、Arm GNU Toolchain最常用的命令 嵌入式科普(5)ARM GNU Toolchain相关概念和逻辑 一、目的/概述 对比高集成度的IDE(MDK、IAR等)&#xff0c;Linux开发需要自己写Makefile等多种脚本。eclipse、Visual Studio等需要了解预处…

高德地图逆地理编码踩坑日志

本人是一枚Java小白&#xff0c;公司项目中用到根据经纬度反查该地址中文信息的场景&#xff0c;因为一开始调用的经纬度是能反查出区域编码的&#xff0c;以为towncode都是String返回结果&#xff0c;如下图&#xff1a; 没想到当没有名字任何一个城市区域的时候&#xff0c;…

在Linux安装卸载文件

目录 一、Linux系统应用程序 1.典型的应用程序的目录结构 2、常见的软件包封装类型 二、RPM软件包管理 1、RPM是什么&#xff1f; 2、rpm一般命名格式 3、RPM安装包从何而来&#xff1f;如何挂载&#xff1f; 4、挂载的注意事项: 5、目的&#xff1a;提供安装包 6、查…

MyBatis——MyBatis的延迟加载

MyBatis的延迟加载&#xff08;一对多查询案例&#xff09; 1.什么是延迟加载&#xff1f; 开启延迟加载后&#xff0c;在真正使用数据的时候才发起级联查询&#xff0c;不用的时候不查询。 2.pojo User类&#xff1a; package com.wt.pojo;import java.io.Serializable; …

【华为鸿蒙系统学习】- HarmonyOS4.0之App项目开发|自学篇

&#x1f308;个人主页: Aileen_0v0 &#x1f525;热门专栏: 华为鸿蒙系统学习|计算机网络|数据结构与算法 &#x1f4ab;个人格言:"没有罗马,那就自己创造罗马~" 目录 创建鸿蒙第一个App项目 项目创建 工程目录区 预览区 运行Hello World 基本工程目录 ws:工…

SpringBoot+vue实现评论区分页效果

当评论区含大量数据时&#xff0c;一次性查询速度很慢&#xff0c;所以使用分页&#xff0c;实现分页效果。 前端&#xff1a; <h3>评论</h3><div><div style"font-size:14px;padding:10px;" v-for"r in form.remark"><!-- …

【Matlab in VSCode】在VSCode中编辑MATLAB文件

【Matlab in VSCode】在VSCode中编辑MATLAB文件 1.安装插件 插件&#xff1a;在vscode拓展商店下载 MATLABMatlab in VSCode 其他&#xff1a;Windows环境MATLAB2019bpython3.7.9 2.插件配置 MATLAB插件下载后不用配置。 Matlab in VSCode需要进行相应的配置。 Windows…

Ubuntu 常用命令之 ping 命令用法介绍

&#x1f4d1;Linux/Ubuntu 常用命令归类整理 ping命令是一种网络诊断工具&#xff0c;用于测试主机之间网络的连通性。它发送ICMP Echo Request消息到指定的网络主机&#xff0c;并等待接收ICMP Echo Reply。通过这种方式&#xff0c;我们可以知道两台主机之间的网络是否畅通…

elementUI CDN引入本地文件报错,刷新页面报错

报错原因&#xff1a;vue.config.js的externals 配置中有外部cdn引入配置&#xff0c;而当前场景我的element是直接下载放在本地的&#xff0c;这时就需要将配置注释或者删除 webpack 中的 externals 配置项用于指定在打包时需要排除掉的模块&#xff0c;这些模块会被视为外部依…

bugku-misc-这是一张单纯的图片

附件&#xff1a;图片 1、查看属性 2、010 whex打开看看 可以看到html编码&#xff0c;将文件后缀&#xff0c;改成html&#xff0c;打开 即可

蓝牙物联网与嵌入式开发如何结合?

蓝牙物联网与嵌入式开发可以紧密结合&#xff0c;以实现更高效、更智能的物联网应用。以下是一些结合的方式&#xff1a; 嵌入式开发为蓝牙设备提供硬件基础设施和控制逻辑&#xff1a;嵌入式系统可以利用微处理器和各种外设组成的系统&#xff0c;为蓝牙设备提供硬件基础设施和…

FastGPT+ChatGLM3-6b搭建知识库

前言&#xff1a;我用fastgpt直接连接chatglm3&#xff0c;没有使用oneai&#xff0c;不是很复杂&#xff0c;只需要对chatglm3项目代码做少量修改就能支持使用embeddings&#xff0c;向量模型用的m3e&#xff0c;效果还可以 我的配置&#xff1a; 处理器&#xff1a;i5-13500 …

web前端html笔记2

新增状态标签<meter><progress> <meter> 属性 值 描述 high 数值 规定高值 low 数值 规定低值 max 数值 规定最大值 min 数值 规定最小值 optimum 数值 规定最优值 value 数值 规定当前值 <body> <meter high"50" …

鸿蒙(HarmonyOS)项目方舟框架(ArkUI)之TextInput输入框组件

鸿蒙&#xff08;HarmonyOS&#xff09;项目方舟框架&#xff08;ArkUI&#xff09;之TextInput输入框组件 一、操作环境 操作系统: Windows 10 专业版 IDE:DevEco Studio 3.1 SDK:HarmonyOS 3.1 二、TextInput 接口 TextInput(value?:{placeholder?: ResourceStr, tex…

NIO的实战教程(简单且高效)

1. 参考 建议按顺序阅读以下三篇文章 为什么NIO被称为同步非阻塞&#xff1f; Java IO 与 NIO&#xff1a;高效的输入输出操作探究 【Java.NIO】Selector&#xff0c;及SelectionKey 2. 实战 我们将模拟一个简单的HTTP服务器&#xff0c;它将响应客户端请求并返回一个固定的…

【EI会议征稿】2024年光电信息与光学工程国际学术会议(OIOE 2024)

2024年光电信息与光学工程国际学术会议&#xff08;OIOE 2024&#xff09; 2024 International Conference on Optoelectronic Information and Optical Engineering 光电信息技术和光学工程技术广泛应用于国民经济和国防建设的各行各业。近年来&#xff0c;随着相关产业的迅…

AcWing算法提高课-1.4.2股票买卖 IV

算法提高课整理 CSDN个人主页&#xff1a;更好的阅读体验 原题链接 题目描述 给定一个长度为 n n n 的数组&#xff0c;数组中的第 i i i 个数字表示一个给定股票在第 i i i 天的价格。 设计一个算法来计算你所能获取的最大利润&#xff0c;你最多可以完成 k k k 笔交易…

2024年你的年度目标OKR制定好了吗?

标题2023年余额见底&#xff0c;2024年的FLAG都制定好了吗&#xff1f; 目标很明确&#xff0c;计划很丰满&#xff0c;执行起来又处处透着一点点乏力&#xff0c;怎么办&#xff1f; 2024年可以尝试用OKR制定目标。 OKR目标管理方法&#xff0c;既适用于企业&#xff0c;也…

智能优化算法应用:基于卷尾猴算法3D无线传感器网络(WSN)覆盖优化 - 附代码

智能优化算法应用&#xff1a;基于卷尾猴算法3D无线传感器网络(WSN)覆盖优化 - 附代码 文章目录 智能优化算法应用&#xff1a;基于卷尾猴算法3D无线传感器网络(WSN)覆盖优化 - 附代码1.无线传感网络节点模型2.覆盖数学模型及分析3.卷尾猴算法4.实验参数设定5.算法结果6.参考文…

前端案例—antdDesign的Select多选框组件加上全选功能

前端案例—antdDesign的Select多选框组件加上全选功能。 实现效果如下&#xff1a; Select 组件里有这个属性&#xff0c;可以利用这个对下拉菜单进行自定义。 const handleChange (e, value) > {setSelectState(e.target.checked)let arr productOptions?productOption…