Skip to content

Instantly share code, notes, and snippets.

@luelista
Last active September 21, 2018 19:38
Show Gist options
  • Save luelista/96730a4dd1c881a31ef754e6792b3ca9 to your computer and use it in GitHub Desktop.
Save luelista/96730a4dd1c881a31ef754e6792b3ca9 to your computer and use it in GitHub Desktop.
Scripts for fixing the REMOTE_ADDR when working with Cloudflare's reverse proxy, and automatically fetching the cloudflare net ranges
<?php
// Include this in your scripts where REMOTE_ADDR is used
function check_ip_range($ip, $rangeFile) {
$bin = inet_pton($ip);
$adrlen = strlen($bin);
if ($adrlen == 16) { //IPv6
$rangeFile.=".ipv6";
} else {
$rangeFile.=".ipv4";
}
$fh = fopen($rangeFile, "rb");
while(!feof($fh)) {
$cAdr = fread($fh, $adrlen); $mask = fread($fh, $adrlen);
if ($cAdr === ($bin & $mask)) {fclose($fh); return TRUE;}
}
fclose($fh); return FALSE;
}
// Fix REMOTE_ADDR if behind reverse proxy, e.g. cloudflare
if (!empty($_SERVER['HTTP_CF_CONNECTING_IP'])) {
if (check_ip_range($_SERVER["REMOTE_ADDR"], "./cloudflare")) {
$_SERVER["REMOTE_ADDR"] = $_SERVER['HTTP_CF_CONNECTING_IP'];
}
}
<?php
// Call this regularly from a cron job
// Fetches the IP ranges from cloudflare and stores them optimized in cloudflare.ip{v6,v6} files
function cidr_to_mask_v4($netbits) {
if ($netbits >= 32) return "\xff\xff\xff\xff";
if ($netbits <= 0) return "\x00\x00\x00\x00";
$n=0; while($netbits-- > 0) $n=($n>>1)|0x80000000;
return pack ("N", $n);
}
function write_range_file($file, $adrlen, $addresses) {
$fh = fopen($file."_new", "wb");
foreach($addresses as $iprange) {
if (empty($iprange)) continue;
list($ip, $netbits) = explode("/", trim($iprange));
$bin = inet_pton($ip);
if ($adrlen == 4) $bin .= cidr_to_mask_v4($netbits);
else if ($adrlen == 16) $bin .= cidr_to_mask_v4($netbits) . cidr_to_mask_v4($netbits - 32) . cidr_to_mask_v4($netbits - 64) . cidr_to_mask_v4($netbits - 96);
// echo "$ip, $netbits, ".bin2hex($bin)."\n";
fwrite($fh, $bin);
if (strlen($bin) != $adrlen*2) die("Invalid address length");
}
fclose($fh);
if (filesize($file."_new") > 0)
rename($file."_new", $file);
}
$ipv4 = explode("\n",file_get_contents("https://www.cloudflare.com/ips-v4"));
write_range_file("cloudflare.ipv4", 4, $ipv4);
$ipv6 = explode("\n",file_get_contents("https://www.cloudflare.com/ips-v6"));
write_range_file("cloudflare.ipv6", 16, $ipv6);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment