1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
|
static void SetACLPrivileges();
static bool ReadSacl=false;
#ifndef SFX_MODULE
void ExtractACL20(Archive &Arc,const wchar *FileName)
{
SetACLPrivileges();
if (Arc.BrokenHeader)
{
uiMsg(UIERROR_ACLBROKEN,Arc.FileName,FileName);
ErrHandler.SetErrorCode(RARX_CRC);
return;
}
if (Arc.EAHead.Method<0x31 || Arc.EAHead.Method>0x35 || Arc.EAHead.UnpVer>VER_PACK)
{
uiMsg(UIERROR_ACLUNKNOWN,Arc.FileName,FileName);
ErrHandler.SetErrorCode(RARX_WARNING);
return;
}
ComprDataIO DataIO;
Unpack Unpack(&DataIO);
Unpack.Init(0x10000,false);
Array<byte> UnpData(Arc.EAHead.UnpSize);
DataIO.SetUnpackToMemory(&UnpData[0],Arc.EAHead.UnpSize);
DataIO.SetPackedSizeToRead(Arc.EAHead.DataSize);
DataIO.EnableShowProgress(false);
DataIO.SetFiles(&Arc,NULL);
DataIO.UnpHash.Init(HASH_CRC32,1);
Unpack.SetDestSize(Arc.EAHead.UnpSize);
Unpack.DoUnpack(Arc.EAHead.UnpVer,false);
if (Arc.EAHead.EACRC!=DataIO.UnpHash.GetCRC32())
{
uiMsg(UIERROR_ACLBROKEN,Arc.FileName,FileName);
ErrHandler.SetErrorCode(RARX_CRC);
return;
}
SECURITY_INFORMATION si=OWNER_SECURITY_INFORMATION|GROUP_SECURITY_INFORMATION|
DACL_SECURITY_INFORMATION;
if (ReadSacl)
si|=SACL_SECURITY_INFORMATION;
SECURITY_DESCRIPTOR *sd=(SECURITY_DESCRIPTOR *)&UnpData[0];
int SetCode=SetFileSecurity(FileName,si,sd);
if (!SetCode)
{
uiMsg(UIERROR_ACLSET,Arc.FileName,FileName);
ErrHandler.SysErrMsg();
ErrHandler.SetErrorCode(RARX_WARNING);
}
}
#endif
void ExtractACL(Archive &Arc,const wchar *FileName)
{
Array<byte> SubData;
if (!Arc.ReadSubData(&SubData,NULL))
return;
SetACLPrivileges();
SECURITY_INFORMATION si=OWNER_SECURITY_INFORMATION|GROUP_SECURITY_INFORMATION|
DACL_SECURITY_INFORMATION;
if (ReadSacl)
si|=SACL_SECURITY_INFORMATION;
SECURITY_DESCRIPTOR *sd=(SECURITY_DESCRIPTOR *)&SubData[0];
int SetCode=SetFileSecurity(FileName,si,sd);
if (!SetCode)
{
wchar LongName[NM];
if (GetWinLongPath(FileName,LongName,ASIZE(LongName)))
SetCode=SetFileSecurity(LongName,si,sd);
}
if (!SetCode)
{
uiMsg(UIERROR_ACLSET,Arc.FileName,FileName);
ErrHandler.SysErrMsg();
ErrHandler.SetErrorCode(RARX_WARNING);
}
}
void SetACLPrivileges()
{
static bool InitDone=false;
if (InitDone)
return;
if (SetPrivilege(SE_SECURITY_NAME))
ReadSacl=true;
SetPrivilege(SE_RESTORE_NAME);
InitDone=true;
}
bool SetPrivilege(LPCTSTR PrivName)
{
bool Success=false;
HANDLE hToken;
if (OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES, &hToken))
{
TOKEN_PRIVILEGES tp;
tp.PrivilegeCount = 1;
tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
if (LookupPrivilegeValue(NULL,PrivName,&tp.Privileges[0].Luid) &&
AdjustTokenPrivileges(hToken, FALSE, &tp, 0, NULL, NULL) &&
GetLastError() == ERROR_SUCCESS)
Success=true;
CloseHandle(hToken);
}
return Success;
}
|