【设计实例】基于SoC FPGA的Linux UDP图像发送。
如果您还没有注册本论坛,将无法下载论坛中附件,但是注册论坛非常简单,使用微 信 扫码即可注册。
也可以在小梅哥任意一个Q群内直接索取邀请码使用邀请码注册,小梅哥创建的任意一个群都可以。
以下代码为基本的Linux 使用UDP发送两个文件的图像数据到远端(192.168.0.106:6000)的程序,使用时,在DS-5或GCC下交叉编译得到可执行文件,然后拷贝到SoC 开发板中,同时,需要把附件的两bin格式图像二进制文件也拷贝到程序所在目录,然后执行,开发板就能不断的发送这两幅图像的数据到远端了。
需要注意的是,为了保证发送成功:
开发板的IP也需要设置为192.168.0.网段,比如设置为192.168.0.2
电脑的IP地址需要设置为192.168.0.168
图像接收软件的几个参数要与实际网络参数匹配(图像软件见下述附件)
如果图像软件运行失败,提示找不到mfcxxx.dll,请安装运行环境,百度下载 vcredist_x86安装就可以了
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/mman.h>
#include <sys/types.h>
#include <dirent.h>
#include <inttypes.h>
#include <sys/time.h>
#include <stdbool.h>
#include <pthread.h>
#include <sys/ioctl.h>
#include "math.h"
#include <string.h>
#include <linux/fb.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netdb.h>
#include <signal.h>
char* ReadBmpFile(const char* szFile)
{
FILE* fTmp = fopen(szFile, "rb");
if (fTmp == NULL) return NULL;
fseek(fTmp, 0, SEEK_END);
int nLen = ftell(fTmp);
if (nLen <= 0)
{
fclose(fTmp);
return NULL;
}
char* szContent = (char*)malloc(nLen + 1);
memset(szContent, 0, nLen + 1);
fseek(fTmp, 0, SEEK_SET);
char szTmp = { 0 };
int nHaveRead = 0;
while (!feof(fTmp))
{
int nRead = fread(szTmp, 1, 1024, fTmp);
if (nRead <= 0) break;
memcpy(szContent + nHaveRead, szTmp, nRead);
nHaveRead += nRead;
}
fclose(fTmp);
return szContent;
}
unsigned char STOP = 0;
void signalFunc(int _signal)
{
STOP = 1;
}
int main(int argc, char ** argv) {
signal(SIGINT, signalFunc);
signal(SIGTERM, signalFunc);
int nX = 640;
int nY = 480;
char* szBmp1 = ReadBmpFile("640_480_01.bin");
if (NULL == szBmp1)
{
printf("read bmp file 1 error!");
return 0;
}
char* szBmp2 = ReadBmpFile("640_480_02.bin");
if (NULL == szBmp2)
{
printf("read bmp file 2 error!");
return 0;
}
int retval;
char buf;
int socket_descriptor; //套接口描述字
struct sockaddr_in address;//处理网络通信的地址
int port=6000;
bzero(&address,sizeof(address));
address.sin_family=AF_INET;
address.sin_addr.s_addr=inet_addr("192.168.0.106");//这里不一样
address.sin_port=htons(port);
unsigned char *p;
//创建一个 UDP socket
socket_descriptor=socket(AF_INET,SOCK_DGRAM,0);//IPV4SOCK_DGRAM 数据报套接字(UDP协议)
int rbufsz = 5 * 1024 * 1024; //5M
setsockopt(socket_descriptor, SOL_SOCKET, SO_RCVBUF, &rbufsz, sizeof(rbufsz));
int wbufsz = 5 * 1024 * 1024; //5M
setsockopt(socket_descriptor, SOL_SOCKET, SO_SNDBUF, &wbufsz, sizeof(wbufsz));
int maxfdp;
fd_set fds;
fd_set fdsErr;
struct timeval timeout = {1, 0};//设置select等待3秒,3秒轮询,非阻塞就置0
int nSendFile = 0;
long iter = 0;
connect(socket_descriptor, (struct sockaddr *)&address,sizeof(address));
while (!STOP)
{
FD_ZERO(&fds);//每次循环都要清空集合,否则不能检测描述符变化
FD_SET(socket_descriptor, &fds);//添加描述符
//FD_ZERO(&fdsErr);//每次循环都要清空集合,否则不能检测描述符变化
//FD_SET(socket_descriptor, &fdsErr);//添加描述符
maxfdp = socket_descriptor + 1;//描述符最大值加1
// printf("1\n");
retval = select(maxfdp, NULL, &fds, NULL, &timeout);
if (retval <= 0)
{
//usleep(1000);
continue;
}
p = (unsigned char *)((nSendFile == 0) ? szBmp1 : szBmp2);
buf=iter >> 8;
buf=iter & 0xff;
//memcpy(&buf,p,1280);
memcpy(&buf, p + iter * 1280, 1280);
if(FD_ISSET(socket_descriptor,&fds))//测试skt是否可写,即网络上是否有数据
{
retval = write(socket_descriptor, buf, 1282);
if(retval < 0){
perror("sendto error: ");
exit(1);
}
}
iter++;
if (iter > nY - 1)
{
iter = 0;
nSendFile = (nSendFile + 1) % 2;
//usleep(1000);
}
}
free(szBmp1);
free(szBmp2);
printf("app exit\n");
}
请问小梅哥有完整的工程吗,我不知道怎么在qsys中配置以太网,能发一份原工程吗
页:
[1]