14.5.27以来。谷歌又打不开了。
从网上找了些国内的googleserverIP,例如以下:
const char* g_google_ips[18] = { "203.208.48.151", "203.208.46.176", "203.208.46.147", "203.208.46.212", "203.208.46.158", "203.208.46.180", "203.208.46.198", "203.208.41.150", "203.208.41.151", "203.208.41.135", "203.208.41.142", "203.116.165.221", "203.116.165.224", "203.116.165.235", "203.116.165.207", "203.116.165.223", "203.116.165.231", "203.116.165.160", };
但每次手动选择一个IP来打开的话,还不知道他速度好不好,所以我做了这么个小程序analyse.exe:
依次ping每一个IP,计算其响应时间,选取最快的一个,写入一个bat文件。内容为:
sprintf(cmd, "start explorer http://%s", g_google_ips[fastest_ndx]);
使用exporer会用ie来打开谷歌站点。
explorer能够替换为自己的浏览器路径或名称,如chrome。
直接执行这个批处理文件就可以打开google站点。下次感觉这个IP变卡了,能够再次执行一下analyse.exe。完整源码例如以下:
typedef struct icmp_hdr { unsigned char icmp_type; // 消息类型 unsigned char icmp_code; // 代码 unsigned short icmp_checksum; // 校验和 // 以下是回显头 unsigned short icmp_id; // 用来惟一标识此请求的ID号,通常设置为进程ID unsigned short icmp_sequence; // 序列号 unsigned long icmp_timestamp; // 时间戳 } ICMP_HDR, *PICMP_HDR; const char* g_google_ips[18] = { "203.208.48.151", "203.208.46.176", "203.208.46.147", "203.208.46.212", "203.208.46.158", "203.208.46.180", "203.208.46.198", "203.208.41.150", "203.208.41.151", "203.208.41.135", "203.208.41.142", "203.116.165.221", "203.116.165.224", "203.116.165.235", "203.116.165.207", "203.116.165.223", "203.116.165.231", "203.116.165.160", }; USHORT checksum(USHORT* buff, int size) { unsigned long cksum = 0; while(size>1) { cksum += *buff++; size -= sizeof(USHORT); } // 是奇数 if(size) { cksum += *(UCHAR*)buff; } // 将32位的chsum高16位和低16位相加。然后取反 cksum = (cksum >> 16) + (cksum & 0xffff); cksum += (cksum >> 16); return (USHORT)(~cksum); } BOOL SetTimeout(SOCKET s, int nTime, BOOL bRecv) { int ret = ::setsockopt(s, SOL_SOCKET, bRecv ? SO_RCVTIMEO : SO_SNDTIMEO, (char*)&nTime, sizeof(nTime)); return ret != SOCKET_ERROR; } int ping(const char* dst_ip) { SOCKET sRaw = ::socket(AF_INET, SOCK_RAW, IPPROTO_ICMP); SetTimeout(sRaw, 1000, TRUE); SOCKADDR_IN dest; dest.sin_family = AF_INET; dest.sin_port = htons(0); dest.sin_addr.S_un.S_addr = inet_addr(dst_ip); // 创建ICMP封包 char buff[sizeof(ICMP_HDR) + 32]; ICMP_HDR* pIcmp = (ICMP_HDR*)buff; pIcmp->icmp_type = 8; // 请求一个ICMP回显 pIcmp->icmp_code = 0; pIcmp->icmp_id = (USHORT)::GetCurrentProcessId(); pIcmp->icmp_checksum = 0; pIcmp->icmp_sequence = 0; memset(&buff[sizeof(ICMP_HDR)], 'E', 32); USHORT nSeq = 0; char recvBuf[1024]; SOCKADDR_IN from; int nLen = sizeof(from); int avr_time = 0; int nCount = 0; while(TRUE) { int nRet; if(nCount++ == 4) break; pIcmp->icmp_checksum = 0; pIcmp->icmp_timestamp = ::GetTickCount(); pIcmp->icmp_sequence = nSeq++; pIcmp->icmp_checksum = checksum((USHORT*)buff, sizeof(ICMP_HDR) + 32); nRet = ::sendto(sRaw, buff, sizeof(ICMP_HDR) + 32, 0, (SOCKADDR *)&dest, sizeof(dest)); if(nRet == SOCKET_ERROR) { printf(" sendto() failed: %d ", ::WSAGetLastError()); return -1; } nRet = ::recvfrom(sRaw, recvBuf, 1024, 0, (sockaddr*)&from, &nLen); if(nRet == SOCKET_ERROR) { if(::WSAGetLastError() == WSAETIMEDOUT) { printf(" timed out "); continue; } printf(" recvfrom() failed: %d ", ::WSAGetLastError()); return -1; } int nTick = ::GetTickCount(); if(nRet < sizeof(IPHeader) + sizeof(ICMP_HDR)) { printf(" Too few bytes from %s ", ::inet_ntoa(from.sin_addr)); } ICMP_HDR* pRecvIcmp = (ICMP_HDR*)(recvBuf + 20); // (ICMP_HDR*)(recvBuf + sizeof(IPHeader)); if(pRecvIcmp->icmp_type != 0) // 回显 { printf(" nonecho type %d recvd ", pRecvIcmp->icmp_type); return -1; } if(pRecvIcmp->icmp_id != ::GetCurrentProcessId()) { printf(" someone else's packet! "); return -1; } printf(" %d bytes from %s:", nRet, inet_ntoa(from.sin_addr)); printf(" icmp_seq = %d. ", pRecvIcmp->icmp_sequence); printf(" time: %d ms", nTick - pRecvIcmp->icmp_timestamp); avr_time += nTick - pRecvIcmp->icmp_timestamp; printf(" "); ::Sleep(1000); } ::closesocket(sRaw); avr_time /= 4; return avr_time; }<pre code_snippet_id="385396" snippet_file_name="blog_20140610_3_201928" name="code" class="cpp">
int main() { static const int MAX_NUM = 18; int ret_times[MAX_NUM] = {0}; int min_ret = 1000; int fastest_ndx = 0; printf("start analyze the speed of google's ips. "); for(int i = 0; i < MAX_NUM; i++) { printf("ping %s ", g_google_ips[i]); ret_times[i] = ping(g_google_ips[i]); if(ret_times[i] != -1 && min_ret > ret_times[i]) { min_ret = ret_times[i]; fastest_ndx = i; } printf("average time from %s is %d ms. ", g_google_ips[i], ret_times[i]); } printf("analyze over, fastest google ip is %s, average time %d ms. ", g_google_ips[fastest_ndx], min_ret); const char* file_name = "google.bat"; char cmd[1024] = {0}; sprintf(cmd, "start explorer http://%s", g_google_ips[fastest_ndx]); ::DeleteFile(file_name); FILE* file = NULL; file = fopen(file_name, "wb"); if(file) { fwrite(cmd, 1, strlen(cmd), file); fclose(file); printf("now you can run google.bat to open the fastest www.google.com! "); } return 0; }