fix: [internal] CIDR validation

pull/8170/head
Jakub Onderka 2022-02-23 09:52:59 +01:00 committed by Jakub Onderka
parent 8424b2637f
commit b32f397949
3 changed files with 32 additions and 13 deletions

View File

@ -78,9 +78,15 @@ class CidrTool
return false;
}
$maximumNetmask = strlen($ipBytes) === 4 ? 32 : 128;
if (isset($parts[1]) && ($parts[1] > $maximumNetmask || $parts[1] < 0)) {
return false; // Netmask part of CIDR is invalid
if (isset($parts[1])) {
if (!ctype_digit($parts[1])) {
return false;
}
$maximumNetmask = strlen($ipBytes) === 4 ? 32 : 128;
if ($parts[1] > $maximumNetmask || $parts[1] < 0) {
return false; // Netmask part of CIDR is invalid
}
}
return true;

View File

@ -2,6 +2,7 @@
App::uses('AppModel', 'Model');
App::uses('RandomTool', 'Tools');
App::uses('CidrTool', 'Tools');
App::uses('JsonTool', 'Tools');
App::uses('BlowfishConstantPasswordHasher', 'Controller/Component/Auth');
/**
@ -47,19 +48,20 @@ class AuthKey extends AppModel
}
if (!empty($this->data['AuthKey']['allowed_ips'])) {
if (is_string($this->data['AuthKey']['allowed_ips'])) {
$this->data['AuthKey']['allowed_ips'] = trim($this->data['AuthKey']['allowed_ips']);
if (empty($this->data['AuthKey']['allowed_ips'])) {
$this->data['AuthKey']['allowed_ips'] = [];
$allowedIps = &$this->data['AuthKey']['allowed_ips'];
if (is_string($allowedIps)) {
$allowedIps = trim($allowedIps);
if (empty($allowedIps)) {
$allowedIps = [];
} else {
$this->data['AuthKey']['allowed_ips'] = explode("\n", $this->data['AuthKey']['allowed_ips']);
$this->data['AuthKey']['allowed_ips'] = array_map('trim', $this->data['AuthKey']['allowed_ips']);
$allowedIps = preg_split('/([\n,])/', $allowedIps);
$allowedIps = array_map('trim', $allowedIps);
}
}
if (!is_array($this->data['AuthKey']['allowed_ips'])) {
if (!is_array($allowedIps)) {
$this->invalidate('allowed_ips', 'Allowed IPs must be array');
}
foreach ($this->data['AuthKey']['allowed_ips'] as $cidr) {
foreach ($allowedIps as $cidr) {
if (!CidrTool::validate($cidr)) {
$this->invalidate('allowed_ips', "$cidr is not valid IP range");
}
@ -91,7 +93,7 @@ class AuthKey extends AppModel
{
foreach ($results as $key => $val) {
if (isset($val['AuthKey']['allowed_ips'])) {
$results[$key]['AuthKey']['allowed_ips'] = $this->jsonDecode($val['AuthKey']['allowed_ips']);
$results[$key]['AuthKey']['allowed_ips'] = JsonTool::decode($val['AuthKey']['allowed_ips']);
}
}
return $results;
@ -103,7 +105,7 @@ class AuthKey extends AppModel
if (empty($this->data['AuthKey']['allowed_ips'])) {
$this->data['AuthKey']['allowed_ips'] = null;
} else {
$this->data['AuthKey']['allowed_ips'] = json_encode($this->data['AuthKey']['allowed_ips']);
$this->data['AuthKey']['allowed_ips'] = JsonTool::encode($this->data['AuthKey']['allowed_ips']);
}
}
return true;

View File

@ -5,6 +5,17 @@ use PHPUnit\Framework\TestCase;
class CidrToolTest extends TestCase
{
public function testValidate(): void
{
$this->assertTrue(CidrTool::validate('1.2.3.4'));
$this->assertTrue(CidrTool::validate('1.2.3.4/32'));
$this->assertTrue(CidrTool::validate('::1'));
$this->assertTrue(CidrTool::validate('::1/128'));
$this->assertFalse(CidrTool::validate('::1/a'));
$this->assertFalse(CidrTool::validate('1.2.3.4/a'));
$this->assertFalse(CidrTool::validate('1.2.3.4/32, 1.2.3.4'));
}
public function testEmptyList(): void
{
$cidrTool = new CidrTool([]);