Check in 1.9.0.1

This commit is contained in:
George Wang
2026-05-07 23:52:18 -04:00
parent 8859ed981b
commit 28f7da3374
37 changed files with 1901 additions and 288 deletions
+1 -1
View File
@@ -1,7 +1,7 @@
cmake_minimum_required(VERSION 3.0)
set( CMAKE_EXPORT_COMPILE_COMMANDS ON)
Project(openlitespeed VERSION 1.8.5)
Project(openlitespeed VERSION 1.9.0)
INCLUDE( ${PROJECT_SOURCE_DIR}/CMakeModules/common.cmake)
INCLUDE(GNUInstallDirs)
+1 -2
View File
@@ -100,7 +100,7 @@ usage()
echo " This should always be done for a first time build,"
echo " but requires manually entering the root password"
echo " -d : Debug build"
echo " -p ON|OFF : Whether you want pagespeed compiled or not. Defaults ON only for x64 Linux"
echo " -p ON|OFF : Whether you want pagespeed compiled or not. Defaults to OFF "
echo " -o ON|OFF : Whether you want mod_security compiled or not. Defaults ON for everywhere but Mac"
echo " -l ON|OFF : Whether you want lua compiled or not. Defaults ON only for x64 Linux"
exit 1
@@ -123,7 +123,6 @@ getOptions()
MOD_LUA="OFF"
if [ "${ISLINUX}" = "yes" ] && [ "${ARCH}" = "x86_64" ]; then
if [ ! "${OSTYPE}" = "ALPINE" ] ; then
MOD_PAGESPEED="ON"
MOD_LUA="ON"
ALPINE="ON"
fi
+1 -7
View File
@@ -153,17 +153,11 @@ class CAuthorizer
}
if (isset($parts['scheme'])) {
$expectedScheme = $this->isHttpsRequest() ? 'https' : 'http';
if (strtolower($parts['scheme']) !== $expectedScheme) {
if (strtolower($parts['scheme']) !== 'https') {
return false;
}
}
$requestPort = $this->getRequestPort();
if ($requestPort !== null && isset($parts['port']) && (int) $parts['port'] !== $requestPort) {
return false;
}
return true;
}
@@ -78,6 +78,18 @@ class ConfigActionContext
}
}
public function SetViewRoute($view, $viewName, $pid, $tid = null, $ref = null)
{
if ($this->_routeState != null && method_exists($this->_routeState, 'SetViewRoute')) {
$this->_routeState->SetViewRoute($view, $viewName, $pid, $tid, $ref);
return;
}
if (is_object($this->_mutationDisplay) && method_exists($this->_mutationDisplay, 'SetViewRoute')) {
$this->_mutationDisplay->SetViewRoute($view, $viewName, $pid, $tid, $ref);
}
}
public function AddTopMsg($message)
{
if (is_object($this->_mutationDisplay) && method_exists($this->_mutationDisplay, 'AddTopMsg')) {
@@ -70,6 +70,11 @@ class ConfigActionRequest
$this->_context->SetViewName($viewName);
}
public function SetViewRoute($view, $viewName, $pid, $tid = null, $ref = null)
{
$this->_context->SetViewRoute($view, $viewName, $pid, $tid, $ref);
}
public function AddTopMsg($message)
{
$this->_context->AddTopMsg($message);
@@ -26,6 +26,7 @@ class ConfigActionService
$validationResult = self::validatePost($request);
$displayData = $validationResult->GetExtracted();
$hasDisplayData = true;
self::appendValidationMessages($request, $validationResult);
if ($validationResult->HasErr()) {
self::setAct($request, 'S');
@@ -33,13 +34,22 @@ class ConfigActionService
break;
}
if ($validationResult->ShouldStopSave()) {
self::setAct($request, 'S');
break;
}
$isNewEntry = self::isNewEntry($request);
$changeDiff = self::buildChangeDiff($confdata, $displayData, $request);
$markChanged = self::shouldMarkChangedAfterSave($request, $displayData);
$forceReLogin = self::shouldForceReLoginAfterSave($request, $displayData);
$confdata->SavePost($displayData, $request->GetMutationDisplay());
$hasDisplayData = false;
$trimRoute = true;
if ($isNewEntry && self::routeToSavedEntryConfig($request, $displayData)) {
$reloadConfig = true;
} else {
$trimRoute = true;
}
if ($isNewEntry) {
OpsAuditLogger::configAdd(
self::resolveAuditTarget($request),
@@ -123,6 +133,17 @@ class ConfigActionService
return new ConfigActionResult($displayData, $hasDisplayData, $reloadConfig, $markChanged, $forceReLogin);
}
private static function appendValidationMessages($request, $validationResult)
{
if ($validationResult == null || !method_exists($validationResult, 'GetMessages')) {
return;
}
foreach ($validationResult->GetMessages() as $message) {
self::appendTopMessage($request, $message);
}
}
private static function validatePost($request)
{
$result = $request->ValidatePost();
@@ -386,6 +407,91 @@ class ConfigActionService
return $rs->GetLastRef() === '~';
}
private static function routeToSavedEntryConfig($request, $extractData)
{
if (!($extractData instanceof CNode)) {
return false;
}
$entryName = self::resolveSavedEntryName($extractData);
if ($entryName === '') {
return false;
}
$target = self::resolveSavedEntryRoute($request, self::resolveMutationTableId($request));
if ($target === null) {
return false;
}
$request->SetViewRoute($target['view'], $entryName, $target['pid'], null, $entryName);
return true;
}
private static function resolveSavedEntryName($extractData)
{
$entryName = trim((string) $extractData->GetChildVal('name'));
if ($entryName !== '') {
return $entryName;
}
$holderValue = trim((string) $extractData->Get(CNode::FLD_VAL));
return $holderValue;
}
private static function resolveSavedEntryRoute($request, $tid)
{
switch ($tid) {
case 'V_TOPD':
case 'V_BASE':
return ['view' => 'vh_', 'pid' => 'base'];
case 'T_TOPD':
return ['view' => 'tp_', 'pid' => 'mbr'];
case 'ADM_L_GENERAL':
return ['view' => 'al_', 'pid' => 'lg'];
case 'L_GENERAL':
case 'L_GENERAL_NEW':
return [
'view' => (self::resolveMutationView($request) === 'al') ? 'al_' : 'sl_',
'pid' => 'lg',
];
case 'LT_GENERAL_NEW':
return ['view' => 'sl4_', 'pid' => 'ltg'];
case 'LB_GENERAL_NEW':
return ['view' => 'lb_', 'pid' => 'lbgeneral'];
case 'LB4_GENERAL_NEW':
return ['view' => 'lb4_', 'pid' => 'lb4general'];
}
return null;
}
private static function resolveMutationView($request)
{
$disp = $request->GetMutationDisplay();
if ($disp === null || !is_object($disp)) {
return '';
}
if (method_exists($disp, 'GetRouteState')) {
$rs = $disp->GetRouteState();
if ($rs !== null && method_exists($rs, 'GetView')) {
return (string) $rs->GetView();
}
}
if (method_exists($disp, 'GetView')) {
return (string) $disp->GetView();
}
return '';
}
private static function shouldMarkChangedAfterSave($request, $extractData)
{
$tid = self::resolveMutationTableId($request);
@@ -24,6 +24,7 @@ class CValidation
protected $_request;
protected $_go_flag;
protected $_messages = [];
public function __construct()
{
@@ -34,6 +35,7 @@ class CValidation
{
$this->_request = $request;
$this->_go_flag = 1;
$this->_messages = [];
$tbl = $request->GetTable();
$tid = $request->GetTid();
@@ -63,10 +65,7 @@ class CValidation
if ($needCheck) {
$this->validateAttr($attr, $dlayer);
}
if (($tid == 'V_TOPD' || $tid == 'V_BASE') && $attr->_type == 'vhname') {
$updatedViewName = ($dlayer == null) ? null : $dlayer->Get(CNode::FLD_VAL);
$hasUpdatedViewName = true;
}
$this->updateValidationRouteContext($tid, $attr, $dlayer, $updatedViewName, $hasUpdatedViewName);
}
}
@@ -75,12 +74,76 @@ class CValidation
// if 0 , make it always point to curr page
if ($this->_go_flag <= 0) {
if ($this->_go_flag < 0) {
$extracted->SetErr('Input error detected. Please resolve the error(s). ');
}
$status = $this->_go_flag;
$messages = $this->_messages;
$this->_request = null;
return new ConfigValidationResult($extracted, $updatedViewName, $hasUpdatedViewName);
$this->_messages = [];
return new ConfigValidationResult($extracted, $updatedViewName, $hasUpdatedViewName, $status, $messages);
}
protected function addValidationMessage($type, $text, $title = '')
{
$this->_messages[] = [
'type' => $type,
'title' => $title,
'text' => $text,
];
}
protected function updateValidationRouteContext($tid, $attr, $dlayer, &$updatedViewName, &$hasUpdatedViewName)
{
if ($dlayer == null || is_array($dlayer)) {
return;
}
if ($this->_request == null) {
return;
}
$value = $dlayer->Get(CNode::FLD_VAL);
if (($tid == 'V_TOPD' || $tid == 'V_BASE') && $attr->_type == 'vhname') {
$updatedViewName = $value;
$hasUpdatedViewName = true;
if (method_exists($this->_request, 'SetViewName')) {
$this->_request->SetViewName($value);
}
return;
}
if (in_array($tid, [
'T_TOPD',
'L_GENERAL',
'L_GENERAL_NEW',
'LT_GENERAL',
'LT_GENERAL_NEW',
'ADM_L_GENERAL',
'LB_GENERAL',
'LB_GENERAL_NEW',
'LB4_GENERAL',
'LB4_GENERAL_NEW',
], true)
&& $attr->GetKey() == 'name'
&& ($attr->_type == 'name' || $attr->_type == 'vhname')) {
$updatedViewName = $value;
$hasUpdatedViewName = true;
if (method_exists($this->_request, 'SetViewName')) {
$this->_request->SetViewName($value);
}
return;
}
if (($tid == 'V_TOPD' || $tid == 'V_BASE') && $attr->GetKey() == 'vhRoot' && $value !== null && $value !== ''
&& method_exists($this->_request, 'SetVHRoot')) {
$this->_request->SetVHRoot(PathTool::GetAbsFile(
$value,
'SR',
$this->_request->GetViewName()
));
}
}
protected function setValid($res)
@@ -388,7 +451,8 @@ class CValidation
if (($type == 'path' && !is_dir($absname)) || ($type == 'file' && !is_file($absname))) {
$err = $type . ' ' . htmlspecialchars($absname) . ' does not exist.';
if ($this->allow_create($attr, $absname)) {
$err .= ' <button type="submit" name="file_create" value="' . htmlspecialchars($attr->GetKey(), ENT_QUOTES) . '" class="lst-btn lst-btn--secondary lst-btn--xs">CLICK TO CREATE</button>';
$err .= ' <input type="hidden" name="a" value="s">';
$err .= ' <button type="submit" name="file_create" value="' . htmlspecialchars($attr->GetKey(), ENT_QUOTES) . '" class="lst-btn lst-btn--danger lst-btn--xs">CLICK TO CREATE</button>';
} else {
$err .= ' Please create manually.';
}
@@ -540,9 +604,15 @@ class CValidation
if ($res == -1 && isset($_POST['file_create']) && $_POST['file_create'] == $attr->GetKey() && $this->allow_create($attr, $path)) {
if (PathTool::createFile($path, $err, $attr->GetKey())) {
$err = "$path has been created successfully.";
$this->addValidationMessage(
'success',
htmlspecialchars($path, ENT_QUOTES) . ' has been created successfully. Click Save to apply this configuration.'
);
$err = null;
return 0;
}
$res = 0; // make it always point to curr page
$res = -1;
}
return $res;
@@ -639,6 +709,9 @@ class CValidation
$err = 'Fail to find $VH_ROOT';
return -1;
}
if (substr($vhroot, -1, 1) !== '/') {
$vhroot .= '/';
}
$path = $vhroot . substr($path, 9);
} elseif ($s == '$') {
$err = 'only accept absolute path or path relative to $SERVER_ROOT or $VH_ROOT: ' . $path;
@@ -111,6 +111,11 @@ class ConfigValidationRequest
return $this->_viewName;
}
public function SetViewName($viewName)
{
$this->_viewName = $viewName;
}
public function GetCurrentRef()
{
return $this->_currentRef;
@@ -131,6 +136,11 @@ class ConfigValidationRequest
return $this->_vhRoot;
}
public function SetVHRoot($vhRoot)
{
$this->_vhRoot = $vhRoot;
}
public function GetTableLocation()
{
return $this->_tableLocation;
@@ -4,15 +4,23 @@ namespace LSWebAdmin\Config\Validation;
class ConfigValidationResult
{
const STATUS_ERROR = -1;
const STATUS_STOP = 0;
const STATUS_OK = 1;
private $_extracted;
private $_viewName;
private $_hasViewNameUpdate;
private $_status;
private $_messages;
public function __construct($extracted, $viewName = null, $hasViewNameUpdate = false)
public function __construct($extracted, $viewName = null, $hasViewNameUpdate = false, $status = self::STATUS_OK, $messages = [])
{
$this->_extracted = $extracted;
$this->_viewName = $viewName;
$this->_hasViewNameUpdate = $hasViewNameUpdate;
$this->_status = (int) $status;
$this->_messages = is_array($messages) ? $messages : [];
}
public function GetExtracted()
@@ -22,7 +30,17 @@ class ConfigValidationResult
public function HasErr()
{
return ($this->_extracted != null && $this->_extracted->HasErr());
return ($this->_status < self::STATUS_STOP || ($this->_extracted != null && $this->_extracted->HasErr()));
}
public function ShouldStopSave()
{
return ($this->_status == self::STATUS_STOP);
}
public function GetMessages()
{
return $this->_messages;
}
public function GetViewName()
@@ -12,14 +12,15 @@ class AdminCommandClient
private $_lastError = '';
public function sendCommand($cmd)
public function sendCommand($cmd, $timeout = self::COMMAND_IO_TIMEOUT_SEC)
{
$sock = $this->openAuthenticatedSocket($cmd);
if (!$sock) {
return false;
}
if (!$this->setSocketTimeout($sock, SO_RCVTIMEO, self::COMMAND_IO_TIMEOUT_SEC, 'cmd ' . trim($cmd) . ' failed to set receive timeout on admin socket')) {
$readTimeout = ((int) $timeout > 0) ? (int) $timeout : self::COMMAND_IO_TIMEOUT_SEC;
if (!$this->setSocketTimeout($sock, SO_RCVTIMEO, $readTimeout, 'cmd ' . trim($cmd) . ' failed to set receive timeout on admin socket')) {
socket_close($sock);
return false;
}
@@ -426,7 +426,6 @@ class DTblDefBase
'ext_retryTimeout' => self::NewIntAttr('retryTimeout', DMsg::ALbl('l_retrytimeout'), false, 0),
'ext_respBuffer' => self::NewSelAttr('respBuffer', DMsg::ALbl('l_respbuffer'), ['0' => DMsg::ALbl('o_no'), '1' => DMsg::ALbl('o_yes'), '2' => DMsg::ALbl('o_nofornph')], false),
'ext_persistConn' => self::NewBoolAttr('persistConn', DMsg::ALbl('l_persistconn')),
'ext_autoStart' => self::NewSelAttr('autoStart', DMsg::ALbl('l_autostart'), ['2' => DMsg::ALbl('o_thrucgidaemon'), '0' => DMsg::ALbl('o_no')], false),
'ext_path' => self::NewPathAttr('path', DMsg::ALbl('l_command'), 'file1', 3, 'x', true, 'extAppPath'),
'ext_backlog' => self::NewIntAttr('backlog', DMsg::ALbl('l_backlog'), true, 1, 100),
'ext_instances' => self::NewIntAttr('instances', DMsg::ALbl('l_instances'), true, 0, 1000),
@@ -1874,12 +1873,6 @@ class DTblDefBase
$rules,
];
}
if ($type == 'charset') {
return [
self::NewTextAttr('addDefaultCharset', DMsg::ALbl('l_adddefaultcharset'), 'charset'),
$this->_attrs['enableIpGeo']
];
}
if ($type == 'uri') {
return [
$this->_attrs['ctx_uri'],
@@ -2,8 +2,6 @@
namespace LSWebAdmin\Product\Base;
use LSWebAdmin\I18n\DMsg;
abstract class ProductBase
{
protected static $instances = [];
@@ -79,35 +77,7 @@ abstract class ProductBase
protected function detectAvailableVersion()
{
$releasefile = $this->getServerRootPath('autoupdate/release');
if ($releasefile === '') {
return '';
}
$releasefilecb = $releasefile . 'cb';
$newver = '';
$rel0 = '';
$rel1 = '';
if (is_file($releasefilecb)) {
$rel = trim(file_get_contents($releasefilecb));
$rel0 = $this->extractReleaseVersion($rel);
if ($this->version != $rel0) {
$newver = $rel . ' (' . DMsg::UIStr('note_curbranch') . ') ';
}
}
if (is_file($releasefile)) {
$rel = trim(file_get_contents($releasefile));
$rel1 = $this->extractReleaseVersion($rel);
if ($this->version != $rel1 && $rel0 != $rel1) {
$newver .= $rel;
}
}
return $newver;
return '';
}
protected function extractReleaseVersion($release)
@@ -120,6 +90,22 @@ abstract class ProductBase
return $release;
}
protected function readReleaseFile($relativePath)
{
$releaseFile = $this->getServerRootPath($relativePath);
if ($releaseFile === '' || !is_file($releaseFile)) {
return '';
}
return trim((string) file_get_contents($releaseFile));
}
protected function isNewRelease($release)
{
$version = $this->extractReleaseVersion($release);
return ($release !== '' && $version !== '' && $this->version != $version);
}
public static function extractBuildDisplay($versionOutput)
{
if (!is_string($versionOutput) || $versionOutput === '') {
@@ -1,173 +0,0 @@
<?php
namespace LSWebAdmin\Product\Base;
use LSWebAdmin\Auth\CAuthorizer;
use LSWebAdmin\Controller\AdminCommandClient;
use LSWebAdmin\I18n\DMsg;
use LSWebAdmin\Product\Current\Service;
abstract class VersionManagerBase
{
const ACTION_UPGRADE = 'upgrade';
const ACTION_SWITCH = 'switchTo';
const ACTION_REMOVE = 'remove';
abstract protected function getProduct();
abstract protected function downloadReleaseArchive($version);
protected function buildUpgradeCommand($version)
{
return 'upgrade:' . $version;
}
public function getViewData()
{
$product = $this->getProduct();
return [
'product_name' => $product->getProductName(),
'edition' => method_exists($product, 'getEdition') ? $product->getEdition() : '',
'version' => $product->getVersion(),
'current_build' => method_exists($product, 'getCurrentBuild') ? $product->getCurrentBuild() : '',
'release_log_url' => method_exists($product, 'getReleaseLogUrl') ? $product->getReleaseLogUrl() : '',
'available_releases' => method_exists($product, 'getAvailableReleases') ? $product->getAvailableReleases() : [],
'installed_releases' => method_exists($product, 'getInstalledReleases') ? $product->getInstalledReleases() : [],
'license' => Service::LicenseInfo(),
'has_validate_license' => $this->supportsValidateLicense(),
];
}
public function perform($action, $version = '')
{
switch ((string) $action) {
case self::ACTION_UPGRADE:
return $this->upgrade($version);
case self::ACTION_SWITCH:
return $this->switchTo($version);
case self::ACTION_REMOVE:
return $this->remove($version);
case 'validatelicense':
if ($this->supportsValidateLicense()) {
return $this->validateLicense();
}
return null;
}
return null;
}
protected function supportsValidateLicense()
{
return false;
}
protected function upgrade($version)
{
if (!$this->isValidVersion($version)) {
return $this->errorMessage(DMsg::UIStr('service_versionmanager_invalidversion'));
}
if (!$this->downloadReleaseArchive($version)) {
return $this->errorMessage(DMsg::UIStr('service_versionmanager_downloadfailed') . ' ' . $version);
}
return $this->runCommand(
$this->buildUpgradeCommand($version),
DMsg::UIStr('service_versionmanager_upgrade_started') . ' ' . $version
);
}
protected function switchTo($version)
{
if (!$this->isValidVersion($version)) {
return $this->errorMessage(DMsg::UIStr('service_versionmanager_invalidversion'));
}
return $this->runCommand(
'mgrver:' . $version,
DMsg::UIStr('service_versionmanager_switch_started') . ' ' . $version
);
}
protected function remove($version)
{
if (!$this->isValidVersion($version)) {
return $this->errorMessage(DMsg::UIStr('service_versionmanager_invalidversion'));
}
return $this->runCommand(
'mgrver:-d ' . $version,
DMsg::UIStr('service_versionmanager_remove_started') . ' ' . $version
);
}
protected function validateLicense()
{
return $this->runCommand(
'ValidateLicense',
DMsg::UIStr('service_versionmanager_validate_started')
);
}
protected function runCommand($command, $successMessage)
{
if (!$this->sendCommand($command)) {
return $this->errorMessage(DMsg::UIStr('service_versionmanager_commandfailed'));
}
$this->waitForStatusChange();
$this->getProduct()->refreshVersion();
return [
'type' => 'success',
'text' => $successMessage,
];
}
protected function sendCommand($command)
{
CAuthorizer::singleton()->Reauthenticate();
return $this->getAdminCommandClient()->sendCommand($command . "\n");
}
protected function waitForStatusChange()
{
Service::WaitForStatusChange();
}
protected function getAdminCommandClient()
{
return new AdminCommandClient();
}
protected function getServerRoot()
{
if (defined('SERVER_ROOT') && SERVER_ROOT !== '') {
return SERVER_ROOT;
}
if (isset($_SERVER['LS_SERVER_ROOT']) && is_string($_SERVER['LS_SERVER_ROOT']) && $_SERVER['LS_SERVER_ROOT'] !== '') {
return rtrim($_SERVER['LS_SERVER_ROOT'], '/') . '/';
}
return '';
}
protected function isValidVersion($version)
{
return (preg_match('/^\d+\.\d+(\.\d+)?(RC\d+)?$/', (string) $version) === 1);
}
protected function errorMessage($text)
{
return [
'type' => 'danger',
'text' => $text,
];
}
}
@@ -43,6 +43,10 @@ class DTblDef extends DTblDefBase
protected function loadCommonOptions()
{
parent::loadCommonOptions();
$this->_options['extAutoStart'] = [
'2' => DMsg::ALbl('o_thrucgidaemon'),
'0' => DMsg::ALbl('o_no')
];
$this->_options['scriptHandler'] = $this->getSharedScriptHandlerOptions([
'module' => DMsg::ALbl('l_modulehandler')
]);
@@ -64,12 +68,25 @@ class DTblDef extends DTblDefBase
protected function loadCommonAttrs()
{
parent::loadCommonAttrs();
$this->_attrs['ext_autoStart'] = self::NewSelAttr('autoStart', DMsg::ALbl('l_autostart'), $this->_options['extAutoStart'], false);
$param = self::NewTextAreaAttr('param', DMsg::ALbl('l_moduleparams'), 'cust', true, 4, 'modParams', 1, 1);
$param->SetFlag(DAttr::BM_RAWDATA);
$this->_attrs['mod_params'] = $param;
$this->_attrs['mod_enabled'] = self::NewBoolAttr('ls_enabled', DMsg::ALbl('l_enablehooks'), true, 'moduleEnabled');
}
protected function get_ctx_attrs($type)
{
if ($type == 'charset') {
return [
self::NewTextAttr('addDefaultCharset', DMsg::ALbl('l_adddefaultcharset'), 'charset'),
$this->_attrs['enableIpGeo']
];
}
return parent::get_ctx_attrs($type);
}
protected function add_S_PROCESS($id) //keep
{
$attrs = [
@@ -2,6 +2,7 @@
namespace LSWebAdmin\Product\Ows;
use LSWebAdmin\I18n\DMsg;
use LSWebAdmin\Product\Base\ProductBase;
class Product extends ProductBase
@@ -18,4 +19,30 @@ class Product extends ProductBase
'bin/lshttpd',
];
}
protected function detectAvailableVersion()
{
$newVersion = '';
$currentBranchVersion = '';
$currentBranchRelease = $this->readReleaseFile('autoupdate/releasecb');
if ($currentBranchRelease !== '') {
$currentBranchVersion = $this->extractReleaseVersion($currentBranchRelease);
if ($this->version != $currentBranchVersion) {
$newVersion = $currentBranchRelease . ' (' . DMsg::UIStr('note_curbranch') . ') ';
}
}
$latestRelease = $this->readReleaseFile('autoupdate/release');
if ($latestRelease !== '') {
$latestVersion = $this->extractReleaseVersion($latestRelease);
if ($this->version != $latestVersion && $currentBranchVersion != $latestVersion) {
$newVersion .= $latestRelease;
}
}
return $newVersion;
}
}
+2 -2
View File
@@ -37,7 +37,7 @@ class ConfRouteParser
if (($pos = strpos($mid, '_')) > 0) {
$view = substr($mid, 0, $pos + 1);
$viewName = substr($mid, $pos + 1);
if ($pid == '' || $view == 'sl' || $view == 'sl_' || $view == 'al' || $view == 'al_' || $view == 'lb' || $view == 'lb_' || $view == 'lb4_' || $pid == 'base' || $pid == 'mbr') {
if ($pid == '' || $view == 'sl' || $view == 'sl_' || $view == 'sl4_' || $view == 'al' || $view == 'al_' || $view == 'lb' || $view == 'lb_' || $view == 'lb4_' || $pid == 'base' || $pid == 'mbr') {
$ref = $viewName;
}
} else {
@@ -125,7 +125,7 @@ class ConfRouteParser
return substr($ref, 0, $pos);
}
if ($view == 'sl_' || $view == 'al_' || $view == 'lb_' || $view == 'lb4_' || $pid == 'base' || $pid == 'mbr') {
if ($view == 'sl_' || $view == 'sl4_' || $view == 'al_' || $view == 'lb_' || $view == 'lb4_' || $pid == 'base' || $pid == 'mbr') {
return $viewName;
}
+11 -1
View File
@@ -127,6 +127,16 @@ class ConfRouteState
$this->_mid = substr($this->_mid, 0, $pos) . $suffix;
}
public function SetViewRoute($view, $viewName, $pid, $tid = null, $ref = null)
{
$this->_view = $view;
$this->_viewName = $viewName;
$this->_mid = (is_string($view) && substr($view, -1) === '_') ? $view . $viewName : $view;
$this->_pid = $pid;
$this->_tid = $tid;
$this->_ref = $ref;
}
public function IsViewAction()
{
if (!is_string($this->_act) || $this->_act === '') {
@@ -175,7 +185,7 @@ class ConfRouteState
if ($this->_ref && ($pos = strrpos($this->_ref, '`')) !== false) {
$this->_ref = substr($this->_ref, 0, $pos);
} elseif ($this->_view == 'sl_' || $this->_view == 'al_' || $this->_pid == 'base' || $this->_pid == 'mbr') {
} elseif ($this->_view == 'sl_' || $this->_view == 'sl4_' || $this->_view == 'al_' || $this->_view == 'lb_' || $this->_view == 'lb4_' || $this->_pid == 'base' || $this->_pid == 'mbr') {
$this->_ref = $this->_viewName;
} else {
$this->_ref = null;
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
+26 -4
View File
@@ -23,11 +23,21 @@ echo UI::content_header('layout-dashboard', DMsg::UIStr('menu_dashboard'), '', f
<article>
<div class="lst-dashboard-statusbar" id="dashboard_statusbar">
<div class="lst-dashboard-statusbar__group lst-dashboard-statusbar__group--version">
<?php if (UI::SupportsVersionManager()) { ?>
<span id="dash_version_value" class="lst-dashboard-statusbar__value lst-dashboard-statusbar__version">
<span class="lst-dashboard-statusbar__version-product">&mdash;</span>
<a class="lst-dashboard-statusbar__version-link" href="index.php?view=versionmanager"></a>
</span>
<?php } else { ?>
<span id="dash_version_value" class="lst-dashboard-statusbar__value">&mdash;</span>
<?php if ($dashboardNewVersion !== '' && $dashboardNewVersionUrl !== '') { ?>
<a class="lst-dashboard-statusbar__link" href="<?php echo UIBase::EscapeAttr($dashboardNewVersionUrl); ?>"<?php echo $dashboardNewVersionExternal ? ' rel="noopener noreferrer" target="_blank"' : ''; ?>><?php echo UIBase::Escape(DMsg::UIStr('note_newver') . ': ' . $dashboardNewVersion); ?></a>
<?php } ?>
<span class="lst-dashboard-statusbar__meta"><?php echo ($dashboardBuildDisplay !== '') ? UIBase::Escape($dashboardBuildDisplay) : ''; ?></span>
<?php if ($dashboardNewVersion !== '' && $dashboardNewVersionUrl !== '') { ?>
<a class="lst-dashboard-statusbar__link" href="<?php echo UIBase::EscapeAttr($dashboardNewVersionUrl); ?>"<?php echo $dashboardNewVersionExternal ? ' rel="noopener noreferrer" target="_blank"' : ''; ?>>
<span class="lst-dashboard-statusbar__link-label"><?php echo UIBase::Escape(DMsg::UIStr('note_newver')); ?></span>
<span class="lst-dashboard-statusbar__link-value"><?php echo UIBase::Escape($dashboardNewVersion); ?></span>
</a>
<?php } ?>
</div>
<div class="lst-dashboard-statusbar__group lst-dashboard-statusbar__group--pid">
<span id="dash_pid_dot" class="lst-dashboard-statusdot is-off" aria-hidden="true"></span>
@@ -555,7 +565,10 @@ echo UI::content_header('layout-dashboard', DMsg::UIStr('menu_dashboard'), '', f
var pidValue,
running,
uptime,
loadValue;
loadValue,
versionValue,
versionProduct,
versionLink;
if (!data) {
return;
@@ -574,7 +587,16 @@ echo UI::content_header('layout-dashboard', DMsg::UIStr('menu_dashboard'), '', f
$("#dash_load_value").text(loadValue);
if (data.version_display || data.product_name) {
$("#dash_version_value").text(data.version_display || data.product_name || "");
versionValue = $("#dash_version_value");
versionProduct = versionValue.find(".lst-dashboard-statusbar__version-product");
versionLink = versionValue.find(".lst-dashboard-statusbar__version-link");
if (versionProduct.length && versionLink.length) {
versionProduct.text(data.product_name || "");
versionLink.text(data.version || "").attr("hidden", data.version ? null : "hidden");
} else {
versionValue.text(data.version_display || data.product_name || "");
}
}
}
+34 -9
View File
@@ -5,6 +5,31 @@ use LSWebAdmin\Product\Current\Product;
use LSWebAdmin\Product\Current\UI;
use LSWebAdmin\UI\UIBase;
if (!function_exists('lstAssetHref')) {
function lstAssetHref($href)
{
if ($href === '' || $href[0] !== '/') {
return $href;
}
$paths = [];
if (defined('SERVER_ROOT') && SERVER_ROOT !== '') {
$paths[] = rtrim(SERVER_ROOT, '/') . '/admin/html' . $href;
}
$paths[] = dirname(__DIR__, 2) . $href;
$paths[] = dirname(__DIR__, 4) . $href;
foreach ($paths as $path) {
if (is_file($path)) {
return $href . '?v=' . filemtime($path);
}
}
return $href;
}
}
if (!$no_main_header) { ?>
<!DOCTYPE html>
<html lang="en-us">
@@ -55,13 +80,13 @@ $consoleName = $product->getWebAdminConsoleName();
<link rel="shortcut icon" href="/res/img/favicon/favicon.ico" type="image/x-icon">
<link rel="icon" href="/res/img/favicon/favicon.ico" type="image/x-icon">
<link rel="stylesheet" type="text/css" media="screen" href="/res/css/googlefonts.css">
<link rel="stylesheet" type="text/css" media="screen" href="/res/css/lst-theme.css">
<link rel="stylesheet" type="text/css" media="screen" href="/res/css/lst-product-accent.css">
<link rel="stylesheet" type="text/css" media="screen" href="/res/css/lst-components.css">
<link rel="stylesheet" type="text/css" media="screen" href="/res/css/lst-shell.css">
<?php if ($no_main_header) { ?>
<link rel="stylesheet" type="text/css" media="screen" href="/res/css/lst-page-login.css">
<link rel="stylesheet" type="text/css" media="screen" href="<?php echo UIBase::EscapeAttr(lstAssetHref('/res/css/googlefonts.css')); ?>">
<link rel="stylesheet" type="text/css" media="screen" href="<?php echo UIBase::EscapeAttr(lstAssetHref('/res/css/lst-theme.css')); ?>">
<link rel="stylesheet" type="text/css" media="screen" href="<?php echo UIBase::EscapeAttr(lstAssetHref('/res/css/lst-product-accent.css')); ?>">
<link rel="stylesheet" type="text/css" media="screen" href="<?php echo UIBase::EscapeAttr(lstAssetHref('/res/css/lst-components.css')); ?>">
<link rel="stylesheet" type="text/css" media="screen" href="<?php echo UIBase::EscapeAttr(lstAssetHref('/res/css/lst-shell.css')); ?>">
<?php if ($no_main_header) { ?>
<link rel="stylesheet" type="text/css" media="screen" href="<?php echo UIBase::EscapeAttr(lstAssetHref('/res/css/lst-page-login.css')); ?>">
<?php } else {
$lstPageStyles = [];
if (isset($view)) {
@@ -74,7 +99,7 @@ $consoleName = $product->getWebAdminConsoleName();
}
foreach ($lstPageStyles as $lstPageStyleHref) {
?>
<link rel="stylesheet" type="text/css" media="screen" href="<?php echo UIBase::EscapeAttr($lstPageStyleHref); ?>">
<link rel="stylesheet" type="text/css" media="screen" href="<?php echo UIBase::EscapeAttr(lstAssetHref($lstPageStyleHref)); ?>">
<?php
}
} ?>
@@ -83,7 +108,7 @@ $consoleName = $product->getWebAdminConsoleName();
<meta name="apple-mobile-web-app-status-bar-style" content="black">
<meta name="robots" content="noindex">
<script src="/res/js/libs/jquery-4.0.0.min.js"></script>
<script src="<?php echo UIBase::EscapeAttr(lstAssetHref('/res/js/libs/jquery-4.0.0.min.js')); ?>"></script>
<script type="text/javascript">
(function () {
var lstPasswordShowLabel = <?php echo json_encode(DMsg::ALbl('btn_showpassword')); ?>;
+3 -2
View File
@@ -1,6 +1,7 @@
<?php
use LSWebAdmin\I18n\DMsg;
use LSWebAdmin\UI\UIBase;
?>
<script type="text/javascript">
@@ -84,8 +85,8 @@ use LSWebAdmin\I18n\DMsg;
}
</script>
<script src="/res/js/lst-app.js"></script>
<script src="/res/js/lucide.min.js"></script>
<script src="<?php echo UIBase::EscapeAttr(lstAssetHref('/res/js/lst-app.js')); ?>"></script>
<script src="<?php echo UIBase::EscapeAttr(lstAssetHref('/res/js/lucide.min.js')); ?>"></script>
<script>
if (typeof lucide !== 'undefined') {
document.addEventListener('DOMContentLoaded', function() {
+1 -1
View File
@@ -1010,7 +1010,7 @@ installation()
util_cpdir "$SDIR_OWN" $DOC_MOD add-ons
util_cpdir "$CONF_OWN" $DOC_MOD share/autoindex
util_ccpfile "$SDIR_OWN" $EXEC_MOD fcgi-bin/lsperld.fpl fcgi-bin/RackRunner.rb fcgi-bin/lsnode.js
util_ccpfile "$SDIR_OWN" $EXEC_MOD fcgi-bin/lsperld.fpl fcgi-bin/RackRunner.rb fcgi-bin/lsnode.js fcgi-bin/lsnodesm.js
util_cpfile "$SDIR_OWN" $EXEC_MOD fcgi-bin/RailsRunner.rb fcgi-bin/RailsRunner.rb.2.3
util_cpfile "$SDIR_OWN" $EXEC_MOD lsns/bin/common.py lsns/bin/lshostexec lsns/bin/lscgctl lsns/bin/lscgstats lsns/bin/lspkgctl lsns/bin/lsnsctl lsns/bin/unmount_ns lsns/bin/cmd_ns lsns/bin/lssetup
+120 -2
View File
@@ -22,6 +22,7 @@
#endif
#include "lscgid.h"
#include "nspersist.h"
#include <lsdef.h>
#include <util/fdpass.h>
@@ -176,6 +177,15 @@ static char s_sDataBuf[16384];
static int s_fdControl = -1;
static int s_ns_enabled = 0;
#define NS_WATCHER_RESTART_DELAY_INITIAL 5
#define NS_WATCHER_RESTART_DELAY_MAX 300
#define NS_WATCHER_RESTART_STABLE 60
static int s_ns_watcher_restart_delay =
NS_WATCHER_RESTART_DELAY_INITIAL;
static time_t s_ns_watcher_next_restart = 0;
static time_t s_ns_watcher_last_start = 0;
static int s_ns_watcher_disabled = 0;
static void log_cgi_error(const char *func, const char *arg,
const char *explanation)
@@ -1006,7 +1016,10 @@ static int new_conn(int fd)
pid_t pid;
pid = fork();
if (!pid)
{
nspersist_socket_watcher_forked_child();
child_main(fd);
}
close(fd);
if (pid > 0)
pid = 0;
@@ -1019,6 +1032,96 @@ static int s_got_sigchild = 0;
static void processSigchild();
static int start_socket_watcher();
static void schedule_socket_watcher_restart(int reset_if_stable,
int immediate_allowed);
static void schedule_socket_watcher_after_reap(int status);
static int start_socket_watcher()
{
if (!s_ns_enabled || s_ns_watcher_disabled)
return 0;
pid_t pid = nspersist_start_socket_watcher();
if (pid > 0)
{
s_ns_watcher_last_start = time(NULL);
s_ns_watcher_next_restart = 0;
DEBUG_MESSAGE("socket watcher running as pid %d\n", (int)pid);
return 0;
}
if (pid == 0)
{
s_ns_watcher_disabled = 1;
s_ns_watcher_next_restart = 0;
DEBUG_MESSAGE("socket watcher disabled; unsupported by this host\n");
return 0;
}
schedule_socket_watcher_restart(0, 0);
return -1;
}
static void schedule_socket_watcher_restart(int reset_if_stable,
int immediate_allowed)
{
if (!s_ns_enabled || s_ns_watcher_disabled || !s_run)
return;
time_t now = time(NULL);
if (reset_if_stable && s_ns_watcher_last_start &&
now - s_ns_watcher_last_start >= NS_WATCHER_RESTART_STABLE)
{
s_ns_watcher_restart_delay = NS_WATCHER_RESTART_DELAY_INITIAL;
}
int delay = s_ns_watcher_restart_delay;
if (immediate_allowed &&
s_ns_watcher_restart_delay == NS_WATCHER_RESTART_DELAY_INITIAL)
{
delay = 0;
}
s_ns_watcher_next_restart = now + delay;
DEBUG_MESSAGE("socket watcher restart scheduled in %d seconds "
"(next backoff %d seconds)\n", delay,
s_ns_watcher_restart_delay);
if (s_ns_watcher_restart_delay < NS_WATCHER_RESTART_DELAY_MAX)
{
s_ns_watcher_restart_delay *= 2;
if (s_ns_watcher_restart_delay > NS_WATCHER_RESTART_DELAY_MAX)
s_ns_watcher_restart_delay = NS_WATCHER_RESTART_DELAY_MAX;
}
}
static void schedule_socket_watcher_after_reap(int status)
{
int reset_if_stable = 1;
int immediate_allowed = 0;
if (WIFSIGNALED(status))
{
int sig_num = WTERMSIG(status);
DEBUG_MESSAGE("socket watcher killed by signal %d\n", sig_num);
immediate_allowed = 1;
}
else if (WIFEXITED(status))
{
DEBUG_MESSAGE("socket watcher exited with status %d\n",
WEXITSTATUS(status));
}
else
{
DEBUG_MESSAGE("socket watcher exited with status 0x%x\n", status);
}
schedule_socket_watcher_restart(reset_if_stable, immediate_allowed);
}
static int run(int fdServerSock)
@@ -1045,6 +1148,8 @@ static int run(int fdServerSock)
}
if (s_got_sigchild)
processSigchild();
if (s_ns_watcher_next_restart && time(NULL) >= s_ns_watcher_next_restart)
start_socket_watcher();
}
return 0;
}
@@ -1083,6 +1188,11 @@ static void processSigchild()
// continue;
break;
}
if (nspersist_socket_watcher_reaped(status[0]))
{
schedule_socket_watcher_after_reap(status[1]);
continue;
}
if (s_fdControl != -1)
write(s_fdControl, status, sizeof(status));
if (WIFSIGNALED(status[1]))
@@ -1170,6 +1280,16 @@ int lscgid_main(int fd, char *argv0, const char *secret, char *pSock)
}
s_ns_enabled = HttpServerConfig::getInstance().getNS();
if (s_ns_enabled)
{
DEBUG_MESSAGE("Namespace container is enabled.\n");
/* Start the host-side socket watcher that monitors MySQL
* (and other) socket bounces and remounts stale bind mounts
* inside persisted namespaces. */
start_socket_watcher();
}
else
DEBUG_MESSAGE("Namespace container is NOT enabled\n");
#endif
#endif
@@ -1195,5 +1315,3 @@ int lscgid_main(int fd, char *argv0, const char *secret, char *pSock)
}
return ret;
}
+39
View File
@@ -86,6 +86,7 @@ SetupOp s_setupOp_all[] =
int s_setupOp_all_size = sizeof(s_setupOp_all);
int s_listenPid = 0;
int s_listenPidStatus = 0;
pid_t s_ns_watcher_pid = 0;
SetupOp s_SetupOp_default[] =
@@ -2906,6 +2907,7 @@ static int do_ns(lscgid_t *pCGI, SetupOp *setupOp, int persisted)
pid_t parent_pid;
mode_t old_umask = -1;
char *old_cwd = NULL;
int host_root_fd = -1;
DEBUG_MESSAGE("Entering do_ns, uid: %d, ppid: %d\n", getuid(), getppid());
debug_ops(setupOp);
@@ -2938,6 +2940,14 @@ static int do_ns(lscgid_t *pCGI, SetupOp *setupOp, int persisted)
old_cwd = get_current_dir_name ();
/* Grab an O_PATH handle to the host root BEFORE the mount namespace is
* modified so we can still reach host files after pivot_root. */
host_root_fd = open("/", O_PATH);
if (host_root_fd == -1)
{
DEBUG_MESSAGE("do_ns: open(/) for host_root_fd: %s\n", strerror(errno));
}
if (!rc)
rc = build_mount_namespace(pCGI);
@@ -2947,6 +2957,14 @@ static int do_ns(lscgid_t *pCGI, SetupOp *setupOp, int persisted)
if (!rc)
rc = cleanup_oldroot(pCGI, persisted);
/* After the namespace is fully built, check for stale socket bind mounts
* and re-establish any that were replaced on the host side. */
if (!rc && host_root_fd != -1)
nspersist_remount_stale_sockets(host_root_fd);
if (host_root_fd != -1)
close(host_root_fd);
//if (pCGI->m_oom_score_adjust != LS_OOM_NO_ADJ)
// apply_oom_score_adj(pCGI->m_oom_score_adjust);
@@ -3206,6 +3224,27 @@ void ns_setverbose_callback(verbose_callback_t callback)
void ns_done()
{
DEBUG_MESSAGE("ns_done\n");
if (s_ns_watcher_pid > 0)
{
kill(s_ns_watcher_pid, SIGTERM);
/* Bound the wait: poll for up to ~2 s, then SIGKILL and reap. */
int waited_ms = 0;
while (waited_ms < 2000)
{
pid_t r = waitpid(s_ns_watcher_pid, NULL, WNOHANG);
if (r == s_ns_watcher_pid || r == -1)
break;
usleep(50000); /* 50 ms */
waited_ms += 50;
}
if (waitpid(s_ns_watcher_pid, NULL, WNOHANG) == 0)
{
kill(s_ns_watcher_pid, SIGKILL);
waitpid(s_ns_watcher_pid, NULL, 0);
}
s_ns_watcher_pid = 0;
}
nspersist_done();
if (s_proc_fd != -1)
{
File diff suppressed because it is too large Load Diff
+62 -3
View File
@@ -119,11 +119,11 @@ int lock_persist_vh_file(int report, int lock_type);
/**
* @fn unlock_close_persist_vh_file
* @brief Unlocks and closes a lock file created by is_persisted.
* @param[in] delete. Whether to delete the file (closed by the last)
* @param[in] del. Whether to delete the file (closed by the last)
* @param[out] none
* @return 0 if no error, or an error code.
**/
int unlock_close_persist_vh_file(int delete);
int unlock_close_persist_vh_file(int del);
/**
* @fn persist_do_ns
@@ -251,6 +251,66 @@ void persist_exit_child(char *desc, int rc);
int nspersist_setvhost(char *vhenv);
/**
* @fn nspersist_remount_stale_sockets
* @brief Check for bind-mounted socket files that have become stale (the
* host-side socket was deleted and recreated) and re-establish them.
* @param[in] host_root_fd An O_PATH descriptor opened on "/" in the initial
* mount namespace BEFORE setns()/unshare() was called.
* @return None.
**/
void nspersist_remount_stale_sockets(int host_root_fd);
/**
* @fn nspersist_start_socket_watcher
* @brief Start the host-side socket watcher daemon that monitors all
* persisted namespaces' bind-mounted sockets and remounts stale ones
* when host-side sockets are bounced (e.g. MySQL restart).
*
* Called once from the lscgid main daemon during startup. Forks a
* dedicated watcher process that lives in the host mount namespace
* (full visibility of the host filesystem) and uses inotify to detect
* socket changes. When changes occur, it forks a helper that
* setns()'s into each persisted namespace to perform the remount.
*
* @return The pid of the watcher process on success, -1 on error.
* The caller should kill(pid, SIGTERM) during shutdown to stop it.
**/
pid_t nspersist_start_socket_watcher(void);
/**
* @fn nspersist_socket_watcher_forked_child
* @brief Clear inherited watcher state in forked request children. The
* watcher belongs to the lscgid daemon process, so request children must not
* signal or reap it from ns_done().
* @return None.
**/
void nspersist_socket_watcher_forked_child(void);
/**
* @fn nspersist_socket_watcher_reaped
* @brief Clear watcher state when the lscgid parent reaps the watcher child.
*
* @param[in] pid The child pid returned by waitpid().
* @return 1 if pid was the active watcher and was cleared, 0 otherwise.
**/
int nspersist_socket_watcher_reaped(pid_t pid);
/**
* @fn nspersist_register_socket_mount
* @brief Called by ns.c when a socket bind mount is created during
* namespace setup, so the host-side watcher knows what to monitor.
*
* @param[in] uid The user id (used to identify the persisted namespace).
* @param[in] persist_num The persist number (matches /var/lsns/uid/N).
* @param[in] host_path The host-side path of the socket (source).
* @param[in] ns_path The namespace-side bind mount target.
* @return None.
**/
void nspersist_register_socket_mount(uid_t uid, int persist_num,
const char *host_path,
const char *ns_path);
extern mount_flags_data_t s_mount_flags_data[];
#ifdef __cplusplus
@@ -259,4 +319,3 @@ extern mount_flags_data_t s_mount_flags_data[];
#endif // Linux
#endif // _NS_OPTS_H
+2 -2
View File
@@ -43,7 +43,7 @@ ExtWorkerConfig::ExtWorkerConfig(const char *pName)
, m_iMaxIdleTime(INT_MAX)
, m_iKeepAliveTimeout(INT_MAX)
, m_iSelfManaged(1)
, m_iStartByServer(0)
, m_iStartByServer(EXTAPP_AUTOSTART_OFF)
, m_iRefAddr(0)
, m_iDaemonSuEXEC(0)
, m_iDropCaps(0)
@@ -66,7 +66,7 @@ ExtWorkerConfig::ExtWorkerConfig()
, m_iMaxIdleTime(INT_MAX)
, m_iKeepAliveTimeout(INT_MAX)
, m_iSelfManaged(1)
, m_iStartByServer(0)
, m_iStartByServer(EXTAPP_AUTOSTART_OFF)
, m_iRefAddr(0)
, m_iDaemonSuEXEC(0)
, m_iDropCaps(0)
-1
View File
@@ -27,7 +27,6 @@
#define EXTAPP_AUTOSTART_OFF 0
#define EXTAPP_AUTOSTART_NORMAL 1
#define EXTAPP_AUTOSTART_CGID 2
#define EXTAPP_AUTOSTART_ASYNC_CGID 3
#define EXTAPP_RUNONSTART_OFF 0
#define EXTAPP_RUNONSTART_ON 1
+1 -1
View File
@@ -484,7 +484,7 @@ int LocalWorker::workerExec(LocalWorkerConfig &config, int fd)
//Since we already in the chroot jail, do not use the global jail path
//If start external app with lscgid, apply global chroot path,
// as lscgid is not inside chroot
if (config.getStartByServer() == 2)
if (config.getStartByServer() == EXTAPP_AUTOSTART_CGID)
{
if (!pChroot)
pChroot = procConfig.getChroot();
+4 -4
View File
@@ -475,7 +475,7 @@ int ExtAppRegistry::configVhostOwnPhp(HttpVHost *pVHost)
char appName[256];
const char *pUri;
char buf[MAX_PATH_LEN];
int iAutoStart = 0;
int iAutoStart = EXTAPP_AUTOSTART_OFF;
const char *pPath = NULL;
ExtWorker *pWorker = NULL;
ExtWorkerConfig *pConfig = NULL;
@@ -714,7 +714,7 @@ ExtWorker *ExtAppRegistry::configExtApp(const XmlNode *pNode, const HttpVHost *p
const char *pType;
const char *pUri;
char buf[MAX_PATH_LEN];
int iAutoStart = 0;
int iAutoStart = EXTAPP_AUTOSTART_OFF;
const char *pPath = NULL;
ExtWorker *pWorker = NULL;
ExtWorkerConfig *pConfig = NULL;
@@ -815,9 +815,9 @@ ExtWorker *ExtAppRegistry::configExtApp(const XmlNode *pNode, const HttpVHost *p
if ((iType == EA_FCGI) || (iType == EA_LOGGER) || (iType == EA_LSAPI) || (iType == EA_SCGI) || (iType == EA_UWSGI))
{
if (iType == EA_LOGGER)
iAutoStart = 1;
iAutoStart = EXTAPP_AUTOSTART_CGID;
else if (iType == EA_SCGI || iType == EA_UWSGI)
iAutoStart = 0;
iAutoStart = EXTAPP_AUTOSTART_OFF;
else
iAutoStart = ConfigCtx::getCurConfigCtx()->getLongValue(pNode, "autoStart",
0, 2, 1);
+2 -2
View File
@@ -542,7 +542,7 @@ int HttpReq::processUnpackedHeaders(UnpackedHeaders *header)
return result;
m_ver = HTTP_1_1;
if (m_method == HttpMethod::HTTP_POST)
if (m_method == HttpMethod::HTTP_POST || m_method == HttpMethod::HTTP_PATCH)
m_lEntityLength = LSI_BODY_SIZE_UNKNOWN;
keepAlive(0);
@@ -3164,7 +3164,7 @@ const char *HttpReq::getCfRealIpHeader(char *name, int &len)
char HttpReq::getRewriteLogLevel() const
{
if (LS_LOG_ENABLED(log4cxx::Level::DBG_LOW))
if (LS_LOG_ENABLED(log4cxx::Level::DBG_HIGH))
return 9;
else
return m_pVHost->getRewriteLogLevel();
+1 -1
View File
@@ -1604,7 +1604,7 @@ void HttpVHost::setDefaultConfig(LocalWorkerConfig &config,
config.setAppPath(pBinPath);
config.setBackLog(pDefault->getBackLog());
config.setSelfManaged(1);
config.setStartByServer(EXTAPP_AUTOSTART_ASYNC_CGID);
config.setStartByServer(EXTAPP_AUTOSTART_CGID);
config.setMaxConns(maxConns);
if (config.isDetached())
+2 -2
View File
@@ -2448,7 +2448,7 @@ LocalWorker *HttpServerImpl::createAdminPhpApp(const char *pChroot,
pFcgiApp->getConfig().setAppPath(&pchPHPBin[iChrootLen]);
pFcgiApp->getConfig().setBackLog(100);
pFcgiApp->getConfig().setSelfManaged(0);
pFcgiApp->getConfig().setStartByServer(1);
pFcgiApp->getConfig().setStartByServer(EXTAPP_AUTOSTART_CGID);
pFcgiApp->setMaxConns(4);
pFcgiApp->getConfig().setKeepAliveTimeout(30);
pFcgiApp->getConfig().setInstances(4);
@@ -4282,7 +4282,7 @@ int HttpServerImpl::configIpToLoc(const XmlNode *pNode)
int HttpServerImpl::configLsrecaptchaWorker(const XmlNode *pNode)
{
const char *pName = "lsrecaptcha";
int iAutoStart = 1;
int iAutoStart = EXTAPP_AUTOSTART_CGID;
int backlog = 10;
int instances = 1;
int iMaxConns = 35;
+1 -1
View File
@@ -91,7 +91,7 @@
/***
* Do not change the below format, it will be set correctly while packing the code
*/
#define BUILDTIME "built: Sat Apr 25 14:44:33 UTC 2026"
#define BUILDTIME "built: Thu May 7 15:34:11 UTC 2026"
static const char s_pVersionFull[] = "LiteSpeed/" PACKAGE_VERSION
" Open (" LS_MODULE_VERSION_INFO_ONELINE ") BUILD (" BUILDTIME ")";
+31
View File
@@ -414,6 +414,37 @@ int SslContext::configOptions(SslContextConfig *pConfig)
pConfig->m_iProtocol);
setProtocol(pConfig->m_iProtocol);
}
#ifdef OPENSSL_IS_BORINGSSL
static const uint16_t s_signAlgsNoSha1[] =
{
SSL_SIGN_ED25519,
SSL_SIGN_RSA_PSS_RSAE_SHA256,
SSL_SIGN_RSA_PSS_RSAE_SHA384,
SSL_SIGN_RSA_PSS_RSAE_SHA512,
SSL_SIGN_ECDSA_SECP256R1_SHA256,
SSL_SIGN_ECDSA_SECP384R1_SHA384,
SSL_SIGN_ECDSA_SECP521R1_SHA512,
SSL_SIGN_RSA_PKCS1_SHA256,
SSL_SIGN_RSA_PKCS1_SHA384,
SSL_SIGN_RSA_PKCS1_SHA512,
};
LS_DBG_L("[SSL:%p] Disable SHA1 for handshake signing/verifying algorithms.\n", this);
if (!SSL_CTX_set_signing_algorithm_prefs(m_pCtx, s_signAlgsNoSha1,
sizeof(s_signAlgsNoSha1) / sizeof(s_signAlgsNoSha1[0])))
{
LS_ERROR("[SSL:%p] Failed to set handshake signing algorithms: %s",
this, SslError().what());
return LS_FAIL;
}
if (!SSL_CTX_set_verify_algorithm_prefs(m_pCtx, s_signAlgsNoSha1,
sizeof(s_signAlgsNoSha1) / sizeof(s_signAlgsNoSha1[0])))
{
LS_ERROR("[SSL:%p] Failed to set handshake verifying algorithms: %s",
this, SslError().what());
return LS_FAIL;
}
#endif
if (pConfig->m_iEnableECDHE)
{
LS_DBG_L("[SSL:%p] Enable ECDHE\n", this);