您所在的位置:小祥子 » 编程 » PHP » 正文

PHP根据IP地址获取地区地址

时间:2015-02-13 编辑:本站 来源:本站原创

方法是从齐博CMS里弄来的,可以到齐博官方网站下载一个IP.DAT数据库,然后就可以得到真实的地址了,下面有部分地方是定义了常量,如ROOT_PATH为网站的目录。

function ipfrom($ip) {
 if(!preg_match("/^\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}$/", $ip)) {
  return '';
 }
 if( !is_file(ROOT_PATH.'inc/ip.dat') ){
  return '<a title><A HREF="http://down.qibosoft.com/ip.rar" title="点击下载后,解压放到整站/inc/目录即可">IP库不存在,请点击下载一个!</A></a>';
 }
 if($fd = @fopen(ROOT_PATH.'inc/ip.dat', 'rb')) {

  $ip = explode('.', $ip);
  $ipNum = $ip[0] * 16777216 + $ip[1] * 65536 + $ip[2] * 256 + $ip[3];

  $DataBegin = fread($fd, 4);
  $DataEnd = fread($fd, 4);
  $ipbegin = implode('', unpack('L', $DataBegin));
  if($ipbegin < 0) $ipbegin += pow(2, 32);
  $ipend = implode('', unpack('L', $DataEnd));
  if($ipend < 0) $ipend += pow(2, 32);
  $ipAllNum = ($ipend - $ipbegin) / 7 + 1;

  $BeginNum = 0;
  $EndNum = $ipAllNum;

  while($ip1num > $ipNum || $ip2num < $ipNum) {
   $Middle= intval(($EndNum + $BeginNum) / 2);

   fseek($fd, $ipbegin + 7 * $Middle);
   $ipData1 = fread($fd, 4);
   if(strlen($ipData1) < 4) {
    fclose($fd);
    return '- System Error';
   }
   $ip1num = implode('', unpack('L', $ipData1));
   if($ip1num < 0) $ip1num += pow(2, 32);

   if($ip1num > $ipNum) {
    $EndNum = $Middle;
    continue;
   }

   $DataSeek = fread($fd, 3);
   if(strlen($DataSeek) < 3) {
    fclose($fd);
    return '- System Error';
   }
   $DataSeek = implode('', unpack('L', $DataSeek.chr(0)));
   fseek($fd, $DataSeek);
   $ipData2 = fread($fd, 4);
   if(strlen($ipData2) < 4) {
    fclose($fd);
    return '- System Error';
   }
   $ip2num = implode('', unpack('L', $ipData2));
   if($ip2num < 0) $ip2num += pow(2, 32);

   if($ip2num < $ipNum) {
    if($Middle == $BeginNum) {
     fclose($fd);
     return '- Unknown';
    }
    $BeginNum = $Middle;
   }
  }

  $ipFlag = fread($fd, 1);
  if($ipFlag == chr(1)) {
   $ipSeek = fread($fd, 3);
   if(strlen($ipSeek) < 3) {
    fclose($fd);
    return '- System Error';
   }
   $ipSeek = implode('', unpack('L', $ipSeek.chr(0)));
   fseek($fd, $ipSeek);
   $ipFlag = fread($fd, 1);
  }

  if($ipFlag == chr(2)) {
   $AddrSeek = fread($fd, 3);
   if(strlen($AddrSeek) < 3) {
    fclose($fd);
    return '- System Error';
   }
   $ipFlag = fread($fd, 1);
   if($ipFlag == chr(2)) {
    $AddrSeek2 = fread($fd, 3);
    if(strlen($AddrSeek2) < 3) {
     fclose($fd);
     return '- System Error';
    }
    $AddrSeek2 = implode('', unpack('L', $AddrSeek2.chr(0)));
    fseek($fd, $AddrSeek2);
   } else {
    fseek($fd, -1, SEEK_CUR);
   }

   while(($char = fread($fd, 1)) != chr(0))
    $ipAddr2 .= $char;

   $AddrSeek = implode('', unpack('L', $AddrSeek.chr(0)));
   fseek($fd, $AddrSeek);

   while(($char = fread($fd, 1)) != chr(0))
    $ipAddr1 .= $char;
  } else {
   fseek($fd, -1, SEEK_CUR);
   while(($char = fread($fd, 1)) != chr(0))
    $ipAddr1 .= $char;

   $ipFlag = fread($fd, 1);
   if($ipFlag == chr(2)) {
    $AddrSeek2 = fread($fd, 3);
    if(strlen($AddrSeek2) < 3) {
     fclose($fd);
     return '- System Error';
    }
    $AddrSeek2 = implode('', unpack('L', $AddrSeek2.chr(0)));
    fseek($fd, $AddrSeek2);
   } else {
    fseek($fd, -1, SEEK_CUR);
   }
   while(($char = fread($fd, 1)) != chr(0))
    $ipAddr2 .= $char;
  }
  fclose($fd);

  if(preg_match('/http/i', $ipAddr2)) {
   $ipAddr2 = '';
  }
  $ipaddr = "$ipAddr1 $ipAddr2";
  $ipaddr = preg_replace('/CZ88\.NET/is', '', $ipaddr);
  $ipaddr = preg_replace('/^\s*/is', '', $ipaddr);
  $ipaddr = preg_replace('/\s*$/is', '', $ipaddr);
  if(preg_match('/http/i', $ipaddr) || $ipaddr == '') {
   $ipaddr = '- Unknown';
  }

  if(WEB_LANG=='big5'){
   require_once(ROOT_PATH."inc/class.chinese.PHP");
   $cnvert = new Chinese("GB2312","BIG5",$ipaddr,ROOT_PATH."./inc/gbkcode/");
   $ipaddr = $cnvert->ConvertIT();
  }elseif(WEB_LANG=='utf-8'){
   require_once(ROOT_PATH."inc/class.chinese.php");
   $cnvert = new Chinese("GB2312","UTF8",$ipaddr,ROOT_PATH."./inc/gbkcode/");
   $ipaddr = $cnvert->ConvertIT();
  }

  return $ipaddr;
 }
}
 

关键词:IP 地址