1###############################################################################
2#  Tested so far:
3# IWbemLevel1Login::EstablishPosition
4# IWbemLevel1Login::RequestChallenge
5# IWbemLevel1Login::WBEMLogin
6# IWbemLevel1Login::NTLMLogin
7# IWbemServices::OpenNamespace
8# IWbemServices::ExecQuery
9# IWbemServices::GetObject
10#
11# Since DCOM is more high level, I'll always use the helper classes
12#
13#  Not yet:
14#
15# IWbemServices::CancelAsyncCall
16# IWbemServices::QueryObjectSink
17# IWbemServices::GetObjectAsync
18# IWbemServices::PutClass
19# IWbemServices::PutClassAsync
20# IWbemServices::DeleteClass
21# IWbemServices::DeleteClassAsync
22# IWbemServices::CreateClassEnum
23# IWbemServices::CreateClassEnumAsync
24# IWbemServices::PutInstance
25# IWbemServices::PutInstanceAsync
26# IWbemServices::DeleteInstance
27# IWbemServices::DeleteInstanceAsync
28# IWbemServices::CreateInstanceEnum
29# IWbemServices::CreateInstanceEnumAsync
30# IWbemServices::ExecQueryAsync
31# IWbemServices::ExecNotificationQuery
32# IWbemServices::ExecNotificationQueryAsync
33# IWbemServices::ExecMethod
34# IWbemServices::ExecMethodAsync
35#
36# Shouldn't dump errors against a win7
37#
38################################################################################
39
40import sys
41import unittest
42import ConfigParser
43from struct import pack, unpack
44
45from impacket.dcerpc.v5 import transport
46from impacket.dcerpc.v5 import epm, dcomrt
47from impacket.dcerpc.v5.dcom import wmi
48from impacket.dcerpc.v5.dtypes import NULL
49from impacket.dcerpc.v5.rpcrt import RPC_C_AUTHN_LEVEL_NONE
50from impacket.dcerpc.v5.dcomrt import DCOMConnection
51from impacket.winregistry import hexdump
52from impacket.uuid import string_to_bin, uuidtup_to_bin, generate
53from impacket import system_errors, ntlm
54
55class WMITests(unittest.TestCase):
56    def tes_activation(self):
57        dcom = DCOMConnection(self.machine, self.username, self.password, self.domain, self.lmhash, self.nthash)
58        iInterface = dcom.CoCreateInstanceEx(wmi.CLSID_WbemLevel1Login,wmi.IID_IWbemLoginClientID)
59        dcom.disconnect()
60
61    def test_IWbemLevel1Login_EstablishPosition(self):
62        dcom = DCOMConnection(self.machine, self.username, self.password, self.domain, self.lmhash, self.nthash)
63        iInterface = dcom.CoCreateInstanceEx(wmi.CLSID_WbemLevel1Login,wmi.IID_IWbemLevel1Login)
64        iWbemLevel1Login = wmi.IWbemLevel1Login(iInterface)
65        resp = iWbemLevel1Login.EstablishPosition()
66        print resp
67        dcom.disconnect()
68
69    def test_IWbemLevel1Login_RequestChallenge(self):
70        dcom = DCOMConnection(self.machine, self.username, self.password, self.domain, self.lmhash, self.nthash)
71        iInterface = dcom.CoCreateInstanceEx(wmi.CLSID_WbemLevel1Login,wmi.IID_IWbemLevel1Login)
72        iWbemLevel1Login = wmi.IWbemLevel1Login(iInterface)
73        try:
74            resp = iWbemLevel1Login.RequestChallenge()
75            print resp
76        except Exception, e:
77            if str(e).find('WBEM_E_NOT_SUPPORTED') < 0:
78                dcom.disconnect()
79                raise
80        dcom.disconnect()
81
82    def test_IWbemLevel1Login_WBEMLogin(self):
83        dcom = DCOMConnection(self.machine, self.username, self.password, self.domain, self.lmhash, self.nthash)
84        iInterface = dcom.CoCreateInstanceEx(wmi.CLSID_WbemLevel1Login,wmi.IID_IWbemLevel1Login)
85        iWbemLevel1Login = wmi.IWbemLevel1Login(iInterface)
86        try:
87            resp = iWbemLevel1Login.WBEMLogin()
88            print resp
89        except Exception, e:
90            if str(e).find('E_NOTIMPL') < 0:
91                dcom.disconnect()
92                raise
93        dcom.disconnect()
94
95    def test_IWbemLevel1Login_NTLMLogin(self):
96        dcom = DCOMConnection(self.machine, self.username, self.password, self.domain, self.lmhash, self.nthash)
97        iInterface = dcom.CoCreateInstanceEx(wmi.CLSID_WbemLevel1Login,wmi.IID_IWbemLevel1Login)
98        iWbemLevel1Login = wmi.IWbemLevel1Login(iInterface)
99        resp = iWbemLevel1Login.NTLMLogin('\\\\%s\\root\\cimv2' % self.machine, NULL, NULL)
100        print resp
101        dcom.disconnect()
102
103    def tes_IWbemServices_OpenNamespace(self):
104        # Not working
105        dcom = DCOMConnection(self.machine, self.username, self.password, self.domain, self.lmhash, self.nthash)
106        iInterface = dcom.CoCreateInstanceEx(wmi.CLSID_WbemLevel1Login,wmi.IID_IWbemLevel1Login)
107        iWbemLevel1Login = wmi.IWbemLevel1Login(iInterface)
108        iWbemServices= iWbemLevel1Login.NTLMLogin('//./ROOT', NULL, NULL)
109        try:
110            resp = iWbemServices.OpenNamespace('__Namespace')
111            print resp
112        except Exception, e:
113            dcom.disconnect()
114            raise
115        dcom.disconnect()
116
117    def test_IWbemServices_GetObject(self):
118        dcom = DCOMConnection(self.machine, self.username, self.password, self.domain, self.lmhash, self.nthash)
119        iInterface = dcom.CoCreateInstanceEx(wmi.CLSID_WbemLevel1Login,wmi.IID_IWbemLevel1Login)
120        iWbemLevel1Login = wmi.IWbemLevel1Login(iInterface)
121        iWbemServices= iWbemLevel1Login.NTLMLogin('\\\\%s\\root\\cimv2' % self.machine, NULL, NULL)
122        iWbemLevel1Login.RemRelease()
123
124        classObject,_ = iWbemServices.GetObject('Win32_Process')
125
126        dcom.disconnect()
127
128    def test_IWbemServices_ExecQuery(self):
129        dcom = DCOMConnection(self.machine, self.username, self.password, self.domain, self.lmhash, self.nthash)
130        iInterface = dcom.CoCreateInstanceEx(wmi.CLSID_WbemLevel1Login,wmi.IID_IWbemLevel1Login)
131        iWbemLevel1Login = wmi.IWbemLevel1Login(iInterface)
132        iWbemServices= iWbemLevel1Login.NTLMLogin('\\\\%s\\root\\cimv2' % self.machine, NULL, NULL)
133        #classes = [ 'Win32_Account', 'Win32_UserAccount', 'Win32_Group', 'Win32_SystemAccount', 'Win32_Service']
134        classes = [ 'Win32_Service']
135        for classn in classes:
136            print "Reading %s " % classn
137            try:
138                iEnumWbemClassObject = iWbemServices.ExecQuery('SELECT * from %s' % classn)
139                done = False
140                while done is False:
141                    try:
142                        iEnumWbemClassObject.Next(0xffffffff,1)
143                    except Exception, e:
144                        if str(e).find('S_FALSE') < 0:
145                            print e
146                        else:
147                            done = True
148                            pass
149            except Exception, e:
150                if str(e).find('S_FALSE') < 0:
151                    print e
152        dcom.disconnect()
153
154    def test_IWbemServices_ExecMethod(self):
155        dcom = DCOMConnection(self.machine, self.username, self.password, self.domain, self.lmhash, self.nthash)
156        iInterface = dcom.CoCreateInstanceEx(wmi.CLSID_WbemLevel1Login,wmi.IID_IWbemLevel1Login)
157        iWbemLevel1Login = wmi.IWbemLevel1Login(iInterface)
158        iWbemServices= iWbemLevel1Login.NTLMLogin('\\\\%s\\root\\cimv2' % self.machine, NULL, NULL)
159
160        #classObject,_ = iWbemServices.GetObject('WinMgmts:Win32_LogicalDisk='C:'')
161        classObject,_ = iWbemServices.GetObject('Win32_Process')
162        obj = classObject.Create('notepad.exe', 'c:\\', None)
163        handle = obj.getProperties()['ProcessId']['value']
164
165        iEnumWbemClassObject = iWbemServices.ExecQuery('SELECT * from Win32_Process where handle = %s' % handle)
166        oooo = iEnumWbemClassObject.Next(0xffffffff,1)[0]
167        #import time
168        #time.sleep(5)
169        owner = oooo.Terminate(1)
170
171        #iEnumWbemClassObject = iWbemServices.ExecQuery('SELECT * from Win32_Group where name = "testGroup0"')
172        #oooo = iEnumWbemClassObject.Next(0xffffffff,1)[0]
173        #import time
174        #owner = oooo.Rename('testGroup1')
175
176        #iEnumWbemClassObject = iWbemServices.ExecQuery('SELECT * from Win32_Share where name = "Users"')
177        #oooo = iEnumWbemClassObject.Next(0xffffffff,1)[0]
178        #import time
179        #owner = oooo.GetAccessMask()
180        #print owner.getProperties()
181
182        #iEnumWbemClassObject = iWbemServices.ExecQuery('SELECT * from Win32_Share where name = "Users"')
183        #oooo = iEnumWbemClassObject.Next(0xffffffff,1)[0]
184        #obj = oooo.SetShareInfo(0, 'HOLA BETO', None)
185
186        #classObject,_ = iWbemServices.GetObject('Win32_ShadowCopy')
187        #obj = classObject.Create('C:\\', 'ClientAccessible')
188        #print obj.getProperties()
189
190        # this one doesn't work
191        #classObject,_ = iWbemServices.GetObject('Win32_Service')
192        #obj = classObject.Create('BETOSERVICE', 'Beto Service', 'c:\\beto', 16, 0, 'Manual', 0, None, None, None, None, None)
193        #print obj.getProperties()
194
195        dcom.disconnect()
196
197class TCPTransport(WMITests):
198    def setUp(self):
199        WMITests.setUp(self)
200        configFile = ConfigParser.ConfigParser()
201        configFile.read('dcetests.cfg')
202        self.username = configFile.get('TCPTransport', 'username')
203        self.domain   = configFile.get('TCPTransport', 'domain')
204        self.serverName = configFile.get('TCPTransport', 'servername')
205        self.password = configFile.get('TCPTransport', 'password')
206        self.machine  = configFile.get('TCPTransport', 'machine')
207        self.hashes   = configFile.get('TCPTransport', 'hashes')
208        self.stringBinding = r'ncacn_ip_tcp:%s' % self.machine
209        self.ts = ('8a885d04-1ceb-11c9-9fe8-08002b104860', '2.0')
210        if len(self.hashes) > 0:
211            self.lmhash, self.nthash = self.hashes.split(':')
212        else:
213            self.lmhash = ''
214            self.nthash = ''
215
216class TCPTransport64(WMITests):
217    def setUp(self):
218        WMITests.setUp(self)
219        configFile = ConfigParser.ConfigParser()
220        configFile.read('dcetests.cfg')
221        self.username = configFile.get('TCPTransport', 'username')
222        self.domain   = configFile.get('TCPTransport', 'domain')
223        self.serverName = configFile.get('TCPTransport', 'servername')
224        self.password = configFile.get('TCPTransport', 'password')
225        self.machine  = configFile.get('TCPTransport', 'machine')
226        self.hashes   = configFile.get('TCPTransport', 'hashes')
227        self.stringBinding = r'ncacn_ip_tcp:%s' % self.machine
228        self.ts = ('71710533-BEBA-4937-8319-B5DBEF9CCC36', '1.0')
229        if len(self.hashes) > 0:
230            self.lmhash, self.nthash = self.hashes.split(':')
231        else:
232            self.lmhash = ''
233            self.nthash = ''
234
235# Process command-line arguments.
236if __name__ == '__main__':
237    import sys
238    if len(sys.argv) > 1:
239        testcase = sys.argv[1]
240        suite = unittest.TestLoader().loadTestsFromTestCase(globals()[testcase])
241    else:
242        suite = unittest.TestLoader().loadTestsFromTestCase(TCPTransport)
243        suite.addTests(unittest.TestLoader().loadTestsFromTestCase(TCPTransport64))
244    unittest.TextTestRunner(verbosity=1).run(suite)
245