欢迎您访问我爱IT技术网,今天小编为你分享的电脑教程是网络协议方面的经验知识教程:协议Jiurl255 技术参考,下面是详细的分享!
协议Jiurl255 技术参考
这是一种很特殊的方法,使用它通讯没有端口,而且由于它的特殊性,也许会带来一些其他的优点。但这种方法也有一个比较大的缺点。它,也许该起个名字,比如叫Jiurl255。它不使用tcp协议,也不使用udp协议,也不使用icmp协议。它使用什么协议,就像乱起的那个名字一样,它使用255协议。
上面这幅图,是一个没有IP选项的IP头。其中有个字段为8位协议,一个字节长,系统就是通过这个字节中的值来区别上层协议是什么,通过这个字节的值来决定应该把数据交给谁来处理。TCP是十进制6,UDP是十进制17。就是说这个值是6的话就交给tcp处理,是17的话就交给udp处理。那么如果这个值是一个没有人处理的值会怎么样呢?比如222,255(8bit,最大255)。我觉得255漂亮些,就拿255说吧,其他没人用的值都是一样的。那么会怎么样呢?我猜测可以收到的,后来做了些小试验,说明我是对的。(我曾夜观天象,发现你有学计算机的命)。这个东西和tcp,udp没什么关系,自然也就不会有tcp,udp的端口号了。
好了,有兴趣的先试一试吧,使用Jiurl255做一次简单通讯的客户端程序下载,服务器端程序下载。
服务器端叫rserver,客户端叫rclient。
rserver 首先 theSocket=socket(AF_INET, SOCK_RAW, 255);建立一个使用Jiurl255的原始套接字,然后绑定本地地址,最后阻塞在recvfrom,等待着发往255协议的数据。收到之后,会将收到数据打印出来。
rclient 首先 获得服务器的IP地址,然后 theSocket=socket(AF_INET, SOCK_RAW, 255);建立一个使用Jiurl255的原始套接字,然后让你从键盘输入些数据 就 sendto 用协议255向服务器端发送输入的数据。
第一个试验,进行一次收发,就可以发现,确实是可以利用没人用的协议号发送和接收数据。大概是这样的,系统收到ip包以后看该协议号有没有进程要接受,如果有的话,就发给那个进程。
第二个试验,运行一个rclient,运行两个rserver,发一次数据。可以发现,两个rserver都收到了rclient发的数据。说明系统会把收到的数据发给每个要接受这个协议号上数据的进程。
另一个试验,server端创建套接字时,指定协议号为200,client端创建套接字,填充ip头时,都指定协议号为255,结果server端就收不到client端发送的数据了。
当时试验后的笔记:"
server端收数据
client端发数据
server端创建套接字时,指定协议号为255,
client端创建套接字,填充ip头时,都指定协议号为255,
结果server端收到了client端发送的数据。
server端创建套接字时,指定协议号为200,
client端创建套接字,填充ip头时,都指定协议号为255,
结果server端就收不到client端发送的数据了。
多个server端,都使用协议号255,
client端也向255协议发数据,
多个server端,都收到了数据。
"
还有就是,如果程序既发又收的,并且是发往本机的,那么程序会收到自己发出的内容。没说清楚好像,比如吧,一个程序,发255的数据之后,就接收255上的数据,他把数据发往本机,那么它就会收到数据。
rclient:
#include rserver:
#include
#include
#include
#include
#include
#pragma comment(lib,"ws2_32.lib")
typedef struct ip_hdr //定义IP首部
{
unsigned char h_verlen; //4位首部长度,4位IP版本号
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地址
}IP_HEADER, *PIP_HEADER;
USHORT CheckSum(USHORT *buffer, int size);
void RawClient( char *szServer );
void main()
{
WSADATA wsaData;
char ServerAddr[256];
printf("Server Addr : ");
scanf("%s",ServerAddr);
printf("
");
WSAStartup(0x0202, &wsaData);
RawClient(ServerAddr);
WSACleanup();
}
/////////////////////////////////////////////////
USHORT CheckSum(USHORT *buffer, int size)
{
unsigned long cksum=0;
while (size > 1)
{
cksum +=*buffer++;
size -=sizeof(USHORT);
}
if (size)
{
cksum +=*(UCHAR*)buffer;
}
cksum=(cksum >> 16) + (cksum & 0xffff);
cksum +=(cksum >>16);
return (USHORT)(~cksum);
}
//////////////////////////////////////////////////////////
void RawClient( char *szServer )
{
LPHOSTENT lpHostEntry;
lpHostEntry=gethostbyname(szServer);
if (lpHostEntry==NULL)
{
printf("gethostbyname() error
");
return;
}
SOCKET theSocket;
theSocket=socket(AF_INET, SOCK_RAW, 255);
if (theSocket==INVALID_SOCKET)
{
printf("socket() error
");
return;
}
int nRet;
BOOL optval;
optval=TRUE;
nRet=setsockopt(theSocket, IPPROTO_IP, IP_HDRINCL, (char*)&optval, sizeof(optval));
if (SOCKET_ERROR==nRet)
{
printf("SetSockOpt Error!%d
", WSAGetLastError());
return;
}
SOCKADDR_IN saServer;
saServer.sin_family=AF_INET;
saServer.sin_addr=*((LPIN_ADDR)*lpHostEntry->h_addr_list); // Let WinSock assign address
saServer.sin_port=0; // Use port passed from user
char szBuf[1024];
//////////////////////////////////////////////////////////////////
memset(szBuf, 0, sizeof(szBuf));
int IpHdrLen=0;
int DataLen=0;
IP_HEADER *pIpHdr=NULL;
char* pData=NULL;
IpHdrLen=sizeof(IP_HEADER);
pIpHdr=(IP_HEADER*)szBuf;
pIpHdr->h_verlen=(4<<4)| (sizeof(IP_HEADER) / sizeof(unsigned long));
pIpHdr->tos=0;
pIpHdr->proto=255;
pIpHdr->ttl=128;
pIpHdr->ident=0;
pIpHdr->checksum=0;
pIpHdr->frag_and_flags=0;
pIpHdr->sourceIP=inet_addr("1.1.1.1");
pIpHdr->destIP=(unsigned int)saServer.sin_addr.s_addr;
pData=(szBuf+IpHdrLen);
printf("Type a String :");
scanf("%s",pData);
DataLen=strlen(pData);
pIpHdr->total_len=IpHdrLen+DataLen;
//////////////////////////////////////////////////////////////////
nRet=sendto(theSocket, // Socket
szBuf, // Data buffer
IpHdrLen+DataLen, // Length of data
0, // Flags
(LPSOCKADDR)&saServer, // Server address
sizeof(struct sockaddr)); // Length of address
if(nRet!=SOCKET_ERROR)
{
printf("Client send: %s
",pData);
}
getch();
closesocket(theSocket);
return;
}
#include
#include
#include
#include
#pragma comment(lib,"ws2_32.lib")
void RawServer();
void main()
{
WSADATA wsaData;
WSAStartup(0x0202, &wsaData);
RawServer();
WSACleanup();
}
//////////////////////////////////////////////////////////
void RawServer()
{
int nRet;
SOCKET theSocket;
theSocket=socket(AF_INET, SOCK_RAW, 255);
if (theSocket==INVALID_SOCKET)
{
printf("socket() error
");
return;
}
SOCKADDR_IN saServer;
saServer.sin_family=AF_INET;
saServer.sin_addr.s_addr=INADDR_ANY; // Let WinSock assign address
saServer.sin_port=0; // Use port passed from user
nRet=bind(theSocket, // Socket descriptor
(LPSOCKADDR)&saServer, // Address to bind to
sizeof(struct sockaddr) // Size of address
);
if (nRet==SOCKET_ERROR)
{
printf("bind() error
");
closesocket(theSocket);
return;
}
///////////////////////////////////////////////////
int nLen;
nLen=sizeof(SOCKADDR);
char szBuf[1024];
nRet=gethostname(szBuf, sizeof(szBuf));
if (nRet==SOCKET_ERROR)
{
printf("gethostname() error
");
closesocket(theSocket);
return;
}
LPHOSTENT lpHostEntry;
lpHostEntry=gethostbyname(szBuf);
printf("Server named %s addr %s
",
szBuf, inet_ntoa(*(LPIN_ADDR)lpHostEntry->h_addr));
///////////////////////////////////////////////////
SOCKADDR_IN saClient;
以上就是关于协议Jiurl255 技术参考的网络协议知识分享,更多电脑教程请移步到>>电脑教程。
- 评论列表(网友评论仅供网友表达个人看法,并不表明本站同意其观点或证实其描述)
-
