手把手教你Uboot移植
记录移植Uboot建立自己的UBOOT编译配置复制设置并写入.config123456noah@ubuntu:~/imx6ull/bsp/bootloader/uboot-imx/configs$ cp mx6ull_14x14_evk_emmc_defconfig igboard_defconfignoah@ubuntu:~/imx6ull/bsp/bootloader/uboot-imx/configs$ cd ..noah@ubuntu:~/imx6ull/bsp/bootloader/uboot-imx$ make igboard_defconfig## configuration written to .config#
进入配置界面,修改配置文件1noah@ubuntu:~/imx6ull/bsp/bootloader/uboot-imx$ make menuconfig
按选项来依次介绍是
ARM architecture ARM架构
ARM architecture ARM架构
用于指定芯片的ARM体系结构,有助于保证U-Boot与特定ARM处理器的指令集和硬 ...
UBOOT、KERNEL移植过程(二)
BOOT、KERNEL移植过程(二)KERNEL内核移植之前我们已经成功移植了Uboot,虽然还有启动时蜂鸣器一直在响,不过这也是后续能够解决的问题,接下来先进行Kernel内核的移植
下载内核可以从官方下载imx6ull的内核,当然由于是外网的且文件较大下载会很久,可以先选择分支然后下载指定分支的压缩包也可
123456# 下载整合包git clone https://source.codeaurora.org/external/imx/linux-imx# 查看所有分支git branch --all# 切换到所要的分支git checkout $所选分支$
若已经从郭工文件服务器下载imx6ull包的,内核的路径在
12# 我这里把imx6ull的文件夹下载到~路径下~/imx6ull/bsp/kernel/linux-imx
修改顶层的Makefile
12ARCH = armCROSS_COMPILE = arm-linux-gnueabihf-
建立自己的板子配置拷贝配置文件
12345# 查看已经编写好的配置文件vim arch/arm/configs/igk ...
UBOOT、KERNEL移植过程(一)
UBOOT、KERNEL移植过程(一)Linux搭建环境 在进行UBOOT、KERNEL移植之前,需要先在Linux下搭建好开发环境,基本的有tftp环境、nfs环境、交叉编译工具链的搭建
报错处理 tftp和nfs环境搭建时,如果配置文件写错,重启服务时会有报错提示,此时需要查看系统日志根据日志消息解决问题
1234# 查看系统日志指令tail -f /var/log/syslog# 或是查看倒数10条日志tail -10 /var/log/syslog
tftp环境 tftp协议:
典型的cs模型: ubuntu为服务器端,开发板为客户端
客户端可以下载服务器端上的内容,效率高
1、查看是否已经安装tftp服务器
1dpkg -s tftpd-hda
2、若不存在则执行以下命令安装tftp服务
12345# 更新apt源sudo apt-get updata# 安装tftp相关服务# tftpd-hpa是服务器 tftp-hda是客户端sudo apt-get install tftpd-hpa tftp-hpa -y
3、创建服务器工作路径并设置为最高权限 ...
Linux bsp驱动学习三:模块参数和模块之间通信
Linux bsp驱动学习三:模块参数和模块之间通信 为了增加模块的灵活性,可以给模块添加参数。模块参数可以控制模块的内部逻辑,从而使模块在不同的情况下,完成不同的功能,简单的说,模块参数就像函数的参数一样。
一、模块参数 用户空间的应用程序可以接受用户的参数,设备驱动程序有时候也需要接受参数。
例如一个模块可以实现两种相似的功能,这时可以传递一个参数到驱动模块,以决定其使用哪一种功能。参数需要在加载模块时指定,
例如 inmod xxx.ko param=1。
可以用“module_param(参数名,参数数据类型,参数读写权限)”来为模块定义个参数
1234static long a = 1;static int b = 1;module_param(a, long, S_IRUGO);module_param(b, int, S_IRUGO);
参数数据类型可以是 byte、short、ushort、int、uint、long、ulong、bool 和 charp(字符指针类型)。模块参数的类型中没有浮点类型,因为通常不在内核中使用浮点数。 ...
Linux bsp驱动学习二:驱动模块与Hello World
Linux bsp驱动学习二:驱动模块与Hello World
接下来将编写第一个驱动模块,该驱动模块功能是在加载时输出“Hello World”,卸载模块时输出“Goodbye World”。首先先对模块的重要组成部分进行介绍
一、驱动模块的组成 一个驱动模块的主要组成部分由如下组成,如下表所示,表中表示的是一个**规范的驱动模块应该包含的结构,同样也是一个规范的在源文件的编写顺序**,不按以下的顺序编写也不会报错,只是依靠以下顺序比较规范。
驱动模块的组成部分
头文件(必选)
模块参数(可选)
模块功能函数(可选)
其他(可选)
模块加载函数(必选)
模块卸载函数(必选)
模块许可声明(必选)
1、头文件(必选) 驱动模块会使用内核中的许多函数,所以需要包含必要的头文件。有两个头文件是所有驱动模块都必须包含的,分别是:
12#include <linux/module.h>#include <linux/init.h>
module.h文件包含了加载模块时需要使用的大量符号和函数定义。init.h包含 ...
Linux bsp驱动学习一:驱动开发入门
Linux bsp驱动学习一:驱动开发入门
设备驱动程序是计算机硬件与应用程序的接口,是软件系统与硬件系统沟通的桥梁。 如果没有设备驱动程序,那么硬件设备就只是一堆废铁,没有什么功能。
一、Linux 操作系统与驱动的关系 Linux系统下的程序开发一般分为两种: 一种是应用程序开发,一种是内核级驱动程序开发,这两种开发种类对应Linux的两种状态,分别是用户态和内核态。当我们在应用程序空间编写一个打印“Hello World”字符串的程序时,在调用 printf("Hello World") 之前的所有代码都运行在用户态。而当C语言库函数printf() 要开始往LCD显示器上打印”Hello World” 字符串时,它将会通过调用 write()系统调用来实现。而该系统调用将会让该进程从 用户态 切换到 内核态 来执行,此时Linux内核中的代码将会调用LCD驱动提供的相应接口函数,把该字符串输出到LCD显示屏上。在完成这些显示工作后,write() 系统调用将会返回,此时该进程将会从 内核态 切回到 用户态 继续运行。
由此可知:
进程从 用户态 切 ...
C按位运算符
C按位运算符 C按位运算符,重读后发现对后续写驱动很有用处,结合自己理解做记录
一、按位逻辑运算符复习一下常见的四种按位逻辑运算符,和数电内容基本一致
1、二进制反码或按位取反:~同数电非门,通过逐位比较两个运算对象,生成一个新值。
12~(10010001) // 表达式01101110 // 结果式
若val的类型为unsigned char即uint8_t,值为00000010,十进制为2。那么,~val的值为11111101,十进制为253
12// 使用参考val = ~val;
2、按位与:&同数电与门,通过逐位比较两个运算对象,生成一个新值。
123456(10010001) & (01101110) // 这里拿两个互为非的进行与运算00000000 // 那不就是全为0嘛 (10010001) & (01100101) // 取两个不相关的值时00000001 // 结果1
使用方法:
12val &= 0156; // 0156是八进制,数字前带0是八进制,0x是十六进制val = val ...
stm32配置ADS8681
stm32配置ADS8681 被提醒了,很多驱动写了就忘了,能用是能用,怎么配置的忘记了,故记录一下。
一、设置引脚123456789/*******ADS8681引脚初始化******* * RVS --> PB15 input * SCLK --> PD9 output * nCS --> PD10 output * RST --> PD13 output * SDI --> PD11 output * SDO1 --> PB14 input * SDO0 --> PD8 input********************************/
output引脚Speed全部拉very high
添加.h .c文件到工程中去,并添加引入路径
二、导入设置文件ads8681.h文件
12345678910111213141516171819202122232425262728293 ...
Linux APUE学习:7、C程序的进程控制(二)
Linux APUE学习:7、C程序的进程控制(二)文件共享 如果父进程和子进程写同一描述符指向的文件,但又没有任何形式的同步(如使父进程等待子进程),那么它们的输出就会相互混合(假定所用的述符是在 fork 之前打开的)。
在fork之后处理文件描述符有以下两种常见的情况:
父进程等待子进程完成。在这种情况下,父进程无需对其描述符做任何处理。当子进程终止后,它曾进行过读、写操作的任一共享的描述符的文件偏移量已做了相应更新(即子进程终止,子进程共享的文件描述符已经被close过一次)。
父进程和子进程各自执行不同的程序。在这种情况下,在 fork 之后,父进和子进程各自关闭它们不需使用的文件描述符,这样就不会干扰对方使用的文件描述符。这种方法是网络服务进程经常使用的。
fork一般有以下两种用法:
一个父进程希望复制自己,使得父进程和子进程同时执行不同的代码段。这在网络服务进程中是常见的——父进程等待客户端的服务请求。当这种请求到达时,父进程调用fork,使子进程处理此请求。父进程则继续等待下一个服务请求。
一个进程要执行一个不同的程序。这对shell是常见的情况 ...
Linux APUE学习:6、C程序的多进程
Linux APUE学习:6、C程序的多进程 本章介绍 UNIX 系统的进程控制,包括创建新进程、执行程序和进程终止。还将说明进程属性的各种 ID一一实际、有效和保的用户 和 D,以及它们如受到进控制的影本章还包括了解释器文件和 system函数。
代码参考 https://github.com/RoxyKko/APUE/tree/master/ch4
进程标识 每个进程都有一个非负整型表示的唯一进程ID。因为进程ID标识符总是唯一的,常将其用作其他标识符的一部分以保证其唯一性。例如,应用程序有时就把进程ID作为名字的一部分来创建一个唯一的文件名。
每个进程标识符在进程运行时总是唯一的,但进程标识符也可复用的。当一个进程终止后,其进程ID就成为复用的候选者。大多数UNIX系统实现延迟复用算法,使得赋予新建进程的ID不同于最近终止进程所使用的进程ID。这一操作可以避免将新进程误认为是使用同一进程ID号的已经终止的某个进程。
系统中有一些专用进程,但具体细节随着进程功能所实现不同。
ID为0的进程通常为调度进程,也称为交换进程(swapper)。此进程是内核的一 ...
Linux APUE学习:5、C程序的存储空间分配
Linux APUE学习:5、C程序的存储空间分配
共享库 在Unix系统中,共享库(Shared Library)是一种可重用的代码库,它包含了许多可由多个程序共享和调用的函数和资源。共享库在许多程序之间提供了一种共享代码的方式,以减少重复和节省系统资源。
共享库的主要优点包括:
节省内存:由于共享库可以被多个程序共享,系统只需将库加载到内存一次,而不是每个程序都加载一份独立的代码。这减少了内存的使用量,特别是当多个程序使用相同的库时。
减少程序体积:共享库允许程序仅包含其自身所需的最小代码量,而将其他功能委托给库。这样可以减小程序的体积,使得程序更加轻便。
简化更新:如果一个共享库需要进行更新或修复,只需更新库本身,而不需要重新编译和分发所有使用该库的程序。这样可以简化维护过程,并提供更快的修复和升级。
在Unix系统中,共享库通常使用动态链接的方式加载。这意味着在程序运行时,操作系统会在内存中加载共享库,并将程序中的函数调用链接到库中的对应函数。这种动态链接的机制使得程序可以在运行时动态加载和卸载共享库,从而提供了更大的灵活性和可扩展性。
共享库在Unix系统中使用 ...
Linux APUE学习:4、C程序的运行时环境和存储空间布局
Linux APUE学习:4、C程序的运行时环境和存储空间布局 C程序的命令行参数和环境表统称为程序的“**运行时环境**”。这是因为这些参数和变量在程序运行期间提供了重要的信息和配置选项,对于程序的正确执行至关重要。命令行参数是在程序启动时传递给程序的选项和参数,而环境表则包含了一些系统和用户定义的环境变量,这些变量可以影响到程序的行为。
命令行参数argv 当执行一个程序时,调用exec的进程可以将命令行参数传递给该新程序
实验例程:
1234567891011121314151617#include <stdio.h>int main (int argc, char **argv){ int i = 0; for( ; i<argc; i++) { printf("argv[%d]: %s\n", i, argv[i]); } // ISO C和POSIX1都要求 argv[argc]是一个空指针。这就使我们可以将参数处理循环改写为如下形式,效果是相同的 ...
Linux APUE学习:3、C程序的启动和终止
Linux APUE学习:3、C程序的启动和终止 学习进程前,线应该了解进程环境,比如main函数是怎么被调用的、命令行参数是怎么传递给新程序的、典型的存储空间布局、如何分配另外的存储空间、进程如何使用环境变量、进程的各种不同中止方式。
main函数 C语言总是从main函数开始执行。main函数的原型是
1int main(int argc, char *argv[]);
argc是命令行参数的数目,argv是指向参数的各个指针所构成的数组。
当内核执行c程序时(使用了一个exec函数),在调用main前先调用一个特殊的启动例程(也称为启动代码)。可执行文件将此启动例程指定为程序的起始地址——这是由连接器设置的。
这个启动例程被执行前,可执行文件需要经过连接器的处理,以将各个模块的目标文件链接起来生成可执行文件。在链接过程中,连接器会将启动例程的地址设置为程序的起始地址,这样操作系统就能够通过该地址开始执行程序。
在启动例程中,通常会进行一些初始化工作,例如设置堆栈、初始化全局变量等操作。然后,启动例程会跳转到main函数的入口处,开始执行程序的主 ...
Linux APUE学习:2、网络socket编程
Linux APUE学习:2、网络socket编程代码地址:https://github.com/RoxyKko/APUE/tree/master/ch3
必背图
TCP/IP -> 网络接口层
三大作用:
数据封装/解封成为帧(frame)
控制帧传输
流量控制
Q:什么是数据封装/解封?为什么要进行数据封装/解封成为帧?
A:数据封装是在所发数据包上附加本地以及目标地址、加纠错字节、以及加密处理等。数据解封是数据封装的逆过程,将发送方发过来的信息经过拆解协议包进而获得业务数据的过程。
作用:保证数据安全(防止被监听窃取数据)、可靠(数据不丢失)传输,每一帧除了需要传输的数据,还有发送方的物理地址(寄件人地址)、接受方物理地址(收件人地址)以及检错和控制信息(保证数据的无差错到达)。
Q:什么是控制帧传输?为什么要?
A:接收方通过对帧的差错编码(奇偶校验码或 CRC 码)的检查,来判断帧在传输过程中是否出错,并向发送发进行反馈,如果传输发生差错,则需要重发纠正。对于发送方,发送帧后同时启动定时器, ...
Linux APUE学习:1、文件I/O操作
Linux APUE学习:1、文件I/O操作文件源代码:https://github.com/RoxyKko/APUE.git
文件描述符stdout.c1234567891011121314151617#include <stdio.h>#include <unistd.h>#include <string.h>#define MSG_STR "Hello World\n"int main(int main, char *argv[]){ printf("%s", MSG_STR); // fputs 写入什么 写入到哪 fputs(MSG_STR, stdout); // write 写入(在哪写入, 写入什么, 写入多少) write(STDOUT_FILENO, MSG_STR, strlen(MSG_STR)); return 0;}
文件I/O操作file_io.c123456789101112131415161718192021222324252627 ...
使用VSCode远程Remote SSH链接
使用VSCode远程Remote SSH链接准备工作1、安装Vscodehttps://code.visualstudio.com/
2、安装SSH可以通过安装 Git 来获取 SSH 功能
https://git-scm.com/
安装git后,可在cmd命令窗输入ssh验证
3、Vscode添加插件打开Vscode,Ctrl+Shift+X快捷键打开插件扩展,输入Remote,下载第一个插件
注:vscode默认是没有中文的,想要中文请自己在扩展的搜索框输入Chinese安装中文包
4、生成ssh私钥、公钥先到路径C:\Users \ {用户名}\ .ssh,如图示,若里面有文件id_rsa.pub、id_rsa的话,应是已经存在私钥公钥
若没有则需要生成ssh私钥公钥
cmd命令窗输入,{youremail@example.com}这里面的内容随便填,我是填的自己邮箱
1ss ...
petalinux方式移植linux
petalinux方式移植linux使用Ubuntu 16.04LST
22.04我用成功安装过一次petalinux,之后重装以后不知道为什么一直安装出问题,折磨了我两三天,换用16.04什么问题都没有
vivado2018.3(Windows下) + petalinux 2018.3(Linux下)
petalinux中文手册
petalinux安装x 1234sudo apt-get install tofrodos iproute2 gawk gcc g++ git make net-tools libncurses5-dev \tftpd zlib1g:i386 libssl-dev flex bison libselinux1 gnupg wget diffstat chrpath socat \xterm autoconf libtool tar unzip texinfo zlib1g-dev gcc-multilib build-essential \libsdl1.2-dev libglib2.0-dev screen pax gzip automake -y
...
ZCU102镜像配置和使用
ZCU102镜像配置和使用一、工具下载和准备1、7-zip 解压用工具,下载地址
2、ADI官方Linux镜像 进去后直接点Image file下载即可,下载地址
值得注意的是
3、准备一张16G及以上的SD卡4、SD卡擦除工具 将已经烧录镜像的SD卡或者普通SD卡清空,下载地址
5、SD卡烧录工具 用于将Linux镜像烧录至SD卡,下载地址
6、MobaXterm工具7、CP210x驱动 下载地址
二、制作步骤1、下载好linux镜像2、将SD卡插入读卡器连接到电脑3、用擦除工具清空SD卡4、用烧录工具将镜像烧录至SD卡 注意:镜像文件选下载好的linux镜像文件,无需将下载好的文件解压,其次盘符一定要看好确认是SD卡的盘符,否则会烧录到你自己的硬盘分区上
5、烧录完成后打开SD卡,找到“zynqmp-common”和“zynqmp-zcu102-rev10-adrv9009”两个文件夹,将两个文件夹内所有文件复制粘贴到SD卡的根目录下
“zynqmp-common”下是有一个image文件
“zynqmp-zcu102-rev10-adrv9009 ...
ZCU102+ADRV9009使用GNU Radio开发使用
ZCU102+ADRV9009使用GNU Radio开发使用GNU Radio的安装Linux下的安装以ubuntu系统为例,建议更新至ubuntu 22.04 LTS,22.04的ubuntu才有GNU Radio 3.10.4.0的版本,里面自带有我们需要的ADI公司的PlutoSDR或是FMCOMMS-2/3/4两种GNU块
一、首先下载和编译libiio库:1(sudo) apt install libxml2 libxml2-dev bison flex cmake git libaio-dev libboost-all-dev
二、然后从源代码编译和安装好libiio库:12345678git clone https://github.com/analogdevicesinc/libiio.gitcd libiiomkdir buildcd buildcmake .. -DPYTHON_BINDINGS=ONmake sudo make installcd ../..
三、安装GNU Radio:新版的GNU Radio不再需要从源代码开始编译安装, ...
利用云服务器进行frp
利用云服务器进行frp具体步骤首先在云服务器和要远控的设备都下载这个并解压
123# 根据服务器端和客户端的架构选择,这里我的两端都是x86-64位的,故都可用这一文件,根据不同架构下载不同的服务器端/客户端$ wget https://github.com/fatedier/frp/releases/download/v0.21.0/frp_0.21.0_linux_amd64.tar.gz$ tar -xzvf frp_0.21.0_linux_amd64.tar.gz
公网frps.ini配置
12[common]bind_port = 7000 #frp服务端端口(必须)
客户端frpc.ini配置文件
123456789101112[common]server_addr = xxx.xxx.xxx.xxx #frp服务端地址,必须是公网ip或者域名,这里假设为xxx.xxx.xxx.xxxserver_port = 7000 #frp服务端端口,即填写服务端配置中的 bind_portprotocol = websocket #因为有的校园网为 ...