Hacked By AnonymousFox
Current Path : /usr/share/cagefs/ |
|
Current File : //usr/share/cagefs/cagefs_ispmanager_lib.py |
# -*- coding: utf-8 -*-
# ISP Manager function library
#
# Copyright © Cloud Linux GmbH & Cloud Linux Software, Inc 2010-2019 All Rights Reserved
#
# Licensed under CLOUD LINUX LICENSE AGREEMENT
# http://cloudlinux.com/docs/LICENSE.TXT
#
#Redistribution and use in source and binary forms, with or without
#modification, are permitted provided that the following conditions
#are met:
# * Redistributions of source code must retain the above copyright
# notice, this list of conditions and the following disclaimer.
# * Redistributions in binary form must reproduce the above
# copyright notice, this list of conditions and the following
# disclaimer in the documentation and/or other materials provided
# with the distribution.
# * The names of its contributors may not be used to endorse or
# promote products derived from this software without specific
# prior written permission.
#
#THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
#"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
#LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
#FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
#COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
#INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
#BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
#LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
#CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
#LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
#ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
#POSSIBILITY OF SUCH DAMAGE.
#
# Module functionality:
# Create php.ini files for DA PHP version selector
# Create symlink to user data directory
#
from __future__ import absolute_import
from __future__ import division
from __future__ import print_function
from __future__ import unicode_literals
from future import standard_library
standard_library.install_aliases()
from builtins import *
import os
import pwd
import shutil
import subprocess
import cagefslib
import sys
import cldetectlib as detect
from cagefsctl import get_list_of_users, cagefs_is_enabled, save_dir_exists, get_exclude_user_list, get_min_uid, MIN_UID
import secureio
from clcommon import clcaptain
from clcommon.utils import ExternalProgramFailed
from clcommon.utils import mod_makedirs
def install_ispmanager_directory_exclude():
"""
Install exclude .cagefs folder from backup
:return: None
"""
# Only for ISP Manager
detect.getCP()
if not detect.is_ispmanager():
return
if detect.CP_VERSION.startswith('4'):
# ISP Manager v4
isp_command_list = ['/usr/local/ispmgr/sbin/mgrctl', 'backupplan']
try:
result = cagefslib.Execute(isp_command_list, check_return_code=False, exit_on_error=False).split('\n')
for line in result:
if line.find('id=') != -1:
plan_id = str(line.split('name=')[0].replace('id=', '').strip())
isp_command_list.extend(['.content.edit plid=' + plan_id, 'sok=ok', 'type=exclude',
'module=file','filedata=.cagefs'])
cagefslib.Execute(isp_command_list, check_return_code=False, exit_on_error=False)
except OSError as e:
secureio.print_error('Failed to set exclude dir for ISPManager 4:', str(e))
else:
# ISP Manager v5
if detect.ispmanager5_is_master():
# ISP5 Master
try:
cagefs_exclude_is_found = False
exclude_files_list = list()
# Search .cagefs in excludes
isp_command_list = ['/usr/local/mgr5/sbin/mgrctl', '-m', 'ispmgr', 'backup2.settings']
result = cagefslib.Execute(isp_command_list, check_return_code=False, exit_on_error=False).split('\n')
for line in result:
if line.startswith('exclude_files'):
# line as:
# exclude_files=data/.cagefs data/mod-tmp data/somedir
l_parts = line.strip().split('=')
if len(l_parts) != 2:
continue
# l_parts[1] as 'data/.cagefs data/mod-tmp data/somedir'
exclude_files_list = l_parts[1].split(' ')
# if .cagefs absent in exclude list, add it
for exclude_file in exclude_files_list:
if '.cagefs' in exclude_file:
cagefs_exclude_is_found = True
break
break
if not cagefs_exclude_is_found:
# .cagefs not found in excludes, add it
add_line = ' '.join(exclude_files_list) + ' ' + 'data/.cagefs'
add_line = add_line.strip()
isp_command_list.extend(['exclude_files=%s' % add_line, 'sok=ok'])
cagefslib.Execute(isp_command_list, check_return_code=False, exit_on_error=False).split('\n')
except (OSError, IOError,) as e:
secureio.print_error('Failed to set exclude dir for ISPManager 5:', str(e))
def create_php_cgi_etc(filename, php_ini_path):
if os.path.isfile(filename):
# check file content
content = cagefslib.read_file(filename)
if content[0] == '#!/bin/bash\n':
for line in content:
parts = line.strip().split()
if (len(parts) == 4) and (parts[0] == 'exec') and (parts[1] == '/usr/bin/php-cgi') and\
(parts[2] == '-c') and (parts[3] == php_ini_path):
return
dirpath = os.path.dirname(filename)
if not os.path.lexists(dirpath):
mod_makedirs(dirpath, 0o755)
f = open(filename, 'w')
f.write('#!/bin/bash\n')
f.write('exec /usr/bin/php-cgi -c ' + php_ini_path + '\n')
f.close()
# make it executable
os.chmod(filename, 0o755)
# Call from cagefs
def configure_selector_for_ispmanager():
# Only for ISP Manager v4.x
detect.getCP()
if not detect.is_ispmanager() or not detect.CP_VERSION.startswith('4'):
return
ISP_MANAGER_CONF_FILE = '/usr/local/ispmgr/etc/ispmgr.conf'
if not os.path.isfile(ISP_MANAGER_CONF_FILE):
return
# 1. Read php.ini path from native conf
cagefslib.read_native_conf()
if not cagefslib.config_loaded:
return
content = cagefslib.orig_binaries
php_ini_path = '/etc/php.ini'
if 'php.ini' in content:
php_ini_path = content['php.ini']
# 2. Create /usr/local/bin/php-cgi-etc
script_file = '/usr/local/bin/php-cgi-etc'
create_php_cgi_etc(script_file, php_ini_path)
# 3. Create in CageFs skeleton (/usr/share/cagefs-skeleton/usr/local/bin/php-cgi-etc)
if os.path.isdir('/usr/share/cagefs-skeleton'):
create_php_cgi_etc('/usr/share/cagefs-skeleton/usr/local/bin/php-cgi-etc', php_ini_path)
# 4. Read /usr/local/ispmgr/etc/ispmgr.conf
content = cagefslib.read_file(ISP_MANAGER_CONF_FILE)
i = 0
is_found = False
old_path = ''
for line in content:
parts = line.strip().split()
if (len(parts) == 3) and (parts[0] == 'path') and (parts[1] == 'phpcgibinary'):
old_path = parts[2]
is_found = True
break
i += 1
if is_found:
# directive found, check path in it
if old_path != script_file:
content[i] = 'path phpcgibinary ' + script_file + '\n'
cagefslib.write_file(ISP_MANAGER_CONF_FILE, content)
else:
# directive not found, append it
f = open(ISP_MANAGER_CONF_FILE, 'a')
f.write('path phpcgibinary ' + script_file + '\n')
f.close()
# 5. Clear ISP Manager's cache and restart it
shutil.rmtree('/usr/local/ispmgr/var/.xmlcache/ispmgr', True)
p = subprocess.Popen(['killall', 'ispmgr'], shell=False, stdin=open('/dev/null'), stdout=subprocess.PIPE,
stderr=subprocess.STDOUT, close_fds=True)
p.wait()
# 6. Create user php wrappers
#!/usr/local/bin/php-cgi-etc - for alt versions
#!/usr/bin/php-cgi - for native
if (not cagefs_is_enabled()) or save_dir_exists():
cagefs_enabled_users = []
else:
cagefs_enabled_users = get_list_of_users(True)
exclude_list = get_exclude_user_list()
get_min_uid()
min_uid = MIN_UID
pw = pwd.getpwall()
for user_data in pw:
if user_data.pw_uid < min_uid or user_data.pw_name in exclude_list:
continue
is_user_in_cagefs = user_data.pw_name in cagefs_enabled_users
ispmanager_create_user_wrapper_detect_php_ver(user_data, is_user_in_cagefs, True)
# Creates user wrapper dependently user in cagefs or not
# This function for single-user operations in cagefsctl
def ispmanager_create_user_wrapper_detect_php_ver(user_data, is_user_in_cagefs, is_write_log=False):
# Only for ISP Manager v4.x
detect.getCP()
if not detect.is_ispmanager() or not detect.CP_VERSION.startswith('4'):
return
if not is_user_in_cagefs:
user_php_ver = "native"
else:
user_php_ver = cagefslib.get_php_version_for_user(user_data.pw_name)
if user_php_ver is None:
return
ispmanager_create_user_wrapper(user_data.pw_name, user_php_ver, user_data, is_write_log)
# Create user wrapper for ISP.
# Call also from cl-selector with username and PHP ver only
def ispmanager_create_user_wrapper(username, user_php_ver, user_data=None, is_write_log=False):
# Only for ISP Manager v4.x
detect.getCP()
if not detect.is_ispmanager() or not detect.CP_VERSION.startswith('4'):
return
# 1. Check rights
if user_data is None:
user_data = pwd.getpwnam(username)
uid = user_data.pw_uid
gid = user_data.pw_gid
process_uid = os.geteuid()
if process_uid != uid:
# we work not as the specified user, drop permissions required
drop_perm = True
else:
# we run under user, drop not needed
uid = None
gid = None
drop_perm = False
# 2. Create wrapper with the proper content (if it isn't present) in user dir
user_wrapper_file = os.path.join(user_data.pw_dir, 'php-bin/php')
write_wrapper(user_wrapper_file, user_php_ver, uid, gid, drop_perm, is_write_log)
# 3. Create wrapper with the proper content (if it isn't present) in /var/www/php-bin/[user]
PATH_MASK = "/var/www/php-bin/%s"
user_wrapper_file = os.path.join(PATH_MASK % username, "php")
write_wrapper(user_wrapper_file, user_php_ver, uid, gid, drop_perm, is_write_log)
# Creates user wrapper
def write_wrapper(wrapper_filename, user_php_ver, uid, gid, drop_perm, is_write_log):
def create_wrapper():
if drop_perm:
secureio.write_file_secure([s_wrapper_contents], wrapper_filename, uid, gid, drop_perm, 0o555, is_write_log)
else:
try:
clcaptain.write(wrapper_filename, s_wrapper_contents)
os.chmod(wrapper_filename, 0o555)
except (OSError, IOError, ExternalProgramFailed) as e:
secureio.logging("Error: failed to write file " + wrapper_filename + ": " + str(e), secureio.SILENT_FLAG, 1, is_write_log)
dir_name = os.path.dirname(wrapper_filename)
if os.path.isdir(dir_name):
# wrapper backup file
bak_wrapper_filename = wrapper_filename+'.cagefs.bak'
# determine wrapper content
if user_php_ver == 'native':
s_wrapper_contents = "#!/usr/bin/php-cgi\n"
else:
s_wrapper_contents = "#!/usr/local/bin/php-cgi-etc\n"
if not os.path.lexists(wrapper_filename):
# there is no wrapper, create it
create_wrapper()
return
# wrapper already present
try:
content = secureio.read_file_secure(wrapper_filename, uid, gid, False, is_write_log)
except (OSError, IOError) as e:
secureio.logging("Error: failed to read file " + wrapper_filename + ": " + str(e), secureio.SILENT_FLAG, 1, is_write_log)
return
if not content:
# empty wrapper, create it
create_wrapper()
return
# change wrapper content according to required PHP version
if content[0].strip() == "#!/usr/local/bin/php-cgi-etc":
# alt version wrapper found
if user_php_ver == 'native':
# and switch to native
if os.path.lexists(bak_wrapper_filename) and os.path.getsize(bak_wrapper_filename) > 0:
# backup copy present and is not empty, restore it to wrapper
rename_file_secure(bak_wrapper_filename, wrapper_filename, uid, gid, write_log=is_write_log)
else:
# if backup copy is absent or empty, create our native wrapper
create_wrapper()
else:
# native wrapper found
if user_php_ver != 'native':
# switch to alt version
# make backup copy old wrapper: copy php to php.cagefs.bak
if drop_perm:
secureio.write_file_secure(content, bak_wrapper_filename, uid, gid, drop_perm, 0o444, is_write_log)
else:
try:
clcaptain.write(bak_wrapper_filename, ''.join(content))
os.chmod(bak_wrapper_filename, 0o444)
except (OSError, IOError, ExternalProgramFailed) as e:
secureio.logging("Error: failed to write file " + bak_wrapper_filename + ": " + str(e), secureio.SILENT_FLAG, 1, is_write_log)
# create wrapper
create_wrapper()
# rename file with drop permissions
def rename_file_secure(old_filename, new_filename, uid=None, gid=None, exit_on_error=False, write_log=True):
drop_perm = (uid is not None) and (gid is not None)
if drop_perm:
secureio.set_user_perm(uid, gid)
is_error = False
# if backup present, rename it to wrapper
try:
os.rename(old_filename, new_filename)
os.chmod(new_filename, 0o555)
except (OSError, IOError) as e:
secureio.logging("Error: failed to rename " + old_filename + " to " + new_filename +
": " + str(e), secureio.SILENT_FLAG, 1, write_log)
is_error = True
if drop_perm:
secureio.set_root_perm()
if is_error and exit_on_error:
sys.exit(1)
return is_error
Hacked By AnonymousFox1.0, Coded By AnonymousFox