实现以太网调试器功能的方法

实现以太网调试器功能的方法

网上有很多串口调试器,用UDP协议实现了一个Windows平台上的以太网调试器,用的是WinSock,也很方便的移植到装有socket的其他平台上。

程序思路实现很简单,初始化创建套接字,绑定,创建一个监听线程,用来接收远方计算机发送来的内容。源程序如下,是一个控制台程序,需要经常改动的地方已标记在注释中:

//发送给对方计算机的IP地址:(经常改动)

#define SENDTO_IP_ADDR "192.168.0.199"

//准备发送的内容:(经常改动)

#define SEND_STRING "lksjadkfjgad123456756544"

#define WIN32_LEAN_AND_MEAN

#include <stdio.h>

#include "windows.h"

#include <winsock2.h>

#include "conio.h"

#pragma comment(lib,"ws2_32.lib") //编译链接包含必要的库

DWORD WINAPI ThreadFunc( LPVOID lpParam ); //接收线程函数

struct sockaddr_in local, from,server;

WSADATA wsaData;

int fromlen;

SOCKET listen_socket;

int retval;

unsigned char Buffer[500]; //接收用缓冲区

DWORD dwThreadId, dwThrdParam = 1;

HANDLE hThread;

void send_buf(char *buf,int len);

int main()

{

char ch;

 

char strBuf[100]=SEND_STRING;

//初始化Winsock

if (WSAStartup(0x202,&wsaData) == SOCKET_ERROR)

{

fprintf(stderr,"WSAStartup failed with error %d/n",WSAGetLastError());

WSACleanup();

return -1;

}

//创建套接字

local.sin_family = AF_INET;

local.sin_addr.s_addr = INADDR_ANY; //监听任何

local.sin_port = htons(1999);

listen_socket = socket(AF_INET, SOCK_DGRAM,0);

 

if (listen_socket == INVALID_SOCKET)

{

fprintf(stderr,"socket() failed with error %d/n",WSAGetLastError());

WSACleanup();

return -1;

}

//欲发送的对方设置

server.sin_family=AF_INET;

server.sin_port=htons(1999);

server.sin_addr.S_un.S_addr=inet_addr(SENDTO_IP_ADDR);

//绑定

if (bind(listen_socket,(struct sockaddr*)&local,sizeof(local))== SOCKET_ERROR)

{

fprintf(stderr,"bind() failed with error %d/n",WSAGetLastError());

WSACleanup();

return -1;

}

fromlen =sizeof(from);

//创建起一个线程,用来接收收到的数据

hThread = CreateThread(

NULL, // no security attributes

0, // use default stack size

ThreadFunc, // thread function

&dwThrdParam, // argument to thread function

0, // use default creation flags 如果该参数为0,线程就会立即开始执行

&dwThreadId); // returns the thread identifier

// Check the return value for success.

if (hThread == NULL)

{

printf("create thread error!/n");

return 0;

}

else

{

CloseHandle( hThread );

}

 

//进入主线程

while (1)

{

if(kbhit())

{

ch=_getch();

if(ch=='q'||ch=='Q'||(int)ch==27) //按‘q’键或“ESC”退出

break;

if(ch==' ') //按空格键发出数据

{

printf("/n已经发送:%s/n",strBuf);

send_buf(strBuf,100);

}

}

}

return 0;

}

//线程函数

DWORD WINAPI ThreadFunc( LPVOID lpParam )

{

while(1)

{

//接收

retval = recvfrom(listen_socket,(char *)Buffer,sizeof(Buffer),0,(struct sockaddr *)&from,&fromlen); // from已经接收了所收到数据方的信息

if (retval == SOCKET_ERROR)

{

fprintf(stderr,"recv() failed: error %d/n",WSAGetLastError());

closesocket(listen_socket);

continue;

}

if (retval == 0)

{

printf("Client closed connection/n");

closesocket(listen_socket);

continue;

}

printf("收到: %d 字节, data [%s] 来自客户方/n",retval,Buffer);

}

}

 

//发送函数封装

void send_buf(char *buf,int len)

{

sendto(listen_socket,buf,len,0,(struct sockaddr *)&server,sizeof(server));

}