puppet 2.7.5 → 2.7.6
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of puppet might be problematic. Click here for more details.
- data/CHANGELOG +121 -0
- data/conf/redhat/puppet.spec +16 -7
- data/lib/puppet.rb +1 -1
- data/lib/puppet/application/cert.rb +17 -3
- data/lib/puppet/application/device.rb +1 -0
- data/lib/puppet/application/kick.rb +0 -2
- data/lib/puppet/application/resource.rb +73 -66
- data/lib/puppet/configurer/plugin_handler.rb +6 -2
- data/lib/puppet/defaults.rb +60 -5
- data/lib/puppet/face/ca.rb +11 -2
- data/lib/puppet/face/certificate.rb +33 -4
- data/lib/puppet/file_serving/fileset.rb +1 -1
- data/lib/puppet/file_serving/indirection_hooks.rb +2 -2
- data/lib/puppet/file_serving/metadata.rb +43 -4
- data/lib/puppet/indirector.rb +0 -1
- data/lib/puppet/indirector/request.rb +3 -4
- data/lib/puppet/indirector/resource/active_record.rb +3 -10
- data/lib/puppet/indirector/resource/ral.rb +2 -2
- data/lib/puppet/indirector/rest.rb +1 -1
- data/lib/puppet/network/handler/ca.rb +16 -106
- data/lib/puppet/network/handler/master.rb +0 -3
- data/lib/puppet/network/handler/runner.rb +1 -0
- data/lib/puppet/parser/scope.rb +10 -0
- data/lib/puppet/provider/file/posix.rb +72 -34
- data/lib/puppet/provider/file/windows.rb +100 -0
- data/lib/puppet/provider/group/windows_adsi.rb +2 -2
- data/lib/puppet/provider/user/windows_adsi.rb +19 -4
- data/lib/puppet/resource.rb +16 -0
- data/lib/puppet/resource/catalog.rb +1 -1
- data/lib/puppet/ssl/certificate.rb +2 -2
- data/lib/puppet/ssl/certificate_authority.rb +86 -10
- data/lib/puppet/ssl/certificate_authority/interface.rb +64 -19
- data/lib/puppet/ssl/certificate_factory.rb +112 -91
- data/lib/puppet/ssl/certificate_request.rb +88 -1
- data/lib/puppet/ssl/host.rb +20 -3
- data/lib/puppet/type/file.rb +15 -34
- data/lib/puppet/type/file/group.rb +11 -91
- data/lib/puppet/type/file/mode.rb +11 -41
- data/lib/puppet/type/file/owner.rb +18 -34
- data/lib/puppet/type/file/source.rb +22 -7
- data/lib/puppet/type/group.rb +4 -3
- data/lib/puppet/type/user.rb +4 -1
- data/lib/puppet/util.rb +59 -6
- data/lib/puppet/util/adsi.rb +11 -0
- data/lib/puppet/util/log.rb +4 -0
- data/lib/puppet/util/log/destinations.rb +7 -1
- data/lib/puppet/util/monkey_patches.rb +19 -0
- data/lib/puppet/util/network_device/config.rb +4 -5
- data/lib/puppet/util/settings.rb +5 -0
- data/lib/puppet/util/suidmanager.rb +0 -1
- data/lib/puppet/util/windows.rb +4 -0
- data/lib/puppet/util/windows/error.rb +16 -0
- data/lib/puppet/util/windows/security.rb +593 -0
- data/spec/integration/defaults_spec.rb +27 -0
- data/spec/integration/network/handler_spec.rb +1 -1
- data/spec/integration/type/file_spec.rb +382 -145
- data/spec/integration/util/windows/security_spec.rb +468 -0
- data/spec/shared_behaviours/file_serving.rb +4 -3
- data/spec/unit/application/agent_spec.rb +1 -0
- data/spec/unit/application/device_spec.rb +5 -0
- data/spec/unit/application/resource_spec.rb +62 -101
- data/spec/unit/configurer/downloader_spec.rb +2 -2
- data/spec/unit/configurer/plugin_handler_spec.rb +15 -8
- data/spec/unit/configurer_spec.rb +2 -2
- data/spec/unit/face/ca_spec.rb +34 -0
- data/spec/unit/face/certificate_spec.rb +168 -1
- data/spec/unit/file_serving/fileset_spec.rb +1 -1
- data/spec/unit/file_serving/indirection_hooks_spec.rb +1 -1
- data/spec/unit/file_serving/metadata_spec.rb +151 -107
- data/spec/unit/indirector/certificate_request/ca_spec.rb +0 -3
- data/spec/unit/indirector/direct_file_server_spec.rb +10 -9
- data/spec/unit/indirector/file_metadata/file_spec.rb +6 -4
- data/spec/unit/indirector/request_spec.rb +13 -3
- data/spec/unit/indirector/resource/active_record_spec.rb +4 -10
- data/spec/unit/indirector/resource/ral_spec.rb +6 -4
- data/spec/unit/indirector/rest_spec.rb +5 -6
- data/spec/unit/network/handler/ca_spec.rb +86 -0
- data/spec/unit/parser/collector_spec.rb +7 -7
- data/spec/unit/parser/scope_spec.rb +20 -0
- data/spec/unit/provider/file/posix_spec.rb +226 -0
- data/spec/unit/provider/file/windows_spec.rb +136 -0
- data/spec/unit/provider/group/windows_adsi_spec.rb +7 -2
- data/spec/unit/provider/user/windows_adsi_spec.rb +36 -3
- data/spec/unit/resource/catalog_spec.rb +20 -10
- data/spec/unit/resource_spec.rb +55 -8
- data/spec/unit/ssl/certificate_authority/interface_spec.rb +97 -54
- data/spec/unit/ssl/certificate_authority_spec.rb +133 -23
- data/spec/unit/ssl/certificate_factory_spec.rb +90 -70
- data/spec/unit/ssl/certificate_request_spec.rb +62 -1
- data/spec/unit/ssl/certificate_spec.rb +20 -14
- data/spec/unit/ssl/host_spec.rb +52 -6
- data/spec/unit/type/file/content_spec.rb +4 -4
- data/spec/unit/type/file/group_spec.rb +34 -96
- data/spec/unit/type/file/mode_spec.rb +88 -0
- data/spec/unit/type/file/owner_spec.rb +32 -123
- data/spec/unit/type/file/source_spec.rb +120 -41
- data/spec/unit/type/file_spec.rb +1033 -753
- data/spec/unit/type_spec.rb +19 -1
- data/spec/unit/util/adsi_spec.rb +19 -0
- data/spec/unit/util/log/destinations_spec.rb +75 -0
- data/spec/unit/util/log_spec.rb +15 -0
- data/spec/unit/util/network_device/config_spec.rb +7 -0
- data/spec/unit/util/settings_spec.rb +10 -0
- data/spec/unit/util_spec.rb +126 -13
- data/test/language/functions.rb +0 -1
- data/test/language/snippets.rb +0 -9
- data/test/lib/puppettest/exetest.rb +1 -1
- data/test/lib/puppettest/servertest.rb +0 -1
- data/test/rails/rails.rb +0 -1
- data/test/ral/type/filesources.rb +0 -60
- metadata +13 -33
- data/lib/puppet/network/client.rb +0 -174
- data/lib/puppet/network/client/ca.rb +0 -56
- data/lib/puppet/network/client/file.rb +0 -6
- data/lib/puppet/network/client/proxy.rb +0 -27
- data/lib/puppet/network/client/report.rb +0 -26
- data/lib/puppet/network/client/runner.rb +0 -10
- data/lib/puppet/network/client/status.rb +0 -4
- data/lib/puppet/network/http_server.rb +0 -3
- data/lib/puppet/network/http_server/mongrel.rb +0 -130
- data/lib/puppet/network/http_server/webrick.rb +0 -155
- data/lib/puppet/network/xmlrpc/client.rb +0 -211
- data/lib/puppet/provider/file/win32.rb +0 -72
- data/lib/puppet/sslcertificates.rb +0 -146
- data/lib/puppet/sslcertificates/ca.rb +0 -375
- data/lib/puppet/sslcertificates/certificate.rb +0 -255
- data/lib/puppet/sslcertificates/inventory.rb +0 -38
- data/lib/puppet/sslcertificates/support.rb +0 -146
- data/spec/integration/network/client_spec.rb +0 -18
- data/spec/unit/network/xmlrpc/client_spec.rb +0 -172
- data/spec/unit/sslcertificates/ca_spec.rb +0 -106
- data/test/certmgr/certmgr.rb +0 -308
- data/test/certmgr/inventory.rb +0 -69
- data/test/certmgr/support.rb +0 -105
- data/test/network/client/ca.rb +0 -69
- data/test/network/client/dipper.rb +0 -34
- data/test/network/handler/ca.rb +0 -273
- data/test/network/server/mongrel_test.rb +0 -99
- data/test/network/server/webrick.rb +0 -111
- data/test/network/xmlrpc/client.rb +0 -45
@@ -0,0 +1,468 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
require 'spec_helper'
|
3
|
+
|
4
|
+
require 'puppet/util/adsi'
|
5
|
+
|
6
|
+
if Puppet.features.microsoft_windows?
|
7
|
+
class WindowsSecurityTester
|
8
|
+
require 'puppet/util/windows/security'
|
9
|
+
include Puppet::Util::Windows::Security
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
describe "Puppet::Util::Windows::Security", :if => Puppet.features.microsoft_windows? do
|
14
|
+
include PuppetSpec::Files
|
15
|
+
|
16
|
+
before :all do
|
17
|
+
@sids = {
|
18
|
+
:current_user => Puppet::Util::ADSI.sid_for_account(Sys::Admin.get_login),
|
19
|
+
:admin => Puppet::Util::ADSI.sid_for_account("Administrator"),
|
20
|
+
:guest => Puppet::Util::ADSI.sid_for_account("Guest"),
|
21
|
+
:users => Win32::Security::SID::BuiltinUsers,
|
22
|
+
:power_users => Win32::Security::SID::PowerUsers,
|
23
|
+
}
|
24
|
+
end
|
25
|
+
|
26
|
+
let (:sids) { @sids }
|
27
|
+
let (:winsec) { WindowsSecurityTester.new }
|
28
|
+
|
29
|
+
shared_examples_for "a securable object" do
|
30
|
+
describe "for a normal user" do
|
31
|
+
before :each do
|
32
|
+
Puppet.features.stubs(:root?).returns(false)
|
33
|
+
end
|
34
|
+
|
35
|
+
after :each do
|
36
|
+
winsec.set_mode(WindowsSecurityTester::S_IRWXU, path)
|
37
|
+
end
|
38
|
+
|
39
|
+
describe "#owner=" do
|
40
|
+
it "should allow setting to the current user" do
|
41
|
+
winsec.set_owner(sids[:current_user], path)
|
42
|
+
end
|
43
|
+
|
44
|
+
it "should raise an exception when setting to a different user" do
|
45
|
+
lambda { winsec.set_owner(sids[:guest], path) }.should raise_error(Puppet::Error, /This security ID may not be assigned as the owner of this object./)
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
describe "#owner" do
|
50
|
+
it "it should not be empty" do
|
51
|
+
winsec.get_owner(path).should_not be_empty
|
52
|
+
end
|
53
|
+
|
54
|
+
it "should raise an exception if an invalid path is provided" do
|
55
|
+
lambda { winsec.get_owner("c:\\doesnotexist.txt") }.should raise_error(Puppet::Error, /The system cannot find the file specified./)
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
describe "#group=" do
|
60
|
+
it "should allow setting to a group the current owner is a member of" do
|
61
|
+
winsec.set_group(sids[:users], path)
|
62
|
+
end
|
63
|
+
|
64
|
+
# Unlike unix, if the user has permission to WRITE_OWNER, which the file owner has by default,
|
65
|
+
# then they can set the primary group to a group that the user does not belong to.
|
66
|
+
it "should allow setting to a group the current owner is not a member of" do
|
67
|
+
winsec.set_group(sids[:power_users], path)
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
describe "#group" do
|
72
|
+
it "should not be empty" do
|
73
|
+
winsec.get_group(path).should_not be_empty
|
74
|
+
end
|
75
|
+
|
76
|
+
it "should raise an exception if an invalid path is provided" do
|
77
|
+
lambda { winsec.get_group("c:\\doesnotexist.txt") }.should raise_error(Puppet::Error, /The system cannot find the file specified./)
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
describe "#mode=" do
|
82
|
+
[0000, 0100, 0200, 0300, 0400, 0500, 0600, 0700].each do |mode|
|
83
|
+
it "should enforce mode #{mode.to_s(8)}" do
|
84
|
+
winsec.set_mode(mode, path)
|
85
|
+
|
86
|
+
check_access(mode, path)
|
87
|
+
end
|
88
|
+
end
|
89
|
+
|
90
|
+
it "should round-trip all 64 modes that do not require deny ACEs" do
|
91
|
+
0.upto(7).each do |u|
|
92
|
+
0.upto(u).each do |g|
|
93
|
+
0.upto(g).each do |o|
|
94
|
+
# if user is superset of group, and group superset of other, then
|
95
|
+
# no deny ace is required, and mode can be converted to win32
|
96
|
+
# access mask, and back to mode without loss of information
|
97
|
+
# (provided the owner and group are not the same)
|
98
|
+
next if ((u & g) != g) or ((g & o) != o)
|
99
|
+
|
100
|
+
mode = (u << 6 | g << 3 | o << 0)
|
101
|
+
winsec.set_mode(mode, path)
|
102
|
+
winsec.get_mode(path).to_s(8).should == mode.to_s(8)
|
103
|
+
end
|
104
|
+
end
|
105
|
+
end
|
106
|
+
end
|
107
|
+
|
108
|
+
describe "for modes that require deny aces" do
|
109
|
+
it "should map everyone to group and owner" do
|
110
|
+
winsec.set_mode(0426, path)
|
111
|
+
winsec.get_mode(path).to_s(8).should == "666"
|
112
|
+
end
|
113
|
+
|
114
|
+
it "should combine user and group modes when owner and group sids are equal" do
|
115
|
+
winsec.set_group(winsec.get_owner(path), path)
|
116
|
+
|
117
|
+
winsec.set_mode(0410, path)
|
118
|
+
winsec.get_mode(path).to_s(8).should == "550"
|
119
|
+
end
|
120
|
+
end
|
121
|
+
|
122
|
+
describe "for read-only objects" do
|
123
|
+
before :each do
|
124
|
+
winsec.add_attributes(path, WindowsSecurityTester::FILE_ATTRIBUTE_READONLY)
|
125
|
+
(winsec.get_attributes(path) & WindowsSecurityTester::FILE_ATTRIBUTE_READONLY).should be_nonzero
|
126
|
+
end
|
127
|
+
|
128
|
+
it "should make them writable if any sid has write permission" do
|
129
|
+
winsec.set_mode(WindowsSecurityTester::S_IWUSR, path)
|
130
|
+
(winsec.get_attributes(path) & WindowsSecurityTester::FILE_ATTRIBUTE_READONLY).should == 0
|
131
|
+
end
|
132
|
+
|
133
|
+
it "should leave them read-only if no sid has write permission" do
|
134
|
+
winsec.set_mode(WindowsSecurityTester::S_IRUSR | WindowsSecurityTester::S_IXGRP, path)
|
135
|
+
(winsec.get_attributes(path) & WindowsSecurityTester::FILE_ATTRIBUTE_READONLY).should be_nonzero
|
136
|
+
end
|
137
|
+
end
|
138
|
+
|
139
|
+
it "should raise an exception if an invalid path is provided" do
|
140
|
+
lambda { winsec.set_mode(sids[:guest], "c:\\doesnotexist.txt") }.should raise_error(Puppet::Error, /The system cannot find the file specified./)
|
141
|
+
end
|
142
|
+
end
|
143
|
+
|
144
|
+
describe "#mode" do
|
145
|
+
it "should report when extra aces are encounted" do
|
146
|
+
winsec.set_acl(path, true) do |acl|
|
147
|
+
[ 544, 545, 546, 547 ].each do |rid|
|
148
|
+
winsec.add_access_allowed_ace(acl, WindowsSecurityTester::STANDARD_RIGHTS_ALL, "S-1-5-32-#{rid}")
|
149
|
+
end
|
150
|
+
end
|
151
|
+
mode = winsec.get_mode(path)
|
152
|
+
(mode & WindowsSecurityTester::S_IEXTRA).should_not == 0
|
153
|
+
end
|
154
|
+
|
155
|
+
it "should warn if a deny ace is encountered" do
|
156
|
+
winsec.set_acl(path) do |acl|
|
157
|
+
winsec.add_access_denied_ace(acl, WindowsSecurityTester::FILE_GENERIC_WRITE, sids[:guest])
|
158
|
+
winsec.add_access_allowed_ace(acl, WindowsSecurityTester::STANDARD_RIGHTS_ALL | WindowsSecurityTester::SPECIFIC_RIGHTS_ALL, sids[:current_user])
|
159
|
+
end
|
160
|
+
|
161
|
+
Puppet.expects(:warning).with("Unsupported access control entry type: 0x1")
|
162
|
+
|
163
|
+
winsec.get_mode(path)
|
164
|
+
end
|
165
|
+
|
166
|
+
it "should skip inherit-only ace" do
|
167
|
+
winsec.set_acl(path) do |acl|
|
168
|
+
winsec.add_access_allowed_ace(acl, WindowsSecurityTester::STANDARD_RIGHTS_ALL | WindowsSecurityTester::SPECIFIC_RIGHTS_ALL, sids[:current_user])
|
169
|
+
winsec.add_access_allowed_ace(acl, WindowsSecurityTester::FILE_GENERIC_READ, Win32::Security::SID::Everyone, WindowsSecurityTester::INHERIT_ONLY_ACE | WindowsSecurityTester::OBJECT_INHERIT_ACE)
|
170
|
+
end
|
171
|
+
|
172
|
+
(winsec.get_mode(path) & WindowsSecurityTester::S_IRWXO).should == 0
|
173
|
+
end
|
174
|
+
|
175
|
+
it "should raise an exception if an invalid path is provided" do
|
176
|
+
lambda { winsec.get_mode("c:\\doesnotexist.txt") }.should raise_error(Puppet::Error, /The system cannot find the file specified./)
|
177
|
+
end
|
178
|
+
end
|
179
|
+
|
180
|
+
describe "inherited access control entries" do
|
181
|
+
it "should be absent when the access control list is protected" do
|
182
|
+
winsec.set_mode(WindowsSecurityTester::S_IRWXU, path)
|
183
|
+
(winsec.get_mode(path) & WindowsSecurityTester::S_IEXTRA).should == 0
|
184
|
+
end
|
185
|
+
|
186
|
+
it "should be present when the access control list is unprotected" do
|
187
|
+
dir = tmpdir('win_sec_parent')
|
188
|
+
|
189
|
+
# add a bunch of aces, make sure we can add to the directory
|
190
|
+
allow = WindowsSecurityTester::STANDARD_RIGHTS_ALL | WindowsSecurityTester::SPECIFIC_RIGHTS_ALL
|
191
|
+
inherit = WindowsSecurityTester::OBJECT_INHERIT_ACE | WindowsSecurityTester::CONTAINER_INHERIT_ACE
|
192
|
+
|
193
|
+
winsec.set_acl(dir, true) do |acl|
|
194
|
+
winsec.add_access_allowed_ace(acl, allow, "S-1-1-0", inherit) # everyone
|
195
|
+
|
196
|
+
[ 544, 545, 546, 547 ].each do |rid|
|
197
|
+
winsec.add_access_allowed_ace(acl, WindowsSecurityTester::STANDARD_RIGHTS_ALL, "S-1-5-32-#{rid}", inherit)
|
198
|
+
end
|
199
|
+
end
|
200
|
+
|
201
|
+
# add a file
|
202
|
+
child = File.join(dir, "child")
|
203
|
+
File.new(child, "w").close
|
204
|
+
|
205
|
+
# unprotect child, it should inherit from parent
|
206
|
+
winsec.set_mode(WindowsSecurityTester::S_IRWXU, child, false)
|
207
|
+
(winsec.get_mode(child) & WindowsSecurityTester::S_IEXTRA).should == WindowsSecurityTester::S_IEXTRA
|
208
|
+
end
|
209
|
+
end
|
210
|
+
end
|
211
|
+
|
212
|
+
describe "for an administrator", :if => Puppet.features.root? do
|
213
|
+
before :each do
|
214
|
+
winsec.set_owner(sids[:guest], path)
|
215
|
+
winsec.set_group(sids[:guest], path)
|
216
|
+
winsec.set_mode(WindowsSecurityTester::S_IRWXU | WindowsSecurityTester::S_IRWXG, path)
|
217
|
+
lambda { File.open(path, 'r') }.should raise_error(Errno::EACCES)
|
218
|
+
end
|
219
|
+
|
220
|
+
after :each do
|
221
|
+
winsec.set_owner(sids[:current_user], path)
|
222
|
+
winsec.set_mode(WindowsSecurityTester::S_IRWXU, path)
|
223
|
+
end
|
224
|
+
|
225
|
+
describe "#owner=" do
|
226
|
+
it "should accept a user sid" do
|
227
|
+
winsec.set_owner(sids[:admin], path)
|
228
|
+
winsec.get_owner(path).should == sids[:admin]
|
229
|
+
end
|
230
|
+
|
231
|
+
it "should accept a group sid" do
|
232
|
+
winsec.set_owner(sids[:power_users], path)
|
233
|
+
winsec.get_owner(path).should == sids[:power_users]
|
234
|
+
end
|
235
|
+
|
236
|
+
it "should raise an exception if an invalid sid is provided" do
|
237
|
+
lambda { winsec.set_owner("foobar", path) }.should raise_error(Puppet::Error, /Failed to convert string SID/)
|
238
|
+
end
|
239
|
+
|
240
|
+
it "should raise an exception if an invalid path is provided" do
|
241
|
+
lambda { winsec.set_owner(sids[:guest], "c:\\doesnotexist.txt") }.should raise_error(Puppet::Error, /The system cannot find the file specified./)
|
242
|
+
end
|
243
|
+
end
|
244
|
+
|
245
|
+
describe "#group=" do
|
246
|
+
it "should accept a group sid" do
|
247
|
+
winsec.set_group(sids[:power_users], path)
|
248
|
+
winsec.get_group(path).should == sids[:power_users]
|
249
|
+
end
|
250
|
+
|
251
|
+
it "should accept a user sid" do
|
252
|
+
winsec.set_group(sids[:admin], path)
|
253
|
+
winsec.get_group(path).should == sids[:admin]
|
254
|
+
end
|
255
|
+
|
256
|
+
it "should allow owner and group to be the same sid" do
|
257
|
+
winsec.set_owner(sids[:power_users], path)
|
258
|
+
winsec.set_group(sids[:power_users], path)
|
259
|
+
winsec.set_mode(0610, path)
|
260
|
+
|
261
|
+
winsec.get_owner(path).should == sids[:power_users]
|
262
|
+
winsec.get_group(path).should == sids[:power_users]
|
263
|
+
# note group execute permission added to user ace, and then group rwx value
|
264
|
+
# reflected to match
|
265
|
+
winsec.get_mode(path).to_s(8).should == "770"
|
266
|
+
end
|
267
|
+
|
268
|
+
it "should raise an exception if an invalid sid is provided" do
|
269
|
+
lambda { winsec.set_group("foobar", path) }.should raise_error(Puppet::Error, /Failed to convert string SID/)
|
270
|
+
end
|
271
|
+
|
272
|
+
it "should raise an exception if an invalid path is provided" do
|
273
|
+
lambda { winsec.set_group(sids[:guest], "c:\\doesnotexist.txt") }.should raise_error(Puppet::Error, /The system cannot find the file specified./)
|
274
|
+
end
|
275
|
+
end
|
276
|
+
|
277
|
+
describe "when the sid is NULL" do
|
278
|
+
it "should retrieve an empty owner sid"
|
279
|
+
it "should retrieve an empty group sid"
|
280
|
+
end
|
281
|
+
|
282
|
+
describe "when the sid refers to a deleted trustee" do
|
283
|
+
it "should retrieve the user sid" do
|
284
|
+
sid = nil
|
285
|
+
user = Puppet::Util::ADSI::User.create("delete_me_user")
|
286
|
+
user.commit
|
287
|
+
begin
|
288
|
+
sid = Sys::Admin::get_user(user.name).sid
|
289
|
+
winsec.set_owner(sid, path)
|
290
|
+
winsec.set_mode(WindowsSecurityTester::S_IRWXU, path)
|
291
|
+
ensure
|
292
|
+
Puppet::Util::ADSI::User.delete(user.name)
|
293
|
+
end
|
294
|
+
|
295
|
+
winsec.get_owner(path).should == sid
|
296
|
+
winsec.get_mode(path).should == WindowsSecurityTester::S_IRWXU
|
297
|
+
end
|
298
|
+
|
299
|
+
it "should retrieve the group sid" do
|
300
|
+
sid = nil
|
301
|
+
group = Puppet::Util::ADSI::Group.create("delete_me_group")
|
302
|
+
group.commit
|
303
|
+
begin
|
304
|
+
sid = Sys::Admin::get_group(group.name).sid
|
305
|
+
winsec.set_group(sid, path)
|
306
|
+
winsec.set_mode(WindowsSecurityTester::S_IRWXG, path)
|
307
|
+
ensure
|
308
|
+
Puppet::Util::ADSI::Group.delete(group.name)
|
309
|
+
end
|
310
|
+
winsec.get_group(path).should == sid
|
311
|
+
winsec.get_mode(path).should == WindowsSecurityTester::S_IRWXG
|
312
|
+
end
|
313
|
+
end
|
314
|
+
|
315
|
+
describe "#mode" do
|
316
|
+
it "should deny all access when the DACL is empty" do
|
317
|
+
winsec.set_acl(path, true) { |acl| }
|
318
|
+
|
319
|
+
winsec.get_mode(path).should == 0
|
320
|
+
end
|
321
|
+
|
322
|
+
# REMIND: ruby crashes when trying to set a NULL DACL
|
323
|
+
# it "should allow all when it is nil" do
|
324
|
+
# winsec.set_owner(sids[:current_user], path)
|
325
|
+
# winsec.open_file(path, WindowsSecurityTester::READ_CONTROL | WindowsSecurityTester::WRITE_DAC) do |handle|
|
326
|
+
# winsec.set_security_info(handle, WindowsSecurityTester::DACL_SECURITY_INFORMATION | WindowsSecurityTester::PROTECTED_DACL_SECURITY_INFORMATION, nil)
|
327
|
+
# end
|
328
|
+
# winsec.get_mode(path).to_s(8).should == "777"
|
329
|
+
# end
|
330
|
+
end
|
331
|
+
|
332
|
+
describe "#string_to_sid_ptr" do
|
333
|
+
it "should raise an error if an invalid SID is specified" do
|
334
|
+
expect do
|
335
|
+
winsec.string_to_sid_ptr('foobar')
|
336
|
+
end.to raise_error(Puppet::Util::Windows::Error) { |error| error.code.should == 1337 }
|
337
|
+
end
|
338
|
+
|
339
|
+
it "should yield if a block is given" do
|
340
|
+
yielded = nil
|
341
|
+
winsec.string_to_sid_ptr('S-1-1-0') do |sid|
|
342
|
+
yielded = sid
|
343
|
+
end
|
344
|
+
yielded.should_not be_nil
|
345
|
+
end
|
346
|
+
|
347
|
+
it "should allow no block to be specified" do
|
348
|
+
winsec.string_to_sid_ptr('S-1-1-0').should be_true
|
349
|
+
end
|
350
|
+
end
|
351
|
+
end
|
352
|
+
end
|
353
|
+
|
354
|
+
describe "file" do
|
355
|
+
let :path do
|
356
|
+
path = tmpfile('win_sec_test_file')
|
357
|
+
File.new(path, "w").close
|
358
|
+
path
|
359
|
+
end
|
360
|
+
|
361
|
+
it_behaves_like "a securable object" do
|
362
|
+
def check_access(mode, path)
|
363
|
+
if (mode & WindowsSecurityTester::S_IRUSR).nonzero?
|
364
|
+
check_read(path)
|
365
|
+
else
|
366
|
+
lambda { check_read(path) }.should raise_error(Errno::EACCES)
|
367
|
+
end
|
368
|
+
|
369
|
+
if (mode & WindowsSecurityTester::S_IWUSR).nonzero?
|
370
|
+
check_write(path)
|
371
|
+
else
|
372
|
+
lambda { check_write(path) }.should raise_error(Errno::EACCES)
|
373
|
+
end
|
374
|
+
|
375
|
+
if (mode & WindowsSecurityTester::S_IXUSR).nonzero?
|
376
|
+
lambda { check_execute(path) }.should raise_error(Errno::ENOEXEC)
|
377
|
+
else
|
378
|
+
lambda { check_execute(path) }.should raise_error(Errno::EACCES)
|
379
|
+
end
|
380
|
+
end
|
381
|
+
|
382
|
+
def check_read(path)
|
383
|
+
File.open(path, 'r').close
|
384
|
+
end
|
385
|
+
|
386
|
+
def check_write(path)
|
387
|
+
File.open(path, 'w').close
|
388
|
+
end
|
389
|
+
|
390
|
+
def check_execute(path)
|
391
|
+
Kernel.exec(path)
|
392
|
+
end
|
393
|
+
end
|
394
|
+
|
395
|
+
describe "locked files" do
|
396
|
+
let (:explorer) { File.join(Dir::WINDOWS, "explorer.exe") }
|
397
|
+
|
398
|
+
it "should get the owner" do
|
399
|
+
winsec.get_owner(explorer).should match /^S-1-5-/
|
400
|
+
end
|
401
|
+
|
402
|
+
it "should get the group" do
|
403
|
+
winsec.get_group(explorer).should match /^S-1-5-/
|
404
|
+
end
|
405
|
+
|
406
|
+
it "should get the mode" do
|
407
|
+
winsec.get_mode(explorer).should == (WindowsSecurityTester::S_IRWXU | WindowsSecurityTester::S_IRWXG | WindowsSecurityTester::S_IEXTRA)
|
408
|
+
end
|
409
|
+
end
|
410
|
+
end
|
411
|
+
|
412
|
+
describe "directory" do
|
413
|
+
let :path do
|
414
|
+
tmpdir('win_sec_test_dir')
|
415
|
+
end
|
416
|
+
|
417
|
+
it_behaves_like "a securable object" do
|
418
|
+
def check_access(mode, path)
|
419
|
+
if (mode & WindowsSecurityTester::S_IRUSR).nonzero?
|
420
|
+
check_read(path)
|
421
|
+
else
|
422
|
+
lambda { check_read(path) }.should raise_error(Errno::EACCES)
|
423
|
+
end
|
424
|
+
|
425
|
+
if (mode & WindowsSecurityTester::S_IWUSR).nonzero?
|
426
|
+
check_write(path)
|
427
|
+
else
|
428
|
+
lambda { check_write(path) }.should raise_error(Errno::EACCES)
|
429
|
+
end
|
430
|
+
|
431
|
+
if (mode & WindowsSecurityTester::S_IXUSR).nonzero?
|
432
|
+
check_execute(path)
|
433
|
+
else
|
434
|
+
lambda { check_execute(path) }.should raise_error(Errno::EACCES)
|
435
|
+
end
|
436
|
+
end
|
437
|
+
|
438
|
+
def check_read(path)
|
439
|
+
Dir.entries(path)
|
440
|
+
end
|
441
|
+
|
442
|
+
def check_write(path)
|
443
|
+
Dir.mkdir(File.join(path, "subdir"))
|
444
|
+
end
|
445
|
+
|
446
|
+
def check_execute(path)
|
447
|
+
Dir.chdir(path) {|dir| }
|
448
|
+
end
|
449
|
+
end
|
450
|
+
|
451
|
+
describe "inheritable aces" do
|
452
|
+
it "should be applied to child objects" do
|
453
|
+
mode640 = WindowsSecurityTester::S_IRUSR | WindowsSecurityTester::S_IWUSR | WindowsSecurityTester::S_IRGRP
|
454
|
+
winsec.set_mode(mode640, path)
|
455
|
+
|
456
|
+
newfile = File.join(path, "newfile.txt")
|
457
|
+
File.new(newfile, "w").close
|
458
|
+
|
459
|
+
newdir = File.join(path, "newdir")
|
460
|
+
Dir.mkdir(newdir)
|
461
|
+
|
462
|
+
[newfile, newdir].each do |p|
|
463
|
+
winsec.get_mode(p).to_s(8).should == mode640.to_s(8)
|
464
|
+
end
|
465
|
+
end
|
466
|
+
end
|
467
|
+
end
|
468
|
+
end
|