Chinaunix首页 | 论坛 | 博客
  • 博客访问: 588929
  • 博文数量: 752
  • 博客积分: 40000
  • 博客等级: 大将
  • 技术积分: 5005
  • 用 户 组: 普通用户
  • 注册时间: 2008-10-13 14:47
文章分类

全部博文(752)

文章存档

2011年(1)

2008年(751)

我的朋友

分类:

2008-10-13 16:50:13

//新格式. 请尊重原作者的劳动, 不要将IP数据库用于商业用途.

#define BYTE3INT(X)  (    ( X[0] & 0x000000FF ) \
                      | ( ( 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 是类似 61.147.225.* 的数据,返回的具体地址仍在 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 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 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 GetData(unsigned char* str, FILE* pFile, int max)
{
    int i = 0;
    while ( (*(str+i)=fgetc(pFile)) && (i<(max-2)) )
        i++;
    str[i] = 0;
}

void 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, "未知");
        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, "未知");
        return;
    }
    if ( buf[0] )
        GetData(buf+1, pFile, 40);
    strcat(content, (char*)buf);
    return;
}


--------------------next---------------------

阅读(293) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~