for( i = 0; i < 4; i ++ ) * ( IP + i ) = -1; i = j = k = 0; for( ; k < 3; k ++ ) { i = str.Find( '.', j ); if( i == -1 ) break; ipstr = str.Mid( j, i - j );
for( l = 0; l < i - j; l ++ ) if ( ipstr[l] < '0' || ipstr[l] > '9' ) return -1;
* ( IP + k ) = atoi((const char*)(LPCTSTR)ipstr); j = i + 1; } for( i = 0; i < 3; i ++ ) if( * ( IP + i ) == -1 ) return -1; * ( IP + 3 ) = 5; ipfp = fopen("qqwry.dat", "rb"); if( ipfp == NULL ) return -1; char pbuf[256] = {0}; fseek(ipfp, 0, SEEK_SET); unsigned int indexHeadPos = 0; unsigned int indexTailPos = 0; struct INDEXITEM target; target.ip[0] = IP[3]; target.ip[1] = IP[2]; target.ip[2] = IP[1]; target.ip[3] = IP[0]; fread(&indexHeadPos, sizeof(indexHeadPos), 1, ipfp); fread(&indexTailPos, sizeof(indexTailPos), 1, ipfp); int amount = (indexTailPos - indexHeadPos)/sizeof(struct INDEXITEM); struct INDEXITEM start = LookForIndexItem(&target, ipfp, indexHeadPos, amount); char result[255] = {0}; RetrieveContent(&start, target.ip, ipfp, result); str = result; fclose(ipfp); return 0; }struct INDEXITEM CConnectSocket::LookForIndexItem(struct INDEXITEM* const pAimItem, FILE* pFile, unsigned int indexBasePos, unsigned int indexAmount ) { struct INDEXITEM tmp; int i = 0; int j = indexAmount; int s = (int)sizeof(struct INDEXITEM); while ( i < j - 1 ) { int k = (int) (i+j)/2; int offset = (int)( k * s ); fseek(pFile, indexBasePos+offset, SEEK_SET); fread(&tmp, s, 1, pFile); int c = Compare( tmp.ip, pAimItem->ip ); if ( c > 0 ) j = k; else if ( c < 0 ) i = k; else { i = k; j = k; } } fseek(pFile, indexBasePos+i*s, SEEK_SET); fread(&tmp, s, 1, pFile); return tmp; }int CConnectSocket::Compare(unsigned char pA[4], unsigned char pB[4]) { unsigned int a = BYTE4INT(pA); unsigned int b = BYTE4INT(pB); if ( a > b ) return 1; else if ( a < b ) return -1; else return 0; }void CConnectSocket::GetData(unsigned char* str, FILE* pFile, int max) { int i = 0; while ( (*(str+i)=fgetc(pFile)) && (i<(max-2)) ) i++; str[i] = 0; }void CConnectSocket::RetrieveContent(struct INDEXITEM* const pIndexItem, unsigned char ip[4], FILE* pFile, char* content ) { // to get the pos from the offset array long tmp = 0; unsigned char buf[80]; int pos = BYTE3INT(pIndexItem->offset); fseek(pFile, pos, SEEK_SET); fread(buf, 4, 1, pFile); if ( Compare(ip, buf) > 0 ) { strcat(content, "未知"); //printf("未知数据\n"); return; } // 获取资料 fread(buf, 1, 1, pFile); if ( buf[0] == 0x01 ) { // 国家地区均重复, 跳转至新地址 fread(buf, 3, 1, pFile); pos = BYTE3INT(buf); fseek(pFile, pos, SEEK_SET); fread(buf, 1, 1, pFile); } // 获取国家 if ( buf[0] == 0x02 ) { // 获取国家偏移 fread(buf, 3, 1, pFile); // 保存地区信息 tmp = ftell(pFile); pos = BYTE3INT(buf); fseek(pFile, pos, SEEK_SET); fread(buf, 1, 1, pFile); } if ( buf[0] == 0x01 || buf[0] == 0x02 ) { strcat(content, "未知"); //printf("There is something wrong....\n"); return; } if ( buf[0] ) GetData(buf+1, pFile, 40); strcat(content, (char*)buf); //printf("%s\t", buf); // 获取地区 if ( tmp ) fseek(pFile, tmp, SEEK_SET); fread(buf, 1, 1, pFile); while ( buf[0] == 0x02 ) { // 获取地区偏移 fread(buf, 3, 1, pFile); pos = BYTE3INT(buf); fseek(pFile, pos, SEEK_SET); fread(buf, 1, 1, pFile); } if ( buf[0] == 0x01 || buf[0] == 0x02 ) { strcat(content, "未知"); //printf("There is something wrong....\n"); return; } if ( buf[0] ) GetData(buf+1, pFile, 40); // strcat(content," "); strcat(content, (char*)buf); return; }
struct WryFileHEAD
{
BYTE Reserved1[4];
UINT TotalNum; // 记录总数
WORD BeginPos; // 记录数据开始的偏移量
WORD RecordSize; // 每条记录的大小
BYTE Reserved2[20]; char StartIp[16];
WORD StartIpSize;
BYTE Reserved3[14]; char EndIp[16];
WORD EndIpSize;
BYTE Reserved4[14]; char Country[16];
WORD CountrySize;
BYTE Reserved5[14]; char Local[16];
WORD LocalSize;
BYTE Reserved6[14]; char Thank[16];
WORD ThankSize;
BYTE Reserved7[14];
};剩下的你自己去分析吧
| ( ( X[1] & 0x000000FF ) << 8 ) \
| ( ( X[2] & 0x000000FF ) << 16 ) )#define BYTE4INT(X) ( ( X[0] & 0x000000FF ) \
| ( ( X[1] & 0x000000FF ) << 8 ) \
| ( ( X[2] & 0x000000FF ) << 16 ) \
| ( ( X[3] & 0x000000FF ) << 24 ) )struct INDEXITEM
{
unsigned char ip[4];
unsigned char offset[3];
};int LocalityFromIP2(CString& str)
{
//str 是类似 *.*.*.* 的数据,返回的具体地址仍在 str 中。两端没有空格。 int i = 0, j = str.GetLength(), k = 0, l, IP[4];
const char* p = (LPCTSTR)str;
FILE* ipfp = NULL;
CString ipstr;
for( i = 0; i < 4; i ++ )
* ( IP + i ) = -1;
i = j = k = 0;
for( ; k < 3; k ++ )
{
i = str.Find( '.', j );
if( i == -1 )
break;
ipstr = str.Mid( j, i - j );
for( l = 0; l < i - j; l ++ )
if ( ipstr[l] < '0' || ipstr[l] > '9' )
return -1;
* ( IP + k ) = atoi((const char*)(LPCTSTR)ipstr);
j = i + 1;
}
for( i = 0; i < 3; i ++ )
if( * ( IP + i ) == -1 )
return -1;
* ( IP + 3 ) = 5;
ipfp = fopen("qqwry.dat", "rb");
if( ipfp == NULL )
return -1;
char pbuf[256] = {0};
fseek(ipfp, 0, SEEK_SET);
unsigned int indexHeadPos = 0;
unsigned int indexTailPos = 0; struct INDEXITEM target;
target.ip[0] = IP[3];
target.ip[1] = IP[2];
target.ip[2] = IP[1];
target.ip[3] = IP[0]; fread(&indexHeadPos, sizeof(indexHeadPos), 1, ipfp);
fread(&indexTailPos, sizeof(indexTailPos), 1, ipfp); int amount = (indexTailPos - indexHeadPos)/sizeof(struct INDEXITEM);
struct INDEXITEM start = LookForIndexItem(&target, ipfp, indexHeadPos, amount); char result[255] = {0};
RetrieveContent(&start, target.ip, ipfp, result);
str = result; fclose(ipfp);
return 0;
}struct INDEXITEM CConnectSocket::LookForIndexItem(struct INDEXITEM* const pAimItem,
FILE* pFile,
unsigned int indexBasePos,
unsigned int indexAmount )
{
struct INDEXITEM tmp;
int i = 0;
int j = indexAmount;
int s = (int)sizeof(struct INDEXITEM);
while ( i < j - 1 )
{
int k = (int) (i+j)/2;
int offset = (int)( k * s );
fseek(pFile, indexBasePos+offset, SEEK_SET);
fread(&tmp, s, 1, pFile);
int c = Compare( tmp.ip, pAimItem->ip );
if ( c > 0 )
j = k;
else if ( c < 0 )
i = k;
else
{
i = k;
j = k;
}
} fseek(pFile, indexBasePos+i*s, SEEK_SET);
fread(&tmp, s, 1, pFile);
return tmp;
}int CConnectSocket::Compare(unsigned char pA[4], unsigned char pB[4])
{
unsigned int a = BYTE4INT(pA);
unsigned int b = BYTE4INT(pB); if ( a > b )
return 1;
else if ( a < b )
return -1;
else
return 0;
}void CConnectSocket::GetData(unsigned char* str, FILE* pFile, int max)
{
int i = 0;
while ( (*(str+i)=fgetc(pFile)) && (i<(max-2)) )
i++;
str[i] = 0;
}void CConnectSocket::RetrieveContent(struct INDEXITEM* const pIndexItem,
unsigned char ip[4],
FILE* pFile,
char* content )
{
// to get the pos from the offset array
long tmp = 0;
unsigned char buf[80]; int pos = BYTE3INT(pIndexItem->offset);
fseek(pFile, pos, SEEK_SET);
fread(buf, 4, 1, pFile);
if ( Compare(ip, buf) > 0 )
{
strcat(content, "未知");
//printf("未知数据\n");
return;
} // 获取资料
fread(buf, 1, 1, pFile);
if ( buf[0] == 0x01 )
{ // 国家地区均重复, 跳转至新地址
fread(buf, 3, 1, pFile);
pos = BYTE3INT(buf);
fseek(pFile, pos, SEEK_SET);
fread(buf, 1, 1, pFile);
} // 获取国家
if ( buf[0] == 0x02 )
{
// 获取国家偏移
fread(buf, 3, 1, pFile);
// 保存地区信息
tmp = ftell(pFile);
pos = BYTE3INT(buf);
fseek(pFile, pos, SEEK_SET);
fread(buf, 1, 1, pFile);
}
if ( buf[0] == 0x01 || buf[0] == 0x02 )
{
strcat(content, "未知");
//printf("There is something wrong....\n");
return;
} if ( buf[0] )
GetData(buf+1, pFile, 40);
strcat(content, (char*)buf);
//printf("%s\t", buf); // 获取地区
if ( tmp )
fseek(pFile, tmp, SEEK_SET);
fread(buf, 1, 1, pFile);
while ( buf[0] == 0x02 )
{
// 获取地区偏移
fread(buf, 3, 1, pFile);
pos = BYTE3INT(buf);
fseek(pFile, pos, SEEK_SET);
fread(buf, 1, 1, pFile);
}
if ( buf[0] == 0x01 || buf[0] == 0x02 )
{
strcat(content, "未知");
//printf("There is something wrong....\n");
return;
}
if ( buf[0] )
GetData(buf+1, pFile, 40);
// strcat(content," ");
strcat(content, (char*)buf); return;
}