geoipcity.inc 6.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217
  1. <?php
  2. /* geoipcity.inc
  3. *
  4. * Copyright (C) 2004 Maxmind LLC
  5. *
  6. * This library is free software; you can redistribute it and/or
  7. * modify it under the terms of the GNU Lesser General Public
  8. * License as published by the Free Software Foundation; either
  9. * version 2.1 of the License, or (at your option) any later version.
  10. *
  11. * This library is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  14. * Lesser General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU Lesser General Public
  17. * License along with this library; if not, write to the Free Software
  18. * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
  19. */
  20. /*
  21. * Changelog:
  22. *
  23. * 2005-01-13 Andrew Hill, Awarez Ltd. (http://www.awarez.net)
  24. * Formatted file according to PEAR library standards.
  25. * Changed inclusion of geoip.inc file to require_once, so that
  26. * this library can be used in the same script as geoip.inc.
  27. */
  28. define("FULL_RECORD_LENGTH",50);
  29. require_once 'geoip.inc';
  30. require_once 'geoipregionvars.php';
  31. class geoiprecord {
  32. var $country_code;
  33. var $country_code3;
  34. var $country_name;
  35. var $region;
  36. var $city;
  37. var $postal_code;
  38. var $latitude;
  39. var $longitude;
  40. var $area_code;
  41. var $dma_code; # metro and dma code are the same. use metro_code
  42. var $metro_code;
  43. var $continent_code;
  44. }
  45. class geoipdnsrecord {
  46. var $country_code;
  47. var $country_code3;
  48. var $country_name;
  49. var $region;
  50. var $regionname;
  51. var $city;
  52. var $postal_code;
  53. var $latitude;
  54. var $longitude;
  55. var $areacode;
  56. var $dmacode;
  57. var $isp;
  58. var $org;
  59. var $metrocode;
  60. }
  61. function getrecordwithdnsservice($str){
  62. $record = new geoipdnsrecord;
  63. $keyvalue = split(";",$str);
  64. foreach ($keyvalue as $keyvalue2){
  65. list($key,$value) = split("=",$keyvalue2);
  66. if ($key == "co"){
  67. $record->country_code = $value;
  68. }
  69. if ($key == "ci"){
  70. $record->city = $value;
  71. }
  72. if ($key == "re"){
  73. $record->region = $value;
  74. }
  75. if ($key == "ac"){
  76. $record->areacode = $value;
  77. }
  78. if ($key == "dm" || $key == "me" ){
  79. $record->dmacode = $value;
  80. $record->metrocode = $value;
  81. }
  82. if ($key == "is"){
  83. $record->isp = $value;
  84. }
  85. if ($key == "or"){
  86. $record->org = $value;
  87. }
  88. if ($key == "zi"){
  89. $record->postal_code = $value;
  90. }
  91. if ($key == "la"){
  92. $record->latitude = $value;
  93. }
  94. if ($key == "lo"){
  95. $record->longitude = $value;
  96. }
  97. }
  98. $number = $GLOBALS['GEOIP_COUNTRY_CODE_TO_NUMBER'][$record->country_code];
  99. $record->country_code3 = $GLOBALS['GEOIP_COUNTRY_CODES3'][$number];
  100. $record->country_name = $GLOBALS['GEOIP_COUNTRY_NAMES'][$number];
  101. if ($record->region != "") {
  102. if (($record->country_code == "US") || ($record->country_code == "CA")){
  103. $record->regionname = $GLOBALS['ISO'][$record->country_code][$record->region];
  104. } else {
  105. $record->regionname = $GLOBALS['FIPS'][$record->country_code][$record->region];
  106. }
  107. }
  108. return $record;
  109. }
  110. function _get_record($gi,$ipnum){
  111. $seek_country = _geoip_seek_country($gi,$ipnum);
  112. if ($seek_country == $gi->databaseSegments) {
  113. return NULL;
  114. }
  115. // workaround php's broken substr, strpos, etc handling with
  116. // mbstring.func_overload and mbstring.internal_encoding
  117. $enc = mb_internal_encoding();
  118. mb_internal_encoding('ISO-8859-1');
  119. $record_pointer = $seek_country + (2 * $gi->record_length - 1) * $gi->databaseSegments;
  120. if ($gi->flags & GEOIP_MEMORY_CACHE) {
  121. $record_buf = substr($gi->memory_buffer,$record_pointer,FULL_RECORD_LENGTH);
  122. } elseif ($gi->flags & GEOIP_SHARED_MEMORY){
  123. $record_buf = @shmop_read($gi->shmid,$record_pointer,FULL_RECORD_LENGTH);
  124. } else {
  125. fseek($gi->filehandle, $record_pointer, SEEK_SET);
  126. $record_buf = fread($gi->filehandle,FULL_RECORD_LENGTH);
  127. }
  128. $record = new geoiprecord;
  129. $record_buf_pos = 0;
  130. $char = ord(substr($record_buf,$record_buf_pos,1));
  131. $record->country_code = $gi->GEOIP_COUNTRY_CODES[$char];
  132. $record->country_code3 = $gi->GEOIP_COUNTRY_CODES3[$char];
  133. $record->country_name = $gi->GEOIP_COUNTRY_NAMES[$char];
  134. $record->continent_code = $gi->GEOIP_CONTINENT_CODES[$char];
  135. $record_buf_pos++;
  136. $str_length = 0;
  137. // Get region
  138. $char = ord(substr($record_buf,$record_buf_pos+$str_length,1));
  139. while ($char != 0){
  140. $str_length++;
  141. $char = ord(substr($record_buf,$record_buf_pos+$str_length,1));
  142. }
  143. if ($str_length > 0){
  144. $record->region = substr($record_buf,$record_buf_pos,$str_length);
  145. }
  146. $record_buf_pos += $str_length + 1;
  147. $str_length = 0;
  148. // Get city
  149. $char = ord(substr($record_buf,$record_buf_pos+$str_length,1));
  150. while ($char != 0){
  151. $str_length++;
  152. $char = ord(substr($record_buf,$record_buf_pos+$str_length,1));
  153. }
  154. if ($str_length > 0){
  155. $record->city = substr($record_buf,$record_buf_pos,$str_length);
  156. }
  157. $record_buf_pos += $str_length + 1;
  158. $str_length = 0;
  159. // Get postal code
  160. $char = ord(substr($record_buf,$record_buf_pos+$str_length,1));
  161. while ($char != 0){
  162. $str_length++;
  163. $char = ord(substr($record_buf,$record_buf_pos+$str_length,1));
  164. }
  165. if ($str_length > 0){
  166. $record->postal_code = substr($record_buf,$record_buf_pos,$str_length);
  167. }
  168. $record_buf_pos += $str_length + 1;
  169. $str_length = 0;
  170. // Get latitude and longitude
  171. $latitude = 0;
  172. $longitude = 0;
  173. for ($j = 0;$j < 3; ++$j){
  174. $char = ord(substr($record_buf,$record_buf_pos++,1));
  175. $latitude += ($char << ($j * 8));
  176. }
  177. $record->latitude = ($latitude/10000) - 180;
  178. for ($j = 0;$j < 3; ++$j){
  179. $char = ord(substr($record_buf,$record_buf_pos++,1));
  180. $longitude += ($char << ($j * 8));
  181. }
  182. $record->longitude = ($longitude/10000) - 180;
  183. if (GEOIP_CITY_EDITION_REV1 == $gi->databaseType){
  184. $metroarea_combo = 0;
  185. if ($record->country_code == "US"){
  186. for ($j = 0;$j < 3;++$j){
  187. $char = ord(substr($record_buf,$record_buf_pos++,1));
  188. $metroarea_combo += ($char << ($j * 8));
  189. }
  190. $record->metro_code = $record->dma_code = floor($metroarea_combo/1000);
  191. $record->area_code = $metroarea_combo%1000;
  192. }
  193. }
  194. mb_internal_encoding($enc);
  195. return $record;
  196. }
  197. function GeoIP_record_by_addr ($gi,$addr){
  198. if ($addr == NULL){
  199. return 0;
  200. }
  201. $ipnum = ip2long($addr);
  202. return _get_record($gi, $ipnum);
  203. }
  204. ?>