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
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
|
// Copyright 2008, Google Inc.
// All rights reserved.
//
// 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.
// * Neither the name of Google Inc. nor the names of its
// contributors may 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.
#ifndef SANDBOX_TOOLS_FINDER_FINDER_H__
#define SANDBOX_TOOLS_FINDER_FINDER_H__
#include "sandbox/src/restricted_token_utils.h"
#include "sandbox/tools/finder/ntundoc.h"
// Type of stats that we calculate during the Scan operation
enum Stats {
READ = 0, // Number of objects with read access
WRITE, // Number of objects with write access
ALL, // Number of objects with r/w access
PARSE, // Number of objects parsed
BROKEN, // Number of errors while parsing the objects
SIZE_STATS // size of the enum
};
const int kScanRegistry = 0x01;
const int kScanFileSystem = 0x02;
const int kScanKernelObjects = 0x04;
const int kTestForRead = 0x01;
const int kTestForWrite = 0x02;
const int kTestForAll = 0x04;
#define FS_ERR L"FILE-ERROR"
#define OBJ_ERR L"OBJ-ERROR"
#define REG_ERR L"REG_ERROR"
#define OBJ L"OBJ"
#define FS L"FILE"
#define REG L"REG"
// The impersonater class will impersonate a token when the object is created
// and revert when the object is going out of scope.
class Impersonater {
public:
Impersonater(HANDLE token_handle) {
if (token_handle)
::ImpersonateLoggedOnUser(token_handle);
};
~Impersonater() {
::RevertToSelf();
};
};
// The finder class handles the search of objects (file system, registry, kernel
// objects) on the system that can be opened by a restricted token. It can
// support multiple levels of restriction for the restricted token and can check
// for read, write or r/w access. It outputs the results to a file or stdout.
class Finder {
public:
Finder();
~Finder();
DWORD Init(sandbox::TokenLevel token_type, DWORD object_type,
DWORD access_type, FILE *file_output);
DWORD Scan();
private:
// Parses a file system path and perform an access check on all files and
// folder found.
// Returns ERROR_SUCCESS if the function succeeded, otherwise, it returns the
// win32 error code associated with the error.
DWORD ParseFileSystem(ATL::CString path);
// Parses a registry hive referenced by "key" and performs an access check on
// all subkeys found.
// Returns ERROR_SUCCESS if the function succeeded, otherwise, it returns the
// win32 error code associated with the error.
DWORD ParseRegistry(HKEY key, ATL::CString print_name);
// Parses the kernel namespace beginning at "path" and performs an access
// check on all objects found. However, only some object types are supported,
// all non supported objects are ignored.
// Returns ERROR_SUCCESS if the function succeeded, otherwise, it returns the
// win32 error code associated with the error.
DWORD ParseKernelObjects(ATL::CString path);
// Checks if "path" can be accessed with the restricted token.
// Returns the access granted.
DWORD TestFileAccess(ATL::CString path);
// Checks if the registry key with the path key\name can be accessed with the
// restricted token.
// print_name is only use for logging purpose.
// Returns the access granted.
DWORD TestRegAccess(HKEY key, ATL::CString name, ATL::CString print_name);
// Checks if the kernel object "path" of type "type" can be accessed with
// the restricted token.
// Returns the access granted.
DWORD TestKernelObjectAccess(ATL::CString path, ATL::CString type);
// Outputs information to the logfile
void Output(ATL::CString type, ATL::CString access, ATL::CString info) {
fprintf(file_output_, "\n%S;%S;%S", type.GetBuffer(), access.GetBuffer(),
info.GetBuffer());
};
// Output information to the log file.
void Output(ATL::CString type, DWORD error, ATL::CString info) {
fprintf(file_output_, "\n%S;0x%X;%S", type.GetBuffer(), error,
info.GetBuffer());
};
// Set func_to_call to the function pointer of the function used to handle
// requests for the kernel objects of type "type". If the type is not
// supported at the moment the function returns false and the func_to_call
// parameter is not modified.
bool GetFunctionForType(ATL::CString type, NTGENERICOPEN * func_to_call);
// Initializes the NT function pointers to be able to use all the needed
// functions in NTDDL.
// Returns ERROR_SUCCESS if the function succeeded, otherwise, it returns the
// win32 error code associated with the error.
DWORD InitNT();
// Calls func_to_call with the parameters desired_access, object_attributes
// and handle. func_to_call is a pointer to a function to open a kernel
// object.
NTSTATUS NtGenericOpen(ACCESS_MASK desired_access,
OBJECT_ATTRIBUTES *object_attributes,
NTGENERICOPEN func_to_call,
HANDLE *handle);
// Type of object to check for.
DWORD object_type_;
// Access to try.
DWORD access_type_;
// Output file for the results.
FILE * file_output_;
// Handle to the restricted token.
HANDLE token_handle_;
// Stats containing the number of operations performed on the different
// objects.
int filesystem_stats_[SIZE_STATS];
int registry_stats_[SIZE_STATS];
int kernel_object_stats_[SIZE_STATS];
};
#endif // SANDBOX_TOOLS_FINDER_FINDER_H__
|