Fix issue matching IPs when whitelisting is enabled

This commit is contained in:
Andrew Hancox 2017-11-18 14:10:45 +00:00
parent f0f988e9d3
commit 91c4be7df4
2 changed files with 53 additions and 27 deletions

View file

@ -122,38 +122,45 @@ class core_userkey_manager implements userkey_manager_interface {
print_error('expiredkey');
}
if ($key->iprestriction) {
$remoteaddr = getremoteaddr(null);
if (isset($this->config->ipwhitelist)) {
$whitelist = $this->config->ipwhitelist;
} else {
$whitelist = false;
}
if (empty($remoteaddr) ) {
print_error('noip', 'auth_userkey');
} else if (!empty($whitelist)) {
$ips = explode(';', $whitelist);
$whitelisted = false;
foreach ($ips as $ip) {
if (address_in_subnet($remoteaddr, $ip)) {
$whitelisted = true;
}
}
if (!$whitelisted) {
print_error('ipmismatch', 'error', '', null, "Remote address: $remoteaddr\nKey IP: $key->iprestriction");
}
} else if (!address_in_subnet($remoteaddr, $key->iprestriction)) {
print_error('ipmismatch', 'error', '', null, "Remote address: $remoteaddr\nKey IP: $key->iprestriction");
}
}
if (!$user = $DB->get_record('user', array('id' => $key->userid))) {
print_error('invaliduserid');
}
$this->validate_ip_address($key);
return $key;
}
/**
* Validates key IP address and returns true if valid.
*
* @param object $key Key object including userid property.
*
* @throws \moodle_exception If provided key is not valid.
*/
protected function validate_ip_address($key) {
if (!$key->iprestriction) {
return true;
}
$remoteaddr = getremoteaddr(null);
if (empty($remoteaddr)) {
print_error('noip', 'auth_userkey');
}
if (address_in_subnet($remoteaddr, $key->iprestriction)) {
return true;
}
if (isset($this->config->ipwhitelist)) {
$ips = explode(';', $this->config->ipwhitelist);
foreach ($ips as $ip) {
if (address_in_subnet($remoteaddr, $ip)) {
return true;
}
}
}
print_error('ipmismatch', 'error', '', null, "Remote address: $remoteaddr\nKey IP: $key->iprestriction");
}
}

View file

@ -169,6 +169,25 @@ class core_userkey_manager_testcase extends advanced_testcase {
$manager->validate_key($value);
}
/**
* Test that IP address mismatch exception gets thrown if incorrect IP and outside whitelist.
*/
public function test_create_correct_key_if_ip_correct_not_whitelisted_and_whitelist_set() {
global $DB;
$this->config->iprestriction = true;
$this->config->ipwhitelist = '10.0.0.0/8;172.16.0.0/12;192.168.0.0/16';
$manager = new core_userkey_manager($this->config);
$value = $manager->create_key($this->user->id, '193.168.1.1');
$_SERVER['HTTP_CLIENT_IP'] = '193.168.1.1';
$key = $manager->validate_key($value);
$this->assertEquals($this->user->id, $key->userid);
}
/**
* Test that key is accepted if incorrect IP and within whitelist.
*/