OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 // This file contains unit tests for the job object. | 5 // This file contains unit tests for the job object. |
6 | 6 |
7 #include "base/win/scoped_process_information.h" | 7 #include "base/win/scoped_process_information.h" |
8 #include "sandbox/win/src/job.h" | 8 #include "sandbox/win/src/job.h" |
9 #include "testing/gtest/include/gtest/gtest.h" | 9 #include "testing/gtest/include/gtest/gtest.h" |
10 | 10 |
11 namespace sandbox { | 11 namespace sandbox { |
12 | 12 |
13 // Tests the creation and destruction of the job. | 13 // Tests the creation and destruction of the job. |
14 TEST(JobTest, TestCreation) { | 14 TEST(JobTest, TestCreation) { |
15 // Scope the creation of Job. | 15 // Scope the creation of Job. |
16 { | 16 { |
17 // Create the job. | 17 // Create the job. |
18 Job job; | 18 Job job; |
19 ASSERT_EQ(ERROR_SUCCESS, job.Init(JOB_LOCKDOWN, L"my_test_job_name", 0, 0)); | 19 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
| 20 job.Init(JOB_LOCKDOWN, L"my_test_job_name", 0, 0)); |
20 | 21 |
21 // check if the job exists. | 22 // check if the job exists. |
22 HANDLE job_handle = ::OpenJobObjectW(GENERIC_ALL, FALSE, | 23 HANDLE job_handle = ::OpenJobObjectW(GENERIC_ALL, FALSE, |
23 L"my_test_job_name"); | 24 L"my_test_job_name"); |
24 ASSERT_TRUE(job_handle != NULL); | 25 ASSERT_TRUE(job_handle != NULL); |
25 | 26 |
26 if (job_handle) | 27 if (job_handle) |
27 CloseHandle(job_handle); | 28 CloseHandle(job_handle); |
28 } | 29 } |
29 | 30 |
30 // Check if the job is destroyed when the object goes out of scope. | 31 // Check if the job is destroyed when the object goes out of scope. |
31 HANDLE job_handle = ::OpenJobObjectW(GENERIC_ALL, FALSE, L"my_test_job_name"); | 32 HANDLE job_handle = ::OpenJobObjectW(GENERIC_ALL, FALSE, L"my_test_job_name"); |
32 ASSERT_TRUE(job_handle == NULL); | 33 ASSERT_TRUE(job_handle == NULL); |
33 ASSERT_EQ(ERROR_FILE_NOT_FOUND, ::GetLastError()); | 34 ASSERT_EQ(static_cast<DWORD>(ERROR_FILE_NOT_FOUND), ::GetLastError()); |
34 } | 35 } |
35 | 36 |
36 // Tests the method "Take". | 37 // Tests the method "Take". |
37 TEST(JobTest, Take) { | 38 TEST(JobTest, Take) { |
38 base::win::ScopedHandle job_handle; | 39 base::win::ScopedHandle job_handle; |
39 // Scope the creation of Job. | 40 // Scope the creation of Job. |
40 { | 41 { |
41 // Create the job. | 42 // Create the job. |
42 Job job; | 43 Job job; |
43 ASSERT_EQ(ERROR_SUCCESS, job.Init(JOB_LOCKDOWN, L"my_test_job_name", 0, 0)); | 44 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
| 45 job.Init(JOB_LOCKDOWN, L"my_test_job_name", 0, 0)); |
44 | 46 |
45 job_handle = job.Take(); | 47 job_handle = job.Take(); |
46 ASSERT_TRUE(job_handle.IsValid()); | 48 ASSERT_TRUE(job_handle.IsValid()); |
47 } | 49 } |
48 | 50 |
49 // Check to be sure that the job is still alive even after the object is gone | 51 // Check to be sure that the job is still alive even after the object is gone |
50 // out of scope. | 52 // out of scope. |
51 HANDLE job_handle_dup = ::OpenJobObjectW(GENERIC_ALL, FALSE, | 53 HANDLE job_handle_dup = ::OpenJobObjectW(GENERIC_ALL, FALSE, |
52 L"my_test_job_name"); | 54 L"my_test_job_name"); |
53 ASSERT_TRUE(job_handle_dup != NULL); | 55 ASSERT_TRUE(job_handle_dup != NULL); |
54 | 56 |
55 // Remove all references. | 57 // Remove all references. |
56 if (job_handle_dup) | 58 if (job_handle_dup) |
57 ::CloseHandle(job_handle_dup); | 59 ::CloseHandle(job_handle_dup); |
58 | 60 |
59 job_handle.Close(); | 61 job_handle.Close(); |
60 | 62 |
61 // Check if the jbo is really dead. | 63 // Check if the jbo is really dead. |
62 job_handle_dup = ::OpenJobObjectW(GENERIC_ALL, FALSE, L"my_test_job_name"); | 64 job_handle_dup = ::OpenJobObjectW(GENERIC_ALL, FALSE, L"my_test_job_name"); |
63 ASSERT_TRUE(job_handle_dup == NULL); | 65 ASSERT_TRUE(job_handle_dup == NULL); |
64 ASSERT_EQ(ERROR_FILE_NOT_FOUND, ::GetLastError()); | 66 ASSERT_EQ(static_cast<DWORD>(ERROR_FILE_NOT_FOUND), ::GetLastError()); |
65 } | 67 } |
66 | 68 |
67 // Tests the ui exceptions | 69 // Tests the ui exceptions |
68 TEST(JobTest, TestExceptions) { | 70 TEST(JobTest, TestExceptions) { |
69 base::win::ScopedHandle job_handle; | 71 base::win::ScopedHandle job_handle; |
70 // Scope the creation of Job. | 72 // Scope the creation of Job. |
71 { | 73 { |
72 // Create the job. | 74 // Create the job. |
73 Job job; | 75 Job job; |
74 ASSERT_EQ(ERROR_SUCCESS, job.Init(JOB_LOCKDOWN, L"my_test_job_name", | 76 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
75 JOB_OBJECT_UILIMIT_READCLIPBOARD, 0)); | 77 job.Init(JOB_LOCKDOWN, L"my_test_job_name", |
| 78 JOB_OBJECT_UILIMIT_READCLIPBOARD, 0)); |
76 | 79 |
77 job_handle = job.Take(); | 80 job_handle = job.Take(); |
78 ASSERT_TRUE(job_handle.IsValid()); | 81 ASSERT_TRUE(job_handle.IsValid()); |
79 | 82 |
80 JOBOBJECT_BASIC_UI_RESTRICTIONS jbur = {0}; | 83 JOBOBJECT_BASIC_UI_RESTRICTIONS jbur = {0}; |
81 DWORD size = sizeof(jbur); | 84 DWORD size = sizeof(jbur); |
82 BOOL result = ::QueryInformationJobObject(job_handle.Get(), | 85 BOOL result = ::QueryInformationJobObject(job_handle.Get(), |
83 JobObjectBasicUIRestrictions, | 86 JobObjectBasicUIRestrictions, |
84 &jbur, size, &size); | 87 &jbur, size, &size); |
85 ASSERT_TRUE(result); | 88 ASSERT_TRUE(result); |
86 | 89 |
87 ASSERT_EQ(jbur.UIRestrictionsClass & JOB_OBJECT_UILIMIT_READCLIPBOARD, 0); | 90 ASSERT_EQ(0u, jbur.UIRestrictionsClass & JOB_OBJECT_UILIMIT_READCLIPBOARD); |
88 job_handle.Close(); | 91 job_handle.Close(); |
89 } | 92 } |
90 | 93 |
91 // Scope the creation of Job. | 94 // Scope the creation of Job. |
92 { | 95 { |
93 // Create the job. | 96 // Create the job. |
94 Job job; | 97 Job job; |
95 ASSERT_EQ(ERROR_SUCCESS, job.Init(JOB_LOCKDOWN, L"my_test_job_name", 0, 0)); | 98 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
| 99 job.Init(JOB_LOCKDOWN, L"my_test_job_name", 0, 0)); |
96 | 100 |
97 job_handle = job.Take(); | 101 job_handle = job.Take(); |
98 ASSERT_TRUE(job_handle.IsValid()); | 102 ASSERT_TRUE(job_handle.IsValid()); |
99 | 103 |
100 JOBOBJECT_BASIC_UI_RESTRICTIONS jbur = {0}; | 104 JOBOBJECT_BASIC_UI_RESTRICTIONS jbur = {0}; |
101 DWORD size = sizeof(jbur); | 105 DWORD size = sizeof(jbur); |
102 BOOL result = ::QueryInformationJobObject(job_handle.Get(), | 106 BOOL result = ::QueryInformationJobObject(job_handle.Get(), |
103 JobObjectBasicUIRestrictions, | 107 JobObjectBasicUIRestrictions, |
104 &jbur, size, &size); | 108 &jbur, size, &size); |
105 ASSERT_TRUE(result); | 109 ASSERT_TRUE(result); |
106 | 110 |
107 ASSERT_EQ(jbur.UIRestrictionsClass & JOB_OBJECT_UILIMIT_READCLIPBOARD, | 111 ASSERT_EQ(static_cast<DWORD>(JOB_OBJECT_UILIMIT_READCLIPBOARD), |
108 JOB_OBJECT_UILIMIT_READCLIPBOARD); | 112 jbur.UIRestrictionsClass & JOB_OBJECT_UILIMIT_READCLIPBOARD); |
109 } | 113 } |
110 } | 114 } |
111 | 115 |
112 // Tests the error case when the job is initialized twice. | 116 // Tests the error case when the job is initialized twice. |
113 TEST(JobTest, DoubleInit) { | 117 TEST(JobTest, DoubleInit) { |
114 // Create the job. | 118 // Create the job. |
115 Job job; | 119 Job job; |
116 ASSERT_EQ(ERROR_SUCCESS, job.Init(JOB_LOCKDOWN, L"my_test_job_name", 0, 0)); | 120 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
117 ASSERT_EQ(ERROR_ALREADY_INITIALIZED, job.Init(JOB_LOCKDOWN, L"test", 0, 0)); | 121 job.Init(JOB_LOCKDOWN, L"my_test_job_name", 0, 0)); |
| 122 ASSERT_EQ(static_cast<DWORD>(ERROR_ALREADY_INITIALIZED), |
| 123 job.Init(JOB_LOCKDOWN, L"test", 0, 0)); |
118 } | 124 } |
119 | 125 |
120 // Tests the error case when we use a method and the object is not yet | 126 // Tests the error case when we use a method and the object is not yet |
121 // initialized. | 127 // initialized. |
122 TEST(JobTest, NoInit) { | 128 TEST(JobTest, NoInit) { |
123 Job job; | 129 Job job; |
124 ASSERT_EQ(ERROR_NO_DATA, job.UserHandleGrantAccess(NULL)); | 130 ASSERT_EQ(static_cast<DWORD>(ERROR_NO_DATA), job.UserHandleGrantAccess(NULL)); |
125 ASSERT_EQ(ERROR_NO_DATA, job.AssignProcessToJob(NULL)); | 131 ASSERT_EQ(static_cast<DWORD>(ERROR_NO_DATA), job.AssignProcessToJob(NULL)); |
126 ASSERT_FALSE(job.Take().IsValid()); | 132 ASSERT_FALSE(job.Take().IsValid()); |
127 } | 133 } |
128 | 134 |
129 // Tests the initialization of the job with different security level. | 135 // Tests the initialization of the job with different security level. |
130 TEST(JobTest, SecurityLevel) { | 136 TEST(JobTest, SecurityLevel) { |
131 Job job1; | 137 Job job1; |
132 ASSERT_EQ(ERROR_SUCCESS, job1.Init(JOB_LOCKDOWN, L"job1", 0, 0)); | 138 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
| 139 job1.Init(JOB_LOCKDOWN, L"job1", 0, 0)); |
133 | 140 |
134 Job job2; | 141 Job job2; |
135 ASSERT_EQ(ERROR_SUCCESS, job2.Init(JOB_RESTRICTED, L"job2", 0, 0)); | 142 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
| 143 job2.Init(JOB_RESTRICTED, L"job2", 0, 0)); |
136 | 144 |
137 Job job3; | 145 Job job3; |
138 ASSERT_EQ(ERROR_SUCCESS, job3.Init(JOB_LIMITED_USER, L"job3", 0, 0)); | 146 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
| 147 job3.Init(JOB_LIMITED_USER, L"job3", 0, 0)); |
139 | 148 |
140 Job job4; | 149 Job job4; |
141 ASSERT_EQ(ERROR_SUCCESS, job4.Init(JOB_INTERACTIVE, L"job4", 0, 0)); | 150 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
| 151 job4.Init(JOB_INTERACTIVE, L"job4", 0, 0)); |
142 | 152 |
143 Job job5; | 153 Job job5; |
144 ASSERT_EQ(ERROR_SUCCESS, job5.Init(JOB_UNPROTECTED, L"job5", 0, 0)); | 154 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
| 155 job5.Init(JOB_UNPROTECTED, L"job5", 0, 0)); |
145 | 156 |
146 // JOB_NONE means we run without a job object so Init should fail. | 157 // JOB_NONE means we run without a job object so Init should fail. |
147 Job job6; | 158 Job job6; |
148 ASSERT_EQ(ERROR_BAD_ARGUMENTS, job6.Init(JOB_NONE, L"job6", 0, 0)); | 159 ASSERT_EQ(static_cast<DWORD>(ERROR_BAD_ARGUMENTS), |
| 160 job6.Init(JOB_NONE, L"job6", 0, 0)); |
149 | 161 |
150 Job job7; | 162 Job job7; |
151 ASSERT_EQ(ERROR_BAD_ARGUMENTS, job7.Init( | 163 ASSERT_EQ(static_cast<DWORD>(ERROR_BAD_ARGUMENTS), |
152 static_cast<JobLevel>(JOB_NONE+1), L"job7", 0, 0)); | 164 job7.Init(static_cast<JobLevel>(JOB_NONE + 1), L"job7", 0, 0)); |
153 } | 165 } |
154 | 166 |
155 // Tests the method "AssignProcessToJob". | 167 // Tests the method "AssignProcessToJob". |
156 TEST(JobTest, ProcessInJob) { | 168 TEST(JobTest, ProcessInJob) { |
157 // Create the job. | 169 // Create the job. |
158 Job job; | 170 Job job; |
159 ASSERT_EQ(ERROR_SUCCESS, job.Init(JOB_UNPROTECTED, L"job_test_process", 0, | 171 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
160 0)); | 172 job.Init(JOB_UNPROTECTED, L"job_test_process", 0, 0)); |
161 | 173 |
162 BOOL result = FALSE; | 174 BOOL result = FALSE; |
163 | 175 |
164 wchar_t notepad[] = L"notepad"; | 176 wchar_t notepad[] = L"notepad"; |
165 STARTUPINFO si = { sizeof(si) }; | 177 STARTUPINFO si = { sizeof(si) }; |
166 PROCESS_INFORMATION temp_process_info = {}; | 178 PROCESS_INFORMATION temp_process_info = {}; |
167 result = ::CreateProcess(NULL, notepad, NULL, NULL, FALSE, 0, NULL, NULL, &si, | 179 result = ::CreateProcess(NULL, notepad, NULL, NULL, FALSE, 0, NULL, NULL, &si, |
168 &temp_process_info); | 180 &temp_process_info); |
169 ASSERT_TRUE(result); | 181 ASSERT_TRUE(result); |
170 base::win::ScopedProcessInformation pi(temp_process_info); | 182 base::win::ScopedProcessInformation pi(temp_process_info); |
171 ASSERT_EQ(ERROR_SUCCESS, job.AssignProcessToJob(pi.process_handle())); | 183 ASSERT_EQ(static_cast<DWORD>(ERROR_SUCCESS), |
| 184 job.AssignProcessToJob(pi.process_handle())); |
172 | 185 |
173 // Get the job handle. | 186 // Get the job handle. |
174 base::win::ScopedHandle job_handle = job.Take(); | 187 base::win::ScopedHandle job_handle = job.Take(); |
175 | 188 |
176 // Check if the process is in the job. | 189 // Check if the process is in the job. |
177 JOBOBJECT_BASIC_PROCESS_ID_LIST jbpidl = {0}; | 190 JOBOBJECT_BASIC_PROCESS_ID_LIST jbpidl = {0}; |
178 DWORD size = sizeof(jbpidl); | 191 DWORD size = sizeof(jbpidl); |
179 result = ::QueryInformationJobObject(job_handle.Get(), | 192 result = ::QueryInformationJobObject(job_handle.Get(), |
180 JobObjectBasicProcessIdList, | 193 JobObjectBasicProcessIdList, |
181 &jbpidl, size, &size); | 194 &jbpidl, size, &size); |
182 EXPECT_TRUE(result); | 195 EXPECT_TRUE(result); |
183 | 196 |
184 EXPECT_EQ(1, jbpidl.NumberOfAssignedProcesses); | 197 EXPECT_EQ(1u, jbpidl.NumberOfAssignedProcesses); |
185 EXPECT_EQ(1, jbpidl.NumberOfProcessIdsInList); | 198 EXPECT_EQ(1u, jbpidl.NumberOfProcessIdsInList); |
186 EXPECT_EQ(pi.process_id(), jbpidl.ProcessIdList[0]); | 199 EXPECT_EQ(pi.process_id(), jbpidl.ProcessIdList[0]); |
187 | 200 |
188 EXPECT_TRUE(::TerminateProcess(pi.process_handle(), 0)); | 201 EXPECT_TRUE(::TerminateProcess(pi.process_handle(), 0)); |
189 } | 202 } |
190 | 203 |
191 } // namespace sandbox | 204 } // namespace sandbox |
OLD | NEW |