一、資料結構
首先根據ip資料報格式(圖下圖)定義ip資料報頭的資料結構
然後根據icmp回送請求與應答報文格式定義icmp的資料結構
然後分別定義請求回送的資料長度
請求回送的資料結構
icmp回送應答的資料結構
二、函式實現
(1)sendechorequest
函式功能是傳送回送請求資料報,首先定義三個靜態變數
static echorequest echoreq; // 回送請求資料結構
static nid = 1; // 識別符號
static nseq = 1; // 序號
然後填寫回送請求資訊
echoreq.icmphdr.type = icmp_echoreq; // 型別
echoreq.icmphdr.code = 0; // **
echoreq.icmphdr.checksum = 0; // 校驗和
echoreq.icmphdr.id = nid++; // 識別符號
echoreq.icmphdr.seq = nseq++; // 序號
填寫要傳送的資料
for (i = 0; i < req_datasize; i++)
儲存傳送時間
echoreq.dwtime = gettickcount();
資料存入包中並計算校驗和
echoreq.icmphdr.checksum = in_chsum((u_short*)&echoreq, sizeof(echorequest));
傳送回送請求
nret = sendto(s,
(lpstr)&echoreq,
sizeof(echorequest),
0,(lpsockaddr)lpsttoaddr,
sizeof(sockaddr_in));
(2)recvechoreply
函式功能為接收回送應答資料
dword recvechoreply(socket s, lpsockaddr_in lpsafrom, u_char *pttl)
*pttl = echoreply.iphdr.ttl; // 取得ttl值
return (echoreply.echorequest.dwtime); // 返回所用時間
}(3)waitforechoreply
函式功能:等待套接子s是否有資料可讀
int waitforechoreply(socket s)
(3)in_chsum
函式功能計算校驗和
u_short in_chsum(u_short *addr, int len)
if (nleft == 1)
sum = (sum >> 16) + (sum & 0xffff);
sum += (sum >> 16);
answer = ~sum;
return (answer);
}(4)main函式的實現
第一步:定義winsock資料結構wsadata並新建版本號1.1
第二步:呼叫wsastartup初始化wsadata
第三步:呼叫ping函式
第四步:呼叫wsacleanup釋放winsock
void main(int argc, char **argv)
// 初始化winsock
nret = wsastartup(wversionrequested, &wsadata);
if (nret)
if (wsadata.wversion != wversionrequested)
// 呼叫ping函式
ping(argv[1]);
//ping("www.sina.com");
// 釋放winsock
wsacleanup();
}(5)ping
函式功能:實現ping功能
定義函式用到的資料
socket rawsocket; // 原始套接字
lphostent lphost; // 主機資訊
sockaddr_in sadest; // 目的位址
sockaddr_in sasrc; // 源位址
dword dwtimesent; // 傳送時間
dword dwelapsed; // 延遲時間
然後建立乙個原始套接字
建立乙個原始套介面,協議為icmp協議
rawsocket = socket(af_inet, sock_raw, ipproto_icmp);
根據使用者輸入的目的位址獲取
lphost = gethostbyname(pstrhost);
設定目標套介面位址
sadest.sin_addr.s_addr = *((u_long far*)(lphost->h_addr));
sadest.sin_family = af_inet;
sadest.sin_port = 0;
輸出ping程式的提示資訊
printf("/npinging %s [%s] with %d bytes of data:/n",
pstrhost,
inet_ntoa(sadest.sin_addr),
req_datasize);
傳送icmp回送請求
sendechorequest(rawsocket, &sadest);
使用select()等待接收回送的資料
waitforechoreply(rawsocket);
接收應答
dwtimesent = recvechoreply(rawsocket, &sasrc, &cttl);
計算傳輸時間,並輸出提示資訊
dwelapsed = gettickcount() - dwtimesent;
答應應答資訊
printf("/nreply from: %s: bytes=%d time=%ldms ttl=%d",
inet_ntoa(sasrc.sin_addr),
req_datasize,
dwelapsed,
cttl);
}// 關閉套接字
nret = closesocket(rawsocket);
附:程式源**
Windows下檢視修改Mysql的編碼
windows下程式設計連線mysql時,易出現中文亂碼情況,以下是解決方案 1 檢視mysql編碼 show variables like char 發現字符集編碼都是latin1,下面就有必要修改。2 修改編碼 第一步,一定要先把mysql的服務停掉,我的電腦 管理 服務 mysql 停止 第二...
python 學習之Windows 下的編碼處理!
問題1 1 non ascii character xe9 in file 問題原因 程式編碼上出現問題 解決方法 在程式頭部加上 coding utf 8 設定 編碼為utf8即刻正常執行 問題2 windows 下print 亂碼 錯誤原因 原始碼檔案的編碼格式為utf 8,但是window的本...
Windows下c 字元編碼 一
在談c 之前,不得不先來說說各種字元編碼。我們知道最早的英文本元採用ascii,因為英文本元很少,因此乙個char就夠用了。但是由於處理其他語言的需求,8位的char顯然不夠用,這就要求更多位數的編碼。在中國,我們的國標是gbk,準確的說經歷了gb2312 gbk gb18030的發展過程 我們常說...