root / image_creator / os_type / windows.py @ 55133880
History | View | Annotate | Download (6.2 kB)
1 | 121f3bc0 | Nikos Skalkotos | # -*- coding: utf-8 -*-
|
---|---|---|---|
2 | 121f3bc0 | Nikos Skalkotos | #
|
3 | ae48a082 | Nikos Skalkotos | # Copyright 2012 GRNET S.A. All rights reserved.
|
4 | ae48a082 | Nikos Skalkotos | #
|
5 | ae48a082 | Nikos Skalkotos | # Redistribution and use in source and binary forms, with or
|
6 | ae48a082 | Nikos Skalkotos | # without modification, are permitted provided that the following
|
7 | ae48a082 | Nikos Skalkotos | # conditions are met:
|
8 | ae48a082 | Nikos Skalkotos | #
|
9 | ae48a082 | Nikos Skalkotos | # 1. Redistributions of source code must retain the above
|
10 | ae48a082 | Nikos Skalkotos | # copyright notice, this list of conditions and the following
|
11 | ae48a082 | Nikos Skalkotos | # disclaimer.
|
12 | ae48a082 | Nikos Skalkotos | #
|
13 | ae48a082 | Nikos Skalkotos | # 2. Redistributions in binary form must reproduce the above
|
14 | ae48a082 | Nikos Skalkotos | # copyright notice, this list of conditions and the following
|
15 | ae48a082 | Nikos Skalkotos | # disclaimer in the documentation and/or other materials
|
16 | ae48a082 | Nikos Skalkotos | # provided with the distribution.
|
17 | ae48a082 | Nikos Skalkotos | #
|
18 | ae48a082 | Nikos Skalkotos | # THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
|
19 | ae48a082 | Nikos Skalkotos | # OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
20 | ae48a082 | Nikos Skalkotos | # WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
21 | ae48a082 | Nikos Skalkotos | # PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
|
22 | ae48a082 | Nikos Skalkotos | # CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
23 | ae48a082 | Nikos Skalkotos | # SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
24 | ae48a082 | Nikos Skalkotos | # LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
|
25 | ae48a082 | Nikos Skalkotos | # USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
|
26 | ae48a082 | Nikos Skalkotos | # AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
27 | ae48a082 | Nikos Skalkotos | # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
|
28 | ae48a082 | Nikos Skalkotos | # ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
29 | ae48a082 | Nikos Skalkotos | # POSSIBILITY OF SUCH DAMAGE.
|
30 | ae48a082 | Nikos Skalkotos | #
|
31 | ae48a082 | Nikos Skalkotos | # The views and conclusions contained in the software and
|
32 | ae48a082 | Nikos Skalkotos | # documentation are those of the authors and should not be
|
33 | ae48a082 | Nikos Skalkotos | # interpreted as representing official policies, either expressed
|
34 | ae48a082 | Nikos Skalkotos | # or implied, of GRNET S.A.
|
35 | ae48a082 | Nikos Skalkotos | |
36 | 121f3bc0 | Nikos Skalkotos | """This module hosts OS-specific code common for the various Microsoft
|
37 | 121f3bc0 | Nikos Skalkotos | Windows OSs."""
|
38 | 121f3bc0 | Nikos Skalkotos | |
39 | 55133880 | Nikos Skalkotos | from image_creator.os_type import OSBase, sysprep |
40 | 55133880 | Nikos Skalkotos | from image_creator.util import FatalError, check_guestfs_version |
41 | aa2062ba | Nikos Skalkotos | |
42 | 76b200cf | Nikos Skalkotos | import hivex |
43 | 76b200cf | Nikos Skalkotos | import tempfile |
44 | 76b200cf | Nikos Skalkotos | import os |
45 | 76b200cf | Nikos Skalkotos | |
46 | 8c574358 | Nikos Skalkotos | |
47 | aa2062ba | Nikos Skalkotos | class Windows(OSBase): |
48 | 88f83027 | Nikos Skalkotos | """OS class for Windows"""
|
49 | 76b200cf | Nikos Skalkotos | |
50 | 55133880 | Nikos Skalkotos | @sysprep(enabled=False) |
51 | 55133880 | Nikos Skalkotos | def remove_user_accounts(self, print_header=True): |
52 | 55133880 | Nikos Skalkotos | """Remove all user accounts with id greater than 1000"""
|
53 | 55133880 | Nikos Skalkotos | pass
|
54 | 55133880 | Nikos Skalkotos | |
55 | 55133880 | Nikos Skalkotos | def do_sysprep(self): |
56 | 55133880 | Nikos Skalkotos | """Prepare system for image creation."""
|
57 | 55133880 | Nikos Skalkotos | |
58 | 55133880 | Nikos Skalkotos | if getattr(self, 'syspreped', False): |
59 | 55133880 | Nikos Skalkotos | raise FatalError("Image is already syspreped!") |
60 | 55133880 | Nikos Skalkotos | |
61 | 55133880 | Nikos Skalkotos | self.mount(readonly=False) |
62 | 55133880 | Nikos Skalkotos | try:
|
63 | 55133880 | Nikos Skalkotos | disabled_uac = self._update_uac_remote_setting(1) |
64 | 55133880 | Nikos Skalkotos | finally:
|
65 | 55133880 | Nikos Skalkotos | self.umount()
|
66 | 55133880 | Nikos Skalkotos | |
67 | 55133880 | Nikos Skalkotos | self.out.output("Shutting down helper VM ...", False) |
68 | 55133880 | Nikos Skalkotos | self.g.sync()
|
69 | 55133880 | Nikos Skalkotos | # guestfs_shutdown which is the prefered way to shutdown the backend
|
70 | 55133880 | Nikos Skalkotos | # process was introduced in version 1.19.16
|
71 | 55133880 | Nikos Skalkotos | if check_guestfs_version(self.g, 1, 19, 16) >= 0: |
72 | 55133880 | Nikos Skalkotos | ret = self.g.shutdown()
|
73 | 55133880 | Nikos Skalkotos | else:
|
74 | 55133880 | Nikos Skalkotos | ret = self.g.kill_subprocess()
|
75 | 55133880 | Nikos Skalkotos | |
76 | 55133880 | Nikos Skalkotos | self.out.success('done') |
77 | 55133880 | Nikos Skalkotos | |
78 | 55133880 | Nikos Skalkotos | self.out.output("Starting windows VM ...", False) |
79 | 55133880 | Nikos Skalkotos | try:
|
80 | 55133880 | Nikos Skalkotos | pass
|
81 | 55133880 | Nikos Skalkotos | finally:
|
82 | 55133880 | Nikos Skalkotos | self.out.output("Relaunching helper VM (may take a while) ...", |
83 | 55133880 | Nikos Skalkotos | False)
|
84 | 55133880 | Nikos Skalkotos | self.g.launch()
|
85 | 55133880 | Nikos Skalkotos | self.out.success('done') |
86 | 55133880 | Nikos Skalkotos | |
87 | 55133880 | Nikos Skalkotos | if disabled_uac:
|
88 | 55133880 | Nikos Skalkotos | self._update_uac_remote_setting(0) |
89 | 55133880 | Nikos Skalkotos | |
90 | 55133880 | Nikos Skalkotos | self.syspreped = True |
91 | 55133880 | Nikos Skalkotos | |
92 | 55133880 | Nikos Skalkotos | def _registry_file_path(self, regfile): |
93 | 55133880 | Nikos Skalkotos | """Retrieves the case sensitive path to a registry file"""
|
94 | 55133880 | Nikos Skalkotos | |
95 | 55133880 | Nikos Skalkotos | systemroot = self.g.inspect_get_windows_systemroot(self.root) |
96 | 55133880 | Nikos Skalkotos | path = "%s/system32/config/%s" % (systemroot, regfile)
|
97 | 55133880 | Nikos Skalkotos | try:
|
98 | 55133880 | Nikos Skalkotos | path = self.g.case_sensitive_path(path)
|
99 | 55133880 | Nikos Skalkotos | except RuntimeError as e: |
100 | 55133880 | Nikos Skalkotos | raise FatalError("Unable to retrieve registry file: %s. Reason: %s" |
101 | 55133880 | Nikos Skalkotos | % (regfile, str(e)))
|
102 | 55133880 | Nikos Skalkotos | return path
|
103 | 55133880 | Nikos Skalkotos | |
104 | 55133880 | Nikos Skalkotos | def _update_uac_remote_setting(self, value): |
105 | 55133880 | Nikos Skalkotos | """Updates the registry key value:
|
106 | 55133880 | Nikos Skalkotos | [HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies
|
107 | 55133880 | Nikos Skalkotos | \System]"LocalAccountTokenFilterPolicy"
|
108 | 55133880 | Nikos Skalkotos |
|
109 | 55133880 | Nikos Skalkotos | value = 1 will disable the UAC remote restrictions
|
110 | 55133880 | Nikos Skalkotos | value = 0 will enable the UAC remote restrictions
|
111 | 55133880 | Nikos Skalkotos |
|
112 | 55133880 | Nikos Skalkotos | For more info see here: http://support.microsoft.com/kb/951016
|
113 | 55133880 | Nikos Skalkotos |
|
114 | 55133880 | Nikos Skalkotos | Returns:
|
115 | 55133880 | Nikos Skalkotos | True if the key is changed
|
116 | 55133880 | Nikos Skalkotos | False if the key is unchanged
|
117 | 55133880 | Nikos Skalkotos | """
|
118 | 55133880 | Nikos Skalkotos | |
119 | 55133880 | Nikos Skalkotos | if value not in (0, 1): |
120 | 55133880 | Nikos Skalkotos | raise ValueError("Valid values for value parameter are 0 and 1") |
121 | 55133880 | Nikos Skalkotos | |
122 | 55133880 | Nikos Skalkotos | path = self._registry_file_path('SOFTWARE') |
123 | 55133880 | Nikos Skalkotos | softwarefd, software = tempfile.mkstemp() |
124 | 55133880 | Nikos Skalkotos | try:
|
125 | 55133880 | Nikos Skalkotos | os.close(softwarefd) |
126 | 55133880 | Nikos Skalkotos | self.g.download(path, software)
|
127 | 55133880 | Nikos Skalkotos | |
128 | 55133880 | Nikos Skalkotos | h = hivex.Hivex(software, write=True)
|
129 | 55133880 | Nikos Skalkotos | |
130 | 55133880 | Nikos Skalkotos | key = h.root() |
131 | 55133880 | Nikos Skalkotos | for child in ('Microsoft', 'Windows', 'CurrentVersion', 'Policies', |
132 | 55133880 | Nikos Skalkotos | 'System'):
|
133 | 55133880 | Nikos Skalkotos | key = h.node_get_child(key, child) |
134 | 55133880 | Nikos Skalkotos | |
135 | 55133880 | Nikos Skalkotos | policy = None
|
136 | 55133880 | Nikos Skalkotos | for val in h.node_values(key): |
137 | 55133880 | Nikos Skalkotos | if h.value_key(val) == "LocalAccountTokenFilterPolicy": |
138 | 55133880 | Nikos Skalkotos | policy = val |
139 | 55133880 | Nikos Skalkotos | |
140 | 55133880 | Nikos Skalkotos | if policy is not None: |
141 | 55133880 | Nikos Skalkotos | dword = h.value_dword(policy) |
142 | 55133880 | Nikos Skalkotos | if dword == value:
|
143 | 55133880 | Nikos Skalkotos | return False |
144 | 55133880 | Nikos Skalkotos | elif value == 0: |
145 | 55133880 | Nikos Skalkotos | return False |
146 | 55133880 | Nikos Skalkotos | |
147 | 55133880 | Nikos Skalkotos | new_value = { |
148 | 55133880 | Nikos Skalkotos | 'key': "LocalAccountTokenFilterPolicy", 't': 4L, |
149 | 55133880 | Nikos Skalkotos | 'value': '%s\x00\x00\x00' % '\x00' if value == 0 else '\x01'} |
150 | 55133880 | Nikos Skalkotos | |
151 | 55133880 | Nikos Skalkotos | h.node_set_value(key, new_value) |
152 | 55133880 | Nikos Skalkotos | h.commit(None)
|
153 | 55133880 | Nikos Skalkotos | |
154 | 55133880 | Nikos Skalkotos | self.g.upload(software, path)
|
155 | 55133880 | Nikos Skalkotos | |
156 | 55133880 | Nikos Skalkotos | finally:
|
157 | 55133880 | Nikos Skalkotos | os.unlink(software) |
158 | 55133880 | Nikos Skalkotos | |
159 | 55133880 | Nikos Skalkotos | return True |
160 | 55133880 | Nikos Skalkotos | |
161 | b8c0848c | Nikos Skalkotos | def _do_collect_metadata(self): |
162 | b8c0848c | Nikos Skalkotos | """Collect metadata about the OS"""
|
163 | b8c0848c | Nikos Skalkotos | super(Windows, self)._do_collect_metadata() |
164 | 76b200cf | Nikos Skalkotos | self.meta["USERS"] = " ".join(self._get_users()) |
165 | 76b200cf | Nikos Skalkotos | |
166 | 76b200cf | Nikos Skalkotos | def _get_users(self): |
167 | 121f3bc0 | Nikos Skalkotos | """Returns a list of users found in the images"""
|
168 | 55133880 | Nikos Skalkotos | path = self._registry_file_path('SAM') |
169 | 76b200cf | Nikos Skalkotos | samfd, sam = tempfile.mkstemp() |
170 | 76b200cf | Nikos Skalkotos | try:
|
171 | 55133880 | Nikos Skalkotos | os.close(samfd) |
172 | 76b200cf | Nikos Skalkotos | self.g.download(path, sam)
|
173 | 76b200cf | Nikos Skalkotos | |
174 | 76b200cf | Nikos Skalkotos | h = hivex.Hivex(sam) |
175 | 76b200cf | Nikos Skalkotos | |
176 | 76b200cf | Nikos Skalkotos | key = h.root() |
177 | 76b200cf | Nikos Skalkotos | # Navigate to /SAM/Domains/Account/Users/Names
|
178 | 76b200cf | Nikos Skalkotos | for child in ('SAM', 'Domains', 'Account', 'Users', 'Names'): |
179 | 76b200cf | Nikos Skalkotos | key = h.node_get_child(key, child) |
180 | 76b200cf | Nikos Skalkotos | |
181 | 76b200cf | Nikos Skalkotos | users = [h.node_name(x) for x in h.node_children(key)] |
182 | 76b200cf | Nikos Skalkotos | |
183 | 76b200cf | Nikos Skalkotos | finally:
|
184 | 76b200cf | Nikos Skalkotos | os.unlink(sam) |
185 | 76b200cf | Nikos Skalkotos | |
186 | 76b200cf | Nikos Skalkotos | # Filter out the guest account
|
187 | 76b200cf | Nikos Skalkotos | return filter(lambda x: x != "Guest", users) |
188 | aa2062ba | Nikos Skalkotos | |
189 | aa2062ba | Nikos Skalkotos | # vim: set sta sts=4 shiftwidth=4 sw=4 et ai : |