|
1 | 1 | <?php |
2 | 2 |
|
3 | | -/** |
| 3 | +use IPLib\Factory; |
| 4 | + |
| 5 | +/* |
4 | 6 | +-----------------------------------------------------------------------+ |
5 | 7 | | This file is part of the Roundcube Webmail client | |
6 | 8 | | | |
@@ -419,6 +421,48 @@ public static function html_identifier($str, $encode = false) |
419 | 421 | return asciiwords($str, true, '_'); |
420 | 422 | } |
421 | 423 |
|
| 424 | + /** |
| 425 | + * Check if an URL point to a local network location. |
| 426 | + * |
| 427 | + * @param string $url |
| 428 | + * |
| 429 | + * @return bool |
| 430 | + */ |
| 431 | + public static function is_local_url($url) |
| 432 | + { |
| 433 | + $host = parse_url($url, \PHP_URL_HOST); |
| 434 | + |
| 435 | + if (is_string($host)) { |
| 436 | + // TODO: This is pretty fast, but a single message can contain multiple links |
| 437 | + // to the same target, maybe we should do some in-memory caching. |
| 438 | + if ($address = Factory::parseAddressString($host = trim($host, '[]'))) { |
| 439 | + $nets = [ |
| 440 | + '127.0.0.0/8', // loopback |
| 441 | + '10.0.0.0/8', // RFC1918 |
| 442 | + '172.16.0.0/12', // RFC1918 |
| 443 | + '192.168.0.0/16', // RFC1918 |
| 444 | + '169.254.0.0/16', // link-local / cloud metadata |
| 445 | + '::1/128', |
| 446 | + 'fc00::/7', |
| 447 | + ]; |
| 448 | + |
| 449 | + foreach ($nets as $net) { |
| 450 | + $range = Factory::parseRangeString($net); |
| 451 | + if ($range->contains($address)) { |
| 452 | + return true; |
| 453 | + } |
| 454 | + } |
| 455 | + |
| 456 | + return false; |
| 457 | + } |
| 458 | + |
| 459 | + // FIXME: Should we accept any non-fqdn hostnames? |
| 460 | + return (bool) preg_match('/^localhost(\.localdomain)?$/i', $host); |
| 461 | + } |
| 462 | + |
| 463 | + return false; |
| 464 | + } |
| 465 | + |
422 | 466 | /** |
423 | 467 | * Replace all css definitions with #container [def] |
424 | 468 | * and remove css-inlined scripting, make position style safe |
|
0 commit comments