Как сменить владельца файла на другого пользователя без получения SeRestorePrivilege? - PullRequest
0 голосов
/ 03 марта 2020

Если процесс имеет SeRestorePrivilege, он может изменить владельца файла с помощью win32security.SetNamedSecurityInfo. В соответствии с Windows документацией API ,

SeRestorePrivilege:

заставляет систему предоставлять все права доступа для записи любому файлу независимо от ACL, указанного для файл. Любой запрос доступа, кроме записи, все еще оценивается с помощью ACL. Следующие права доступа предоставляются, если эта привилегия удерживается: WRITE_DA C, WRITE_OWNER, ACCESS_SYSTEM_SECURITY, FILE_GENERIC_WRITE, FILE_ADD_FILE, FILE_ADD_SUBDIRECTORY, DELETE

право доступа ко всем упомянутым правам на все упомянутые права на все упомянутые права , но изменение владельца не выполняется с ошибкой 1307: «Этот идентификатор безопасности не может быть назначен владельцем данного объекта». Почему?

Код:

import ntsecuritycon
import win32security
import win32api
import sys
import os

# grant access rights of SeRestorePrivilege
def simulate_se_restore_privilege(path):
    sd = win32security.GetNamedSecurityInfo(path, win32security.SE_FILE_OBJECT, win32security.OWNER_SECURITY_INFORMATION)
    owner_sid = sd.GetSecurityDescriptorOwner()

    dacl = win32security.ACL()
    dacl.SetEntriesInAcl([
        {'AccessPermissions': ntsecuritycon.WRITE_DAC
            | ntsecuritycon.WRITE_OWNER
            | ntsecuritycon.ACCESS_SYSTEM_SECURITY
            | ntsecuritycon.FILE_GENERIC_WRITE
            | ntsecuritycon.FILE_ADD_FILE
            | ntsecuritycon.FILE_ADD_SUBDIRECTORY
            | ntsecuritycon.DELETE,
         'AccessMode': win32security.GRANT_ACCESS,
         'Inheritance': 0,
         'Trustee': {
             'MultipleTrustee': None,
             'MultipleTrusteeOperation': 0,
             'TrusteeForm': win32security.TRUSTEE_IS_SID,
             'TrusteeType': win32security.TRUSTEE_IS_UNKNOWN,
             'Identifier': owner_sid,
         }
        }
    ])

    win32security.SetNamedSecurityInfo(
        path,
        win32security.SE_FILE_OBJECT,
        win32security.DACL_SECURITY_INFORMATION,
        None,
        None,
        dacl,
        None,
    )

def enable_se_restore_privilege():
    tok = win32security.OpenProcessToken(
        win32api.GetCurrentProcess(), win32security.TOKEN_ADJUST_PRIVILEGES | win32security.TOKEN_QUERY
    )
    luid = win32security.LookupPrivilegeValue(None, win32security.SE_RESTORE_NAME)
    new_state = [(luid, win32security.SE_PRIVILEGE_ENABLED)]
    win32security.AdjustTokenPrivileges(tok, 0, new_state)
    win32api.CloseHandle(tok)

def change_ownership(path):
    win32security.SetNamedSecurityInfo(
        path,
        win32security.SE_FILE_OBJECT,
        win32security.OWNER_SECURITY_INFORMATION,
        win32security.ConvertStringSidToSid("S-1-0-0"),
        None,
        None,
        None,
    )


path = sys.argv[1]
try:
    os.unlink(path)
except OSError:
    pass

with open(path, "w"):
    pass

print("Adding access rights from SeRestorePrivilege")
simulate_se_restore_privilege(path)
try:
    change_ownership(path)
except Exception as e:
    print(f"Changing ownership failed: {e}")

print("Enabling SeRestorePrivilege")
enable_se_restore_privilege()
change_ownership(path)
print("Changing ownership succeeded")

Вывод в приподнятой консоли:

> python .\chown.py file
Adding access rights from SeRestorePrivilege
Changing ownership failed: (1307, 'SetNamedSecurityInfo', 'This security ID may not be assigned as the owner of this object.')
Enabling SeRestorePrivilege
Changing ownership succeeded

1 Ответ

0 голосов
/ 17 марта 2020

В соответствии с документацией SeRestorePrivilege:

Кроме того, эта привилегия позволяет вам установить любого допустимого SID пользователя или группы в качестве владельца файла.

...