This commit is contained in:
Amberstone 2024-09-29 07:15:13 +09:00
parent 39adda76cc
commit df218c0157
Signed by: amber
GPG key ID: 094B0E55F98D8BF1
3 changed files with 43 additions and 46 deletions

View file

@ -159,9 +159,6 @@ $_system->addons = load_libs(__DIR__ . "/addons", "addon");
// $_system->modules = load_libs(__DIR__ . "/modules", "model"); // $_system->modules = load_libs(__DIR__ . "/modules", "model");
// $_system->modules = load_libs(__DIR__ . "/modules"); // $_system->modules = load_libs(__DIR__ . "/modules");
// arc: 이 이벤트는 before 가 없습니다.
EventHandler::triggerEvent("gnuboard.loadlibs.after", $_system);
function g5_path() function g5_path()
{ {
$result['path'] = str_replace('\\', '/', dirname(__FILE__)); $result['path'] = str_replace('\\', '/', dirname(__FILE__));
@ -183,6 +180,9 @@ $g5_path = g5_path();
include_once $g5_path['path'] . '/config.php'; // 설정 파일 include_once $g5_path['path'] . '/config.php'; // 설정 파일
// arc: 이 이벤트는 before 가 없습니다.
EventHandler::triggerEvent("gnuboard.loadlibs.after", $_system);
unset($g5_path); unset($g5_path);
// Cloudflare 환경을 고려한 https 사용여부 // Cloudflare 환경을 고려한 https 사용여부

View file

@ -16,7 +16,6 @@ date_default_timezone_set("Asia/Seoul");
/******************** /********************
경로 상수 경로 상수
********************/ ********************/
define('G5_DOMAIN', ''); define('G5_DOMAIN', '');
define('G5_HTTPS_DOMAIN', ''); define('G5_HTTPS_DOMAIN', '');

View file

@ -568,7 +568,6 @@ function conv_content($content, $html, $filter = true)
return $content; return $content;
} }
// http://htmlpurifier.org/ // http://htmlpurifier.org/
// Standards-Compliant HTML Filtering // Standards-Compliant HTML Filtering
// Safe : HTML Purifier defeats XSS with an audited whitelist // Safe : HTML Purifier defeats XSS with an audited whitelist
@ -610,9 +609,9 @@ function html_purifier($html)
$config->set('HTML.Nofollow', true); // rel=nofollow 으로 스팸유입을 줄임 $config->set('HTML.Nofollow', true); // rel=nofollow 으로 스팸유입을 줄임
} }
$config->set('URI.SafeIframeRegexp', '%^(https?:)?//(' . preg_replace('/\\\?\./', '\.', $safeiframe) . ')%'); $config->set('URI.SafeIframeRegexp', '%^(https?:)?//(' . preg_replace('/\\\?\./', '\.', $safeiframe) . ')%');
$config->set('Attr.AllowedFrameTargets', array('_blank')); $config->set('Attr.AllowedFrameTargets', ['_blank']);
//유튜브, 비메오 전체화면 가능하게 하기 //유튜브, 비메오 전체화면 가능하게 하기
$config->set('Filter.Custom', array(new HTMLPurifier_Filter_Iframevideo())); $config->set('Filter.Custom', [new HTMLPurifier_Filter_Iframevideo()]);
/* /*
* HTMLPurifier 설정을 변경할 있는 Event hook * HTMLPurifier 설정을 변경할 있는 Event hook
@ -3283,37 +3282,42 @@ function login_password_check($mb, $pass, $hash)
return check_password($pass, $hash); return check_password($pass, $hash);
} }
// 동일한 host url 인지 // 동일한 host url 인지
function check_url_host($url, $msg = '', $return_url = G5_URL, $is_redirect = false) function check_url_host($url, $msg = '', $return_url = G5_URL, $is_redirect = false)
{ {
if (!$msg) if (!$msg) {
$msg = 'url에 타 도메인을 지정할 수 없습니다.'; $msg = 'url에 타 도메인을 지정할 수 없습니다.';
}
if (run_replace('check_url_host_before', '', $url, $msg, $return_url, $is_redirect) === 'is_checked') { if (run_replace('check_url_host_before', '', $url, $msg, $return_url, $is_redirect) === 'is_checked') {
return; return;
} }
// KVE-2021-1277 Open Redirect 취약점 해결
if (preg_match('#\\\0#', $url)) { if (preg_match('#\\\0#', $url)) {
alert('url 에 올바르지 않은 값이 포함되어 있습니다.'); alert('url 에 올바르지 않은 값이 포함되어 있습니다.');
} }
while (($replace_url = preg_replace(array('/\/{2,}/', '/\\@/'), array('//', ''), urldecode($url))) != $url) { // remove consecutive slashes
$patterns = ['/\/{2,}/', '/\\@/'];
$replacements = ['/', ''];
while (($replace_url = preg_replace($patterns, $replacements, urldecode($url))) != $url) {
$url = $replace_url; $url = $replace_url;
} }
$p = @parse_url(trim($url)); $p = @parse_url(trim($url));
$host = preg_replace('/:[0-9]+$/', '', $_SERVER['HTTP_HOST']); // ref: https://github.com/gnuboard/gnuboard5/issues/261
$host = preg_replace('/:[0-9]+$/', '', G5_DOMAIN ?: G5_HTTPS_DOMAIN ?: $_SERVER['HTTP_HOST']);
$is_host_check = false; $is_host_check = false;
// url을 urlencode 를 2번이상하면 parse_url 에서 scheme와 host 값을 가져올수 없는 취약점이 존재함 // decode url if necessary
if ($is_redirect && !isset($p['host']) && urldecode($url) != $url) { if ($is_redirect && !isset($p['host']) && urldecode($url) != $url) {
$i = 0; $max_iterations = 3;
while ($i <= 3) { for ($i = 0; $i <= $max_iterations; $i++) {
$url = urldecode($url); $decoded = urldecode($url);
if (urldecode($url) == $url) if ($decoded === $url)
break; break;
$i++; $url = $decoded;
} }
if (urldecode($url) == $url) { if (urldecode($url) == $url) {
@ -3323,22 +3327,19 @@ function check_url_host($url, $msg = '', $return_url = G5_URL, $is_redirect = fa
} }
} }
// if(stripos($url, 'http:') !== false) { // check host for redirect
// if(!isset($p['scheme']) || !$p['scheme'] || !isset($p['host']) || !$p['host'])
// alert('url 정보가 올바르지 않습니다.', $return_url);
// }
//php 5.6.29 이하 버전에서는 parse_url 버그가 존재함
//php 7.0.1 ~ 7.0.5 버전에서는 parse_url 버그가 존재함
if ($is_redirect && (isset($p['host']) && $p['host'])) { if ($is_redirect && (isset($p['host']) && $p['host'])) {
$bool_ch = false; $sensitive_parts = ['user', 'host'];
foreach (array('user', 'host') as $key) { $has_sensitive_chars = false;
if (isset($p[$key]) && strpbrk($p[$key], ':/?#@')) { foreach ($sensitive_parts as $part) {
$bool_ch = true; if (isset($p[$part]) && strpbrk($p[$part], ':/?#@')) {
$has_sensitive_chars = true;
break;
} }
} }
if ($bool_ch) {
$regex = '/https?\:\/\/' . $host . '/i'; if ($has_sensitive_chars) {
$regex = '/https?\:\/\/' . preg_quote($host, '/') . '/i';
if (!preg_match($regex, $url)) { if (!preg_match($regex, $url)) {
$is_host_check = true; $is_host_check = true;
} }
@ -3346,16 +3347,15 @@ function check_url_host($url, $msg = '', $return_url = G5_URL, $is_redirect = fa
} }
if ((isset($p['scheme']) && $p['scheme']) || (isset($p['host']) && $p['host']) || $is_host_check) { if ((isset($p['scheme']) && $p['scheme']) || (isset($p['host']) && $p['host']) || $is_host_check) {
//if ($p['host'].(isset($p['port']) ? ':'.$p['port'] : '') != $_SERVER['HTTP_HOST']) { if (run_replace('check_same_url_host', ($p['host'] != $host) || $is_host_check, $p, $host, $is_host_check, $return_url, $is_redirect)) {
if (run_replace('check_same_url_host', (($p['host'] != $host) || $is_host_check), $p, $host, $is_host_check, $return_url, $is_redirect)) { echo "<script>
echo '<script>' . PHP_EOL; alert('url에 타 도메인을 지정할 수 없습니다.');
echo 'alert("url에 타 도메인을 지정할 수 없습니다.");' . PHP_EOL; document.location.href = '{$return_url}';
echo 'document.location.href = "' . $return_url . '";' . PHP_EOL; </script>
echo '</script>' . PHP_EOL; <noscript>
echo '<noscript>' . PHP_EOL; <p>{$msg}</p>
echo '<p>' . $msg . '</p>' . PHP_EOL; <p><a href='{$return_url}'>돌아가기</a></p>
echo '<p><a href="' . $return_url . '">돌아가기</a></p>' . PHP_EOL; </noscript>";
echo '</noscript>' . PHP_EOL;
exit; exit;
} }
} }
@ -3365,9 +3365,7 @@ function check_url_host($url, $msg = '', $return_url = G5_URL, $is_redirect = fa
function clean_query_string($query, $amp = true) function clean_query_string($query, $amp = true)
{ {
$qstr = trim($query); $qstr = trim($query);
parse_str($qstr, $out); parse_str($qstr, $out);
if (is_array($out)) { if (is_array($out)) {
$q = []; $q = [];