哈哈,五个三角了!问个问题,散点分!

LiChenYue 2007-03-12 01:25:17
#include <stdio.h>
#include <winsock2.h>
#include <ws2tcpip.h>

#pragma comment (lib,"ws2_32.lib")

#define SIO_RCVALL _WSAIOW(IOC_VENDOR,1)

struct IPHEAD
{
unsigned char h_len:4;//4位首部长度+4位IP版本号
unsigned char ver:4;
unsigned char tos;//8位服务类型TOS
unsigned short total_len;//16位总长度(字节)
unsigned short ident;//16位标识
unsigned short frag_and_flags;//3位标志位
unsigned char ttl;//8位生存时间 TTL
unsigned char proto;//8位协议 (TCP, UDP 或其他)
unsigned short checksum;//16位IP首部校验和
unsigned int sourceip;//32位源IP地址
unsigned int destip;//32位目的IP地址
};

struct TCPHEAD //定义TCP首部
{
USHORT th_sport; //16位源端口
USHORT th_dport; //16位目的端口
unsigned int th_seq; //32位序列号
unsigned int th_ack; //32位确认号
unsigned char th_lenres; //4位首部长度/6位保留字
unsigned char th_flag; //6位标志位
USHORT th_win; //16位窗口大小
USHORT th_sum; //16位校验和
USHORT th_urp; //16位紧急数据偏移量
};


char *phostlist[10];//列举主机网卡的数组

DWORD _stdcall listen(void *p)
{
SOCKET s;
struct sockaddr_in addr;
int itimeout=1000;
int ret;
char cbuf[1500];//接收数据缓冲区
struct IPHEAD *piphd;//定义IP头结构
struct TCPHEAD *ptcphd;//定义TCP头结构

s=socket(AF_INET,SOCK_RAW,IPPROTO_RAW); //创建一个原始套接字
setsockopt(s,SOL_SOCKET,SO_RCVTIMEO,(char*)&itimeout,sizeof(itimeout));

memset(&addr,0,sizeof(addr));
addr.sin_family=AF_INET;
addr.sin_addr.S_un.S_addr=inet_addr((char *)p);
addr.sin_port=htons(6000);//设置本地端口号
bind(s,(struct sockaddr *)&addr,sizeof(addr));//绑定端口
//设置sock_raw为sio_rcvall,以便接收所有IP包
DWORD dwin=1;
DWORD dwout[10];
DWORD dwret;
WSAIoctl(s,SIO_RCVALL,&dwin,sizeof(dwin),&dwout,sizeof(dwout),&dwret,NULL,NULL);

for(;;)
{
ret=recv(s,cbuf,sizeof(cbuf),0);//接收数据
if(ret==SOCKET_ERROR)
{
if(WSAGetLastError()==WSAETIMEDOUT)continue;/*这里,这里*/
closesocket(s);
return 0;
}

piphd=(struct IPHEAD *)cbuf;//取得IP头数据的地址
int iIphLen = sizeof(unsigned long) * (piphd->h_len & 0xf);
ptcphd=(struct TCPHEAD *)(cbuf+iIphLen);//取得TCP头数据的地址

printf("From : %s \t port %d\t",inet_ntoa(*(struct in_addr*)&piphd->sourceip),ntohs(ptcphd->th_sport) );
printf("To : %s \t port %d ",inet_ntoa(*(struct in_addr*)&piphd->destip),ntohs(ptcphd->th_dport));

switch(piphd->proto)//根据IP头的协议判断数据包协议类型
{
case 1:
printf("ICMP\n");
break;
case 2:
printf("IGMP\n");
break;
case 6:
printf("TCP\n");
break;
case 17:
printf("UDP\n");
break;
default:
printf("unknow:%d\n",piphd->proto);
}
}

return 1;
}

void main()
{
//初始化sock
WSADATA wsa;
int i=0;
DWORD dwtid;
char chname[128];
hostent *host;

WSAStartup(MAKEWORD(2,1),&wsa);
gethostname(chname,sizeof(chname));
host=gethostbyname(chname);
while(host->h_addr_list[i]!=NULL)//取所有网卡序号,为每个网卡开启一个监听线程
{
phostlist[i]=(char *)malloc(16);
sprintf(phostlist[i],"%s",inet_ntoa(*(struct in_addr *)host->h_addr_list[i]));
printf("Bind to %s\n",phostlist[i]);
CreateThread(NULL,0,listen,phostlist[i],0,&dwtid);
i++;
}

for(;;)//为每个网卡创建监听线程后要用一个循环防止主线程退出
{
Sleep(10);
}
}

第六十九行,就是标/*这里,这里*/的地方,总是continue.是怎么回事?

...全文
912 52 打赏 收藏 转发到动态 举报
写回复
用AI写文章
52 条回复
切换为时间正序
请发表友善的回复…
发表回复
Stefine 2007-03-21
  • 打赏
  • 举报
回复
呵,你当然得先开server在那listen,然后client再connect,然后就互相send recv了咯

这些东东与你程序写成哪样是直接相关的
逸学堂 2007-03-21
  • 打赏
  • 举报
回复
纯jf
littlegang 2007-03-21
  • 打赏
  • 举报
回复
lz给的第二个例子中,服务端收到连接后马上就关闭了啊?
那你让客户端怎么连接啊,当然连不上了
LiChenYue 2007-03-19
  • 打赏
  • 举报
回复
他害我!:
DrawText
大家别误会!
konj 2007-03-19
  • 打赏
  • 举报
回复
解放
anjuta_c 2007-03-19
  • 打赏
  • 举报
回复
你的名字很恶心啊,呵呵
DrawText 2007-03-19
  • 打赏
  • 举报
回复
anjuta_c(天天学习不退步)
下面程序调试又通过了,搞了我很长时间,大家帮我看一下,是为什么呀?
#pragma comment(lib,"ws2_32.lib")
#include <winsock2.h>
#include <stdio.h>

void main(int argc, char **argv)
{
WSADATA wsaData;
SOCKET s;
SOCKADDR_IN ServerAddr;
int Port = 5150;
int Ret;

if (argc <= 1)
{
printf("USAGE: tcpclient <Server IP address>.\n");
return;
}

// Initialize Winsock version 2.2

if ((Ret = WSAStartup(MAKEWORD(2,2), &wsaData)) != 0)
{
// NOTE: Since Winsock failed to load we cannot use WSAGetLastError
// to determine the error code as is normally done when a Winsock
// API fails. We have to report the return status of the function.

printf("WSAStartup failed with error %d\n", Ret);
return;
}

// Create a new socket to make a client connection.

if ((s = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP))
== INVALID_SOCKET)
{
printf("socket failed with error %d\n", WSAGetLastError());
WSACleanup();
return;
}

// Setup a SOCKADDR_IN structure that will be used to connect
// to a listening server on port 5150. For demonstration
// purposes, we required the user to supply an IP address
// on the command line and we filled this field in with the
// data from the user.

ServerAddr.sin_family = AF_INET;
ServerAddr.sin_port = htons(Port);
ServerAddr.sin_addr.s_addr = inet_addr(argv[1]);

// Make a connection to the server with socket s.

printf("We are trying to connect to %s:%d...\n",
inet_ntoa(ServerAddr.sin_addr), htons(ServerAddr.sin_port));

if (connect(s, (SOCKADDR *) &ServerAddr, sizeof(ServerAddr))
== SOCKET_ERROR)
{
printf("connect failed with error %d\n", WSAGetLastError());
closesocket(s);
WSACleanup();
return;
}

printf("Our connection succeeded.\n");

// At this point you can start sending or receiving data on
// the socket s. We will just send a hello message to the server.

printf("We will now try to send a hello message.\n");

if ((Ret = send(s, "Hello", 5, 0)) == SOCKET_ERROR)
{
printf("send failed with error %d\n", WSAGetLastError());
closesocket(s);
WSACleanup();
return;
}

printf("We successfully sent %d byte(s).\n", Ret);

// When you are finished sending and receiving data on socket s,
// you should close the socket.

printf("We are closing the connection.\n");

closesocket(s);

// When your application is finished handling the connection, call
// WSACleanup.

WSACleanup();
}
---------------------------------------------------------------------------------
---------------------------------------------------------------------------------

#pragma comment(lib,"ws2_32.lib")
#include <winsock2.h>
#include <stdio.h>

void main(void)
{
WSADATA wsaData;
SOCKET ListeningSocket;
SOCKET NewConnection;
SOCKADDR_IN ServerAddr;
SOCKADDR_IN ClientAddr;
int ClientAddrLen;
int Port = 5150;
int Ret;
char DataBuffer[1024];

// Initialize Winsock version 2.2

if ((Ret = WSAStartup(MAKEWORD(2,2), &wsaData)) != 0)
{
// NOTE: Since Winsock failed to load we cannot use WSAGetLastError
// to determine the error code as is normally done when a Winsock
// API fails. We have to report the return status of the function.

printf("WSAStartup failed with error %d\n", Ret);
return;
}

// Create a new socket to listening for client connections.

if ((ListeningSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP))
== INVALID_SOCKET)
{
printf("socket failed with error %d\n", WSAGetLastError());
WSACleanup();
return;
}

// Setup a SOCKADDR_IN structure that will tell bind that we
// want to listen for connections on all interfaces using port
// 5150. Notice how we convert the Port variable from host byte
// order to network byte order.

ServerAddr.sin_family = AF_INET;
ServerAddr.sin_port = htons(Port);
ServerAddr.sin_addr.s_addr = htonl(INADDR_ANY);

// Associate the address information with the socket using bind.

if (bind(ListeningSocket, (SOCKADDR *)&ServerAddr, sizeof(ServerAddr))
== SOCKET_ERROR)
{
printf("bind failed with error %d\n", WSAGetLastError());
closesocket(ListeningSocket);
WSACleanup();
return;
}

// Listen for client connections. We used a backlog of 5 which is
// normal for many applications.

if (listen(ListeningSocket, 5) == SOCKET_ERROR)
{
printf("listen failed with error %d\n", WSAGetLastError());
closesocket(ListeningSocket);
WSACleanup();
return;
}

printf("We are awaiting a connection on port %d.\n", Port);

// Accept a new connection when one arrives.
ClientAddrLen=sizeof(ClientAddr);
if ((NewConnection = accept(ListeningSocket, (SOCKADDR *) &ClientAddr,
&ClientAddrLen)) == INVALID_SOCKET)
{
printf("accept failed with error %d\n", WSAGetLastError());
closesocket(ListeningSocket);
WSACleanup();
return;
}


printf("We successfully got a connection from %s:%d.\n",
inet_ntoa(ClientAddr.sin_addr), ntohs(ClientAddr.sin_port));

// At this point you can do two things with these sockets. Await
// for more connections by calling accept again on ListeningSocket
// and start sending or receiving data on NewConnection. For
// simplicity We will stop listening for more connections by closing
// ListeningSocket. We will start sending and receiving data on
// NewConnection.

closesocket(ListeningSocket);

// Start sending and receiving data on NewConnection. For simplicity,
// we will just receive some data and report how many bytes were
// received.

printf("We are waiting to receive data...\n");

if ((Ret = recv(NewConnection, DataBuffer, sizeof(DataBuffer), 0))
== SOCKET_ERROR)
{
printf("recv failed with error %d\n", WSAGetLastError());
closesocket(NewConnection);
WSACleanup();
return;
}

printf("We successfully received %d byte(s).\n", Ret);

// For this application we do not plan to do anything else with the
// connection so we will just close the connection.

printf("We are now going to close the client connection.\n");

closesocket(NewConnection);

// When your application is finished handling the connections
// call WSACleanup.

WSACleanup();
}
一个服务端,一个客户,两个一先一后运行才行,这样可以,为什么上面的不行呢?
是差什么吗?
argenCHN 2007-03-15
  • 打赏
  • 举报
回复
jf 不会
pomelowu 2007-03-14
  • 打赏
  • 举报
回复
我是说保持连接的方法。不过正如 corrupt 说的,用recvfrom吧
zaza_bbface 2007-03-14
  • 打赏
  • 举报
回复
楼主昵称有点意思
LiChenYue 2007-03-14
  • 打赏
  • 举报
回复
比如说:
#pragma comment(lib,"ws2_32.lib")
#include <winsock2.h>
#include <stdio.h>

int main(void) {

//----------------------
// Initialize Winsock.
WSADATA wsaData;
int iResult = WSAStartup(MAKEWORD(2,2), &wsaData);
if (iResult != NO_ERROR) {
printf("Error at WSAStartup()\n");
return 1;
}

//----------------------
// Create a SOCKET for listening for
// incoming connection requests.
SOCKET ListenSocket;
ListenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (ListenSocket == INVALID_SOCKET) {
printf("Error at socket(): %ld\n", WSAGetLastError());
WSACleanup();
return 1;
}

//----------------------
// The sockaddr_in structure specifies the address family,
// IP address, and port for the socket that is being bound.
sockaddr_in service;
service.sin_family = AF_INET;
service.sin_addr.s_addr = inet_addr("127.0.0.1");
service.sin_port = htons(27015);

if (bind( ListenSocket,
(SOCKADDR*) &service,
sizeof(service)) == SOCKET_ERROR) {
printf("bind() failed.\n");
closesocket(ListenSocket);
WSACleanup();
return 1;
}

//----------------------
// Listen for incoming connection requests.
// on the created socket
if (listen( ListenSocket, 1 ) == SOCKET_ERROR) {
printf("Error listening on socket.\n");
closesocket(ListenSocket);
WSACleanup();
return 1;
}

//----------------------
// Create a SOCKET for accepting incoming requests.
SOCKET AcceptSocket;
printf("Waiting for client to connect...\n");

//----------------------
// Accept the connection.
AcceptSocket = accept( ListenSocket, NULL, NULL );
if (AcceptSocket == INVALID_SOCKET) {
printf("accept failed: %d\n", WSAGetLastError());
closesocket(ListenSocket);
WSACleanup();
return 1;
} else
printf("Client connected.\n");

// No longer need server socket
closesocket(ListenSocket);

WSACleanup();
return 0;
}

这个就也不能正常运行!
包括WINPCAP的例子!
什么原因呀?
有人说是accept()函数的第三个参数要初始化为sizeof(SOCKADDR),我按这样办也不行!
不是得到错误10061jiu shi de dao cuo wu 10014,
jing ran da bu chu han zi le shi wo de xi tong huai le ma ?
睡在床板下_ 2007-03-14
  • 打赏
  • 举报
回复
原始 套接字 是没有端口的, 所以不需要 recv ,用recvfrom
Red_angelX 2007-03-14
  • 打赏
  • 举报
回复
接分
LiChenYue 2007-03-14
  • 打赏
  • 举报
回复
几个例子编译不过
anjuta_c 2007-03-14
  • 打赏
  • 举报
回复
太有关系了,你看看msdn吧,很多api特别是高级点的api是不能在98上运行的;另外使用那个库以前看看这些库的readme文件,需要在什么平台下运行;

另外 基于win98落后操作系统体系结构,有太多的功能它都不支持,呵呵
LiChenYue 2007-03-14
  • 打赏
  • 举报
回复
始终不能接受数据,这和我用WIN98的老机器有关吗?
dovelee 2007-03-14
  • 打赏
  • 举报
回复
mark
hurryboylqs 2007-03-14
  • 打赏
  • 举报
回复
关注,接分
cheneyhehe 2007-03-14
  • 打赏
  • 举报
回复
关注
lshadow 2007-03-14
  • 打赏
  • 举报
回复
先接分再看问题
加载更多回复(32)

18,356

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC 网络编程
c++c语言开发语言 技术论坛(原bbs)
社区管理员
  • 网络编程
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧