Coverage for /root/GitHubProjects/impacket/impacket/dcerpc/v5/iphlp.py: 58%

# Coverage for /root/GitHubProjects/impacket/impacket/dcerpc/v5/iphlp.py : 58%

## 77 statements

Hot-keys on this page

r m x p toggle line displays

j k next/prev highlighted chunk

0 (zero) top of page

1 (one) first highlighted chunk

1# SECUREAUTH LABS. Copyright 2020 SecureAuth Corporation. All rights reserved.

2#

3# This software is provided under a slightly modified version

4# of the Apache Software License. See the accompanying LICENSE file

5# for more information.

6#

7# Authors:

8# Arseniy Sharoglazov <mohemiv@gmail.com> / Positive Technologies (https://www.ptsecurity.com/)

9#

10# Description:

11# Implementation of iphlpsvc.dll MSRPC calls (Service that offers IPv6 connectivity over an IPv4 network)

12

13 from socket import inet_aton

14

15 from impacket import uuid

16 from impacket import hresult_errors

17 from impacket.uuid import uuidtup_to_bin

18 from impacket.dcerpc.v5.dtypes import BYTE, ULONG, WSTR, GUID, NULL

19 from impacket.dcerpc.v5.ndr import NDRCALL, NDRUniConformantArray

20 from impacket.dcerpc.v5.rpcrt import DCERPCException

21

22 MSRPC_UUID_IPHLP_IP_TRANSITION = uuidtup_to_bin(('552d076a-cb29-4e44-8b6a-d15e59e2c0af', '1.0'))

23

24# RPC_IF_ALLOW_LOCAL_ONLY

25 MSRPC_UUID_IPHLP_TEREDO = uuidtup_to_bin(('ecbdb051-f208-46b9-8c8b-648d9d3f3944', '1.0'))

26 MSRPC_UUID_IPHLP_TEREDO_CONSUMER = uuidtup_to_bin(('1fff8faa-ec23-4e3f-a8ce-4b2f8707e636', '1.0'))

27

28 class DCERPCSessionError(DCERPCException):

29 def __init__(self, error_string=None, error_code=None, packet=None):

30 DCERPCException.__init__(self, error_string, error_code, packet)

31

32 def __str__( self ):

33 key = self.error_code

34 if key in hresult_errors.ERROR_MESSAGES:

35 error_msg_short = hresult_errors.ERROR_MESSAGES[key][0]

36 error_msg_verbose = hresult_errors.ERROR_MESSAGES[key][1]

37 return 'IPHLP SessionError: code: 0x%x - %s - %s' % (self.error_code, error_msg_short, error_msg_verbose)

38 else:

39 return 'IPHLP SessionError: unknown error code: 0x%x' % self.error_code

40

41################################################################################

42# CONSTANTS

43################################################################################

44

45# Notification types

46 NOTIFICATION_ISATAP_CONFIGURATION_CHANGE = 0

47 NOTIFICATION_PROCESS6TO4_CONFIGURATION_CHANGE = 1

48 NOTIFICATION_TEREDO_CONFIGURATION_CHANGE = 2

49 NOTIFICATION_IP_TLS_CONFIGURATION_CHANGE = 3

50 NOTIFICATION_PORT_CONFIGURATION_CHANGE = 4

51 NOTIFICATION_DNS64_CONFIGURATION_CHANGE = 5

52 NOTIFICATION_DA_SITE_MGR_LOCAL_CONFIGURATION_CHANGE_EX = 6

53

54################################################################################

55# STRUCTURES

56################################################################################

57

58 class BYTE_ARRAY(NDRUniConformantArray):

59 item = 'c'

60

61################################################################################

62# RPC CALLS

63################################################################################

64

65# Opnum 0

66 class IpTransitionProtocolApplyConfigChanges(NDRCALL):

67 opnum = 0

68 structure = (

69 ('NotificationNum', BYTE),

70 )

71

72 class IpTransitionProtocolApplyConfigChangesResponse(NDRCALL):

73 structure = (

74 ('ErrorCode', ULONG),

75 )

76

77# Opnum 1

78 class IpTransitionProtocolApplyConfigChangesEx(NDRCALL):

79 opnum = 1

80 structure = (

81 ('NotificationNum', BYTE),

82 ('DataLength', ULONG),

83 ('Data', BYTE_ARRAY),

84 )

85

86 class IpTransitionProtocolApplyConfigChangesExResponse(NDRCALL):

87 structure = (

88 ('ErrorCode', ULONG),

89 )

90

91# Opnum 2

92 class IpTransitionCreatev6Inv4Tunnel(NDRCALL):

93 opnum = 2

94 structure = (

95 ('LocalAddress', "4s=''"),

96 ('RemoteAddress', "4s=''"),

97 ('InterfaceName', WSTR),

98 )

99

100 class IpTransitionCreatev6Inv4TunnelResponse(NDRCALL):

101 structure = (

102 ('ErrorCode', ULONG),

103 )

104

105# Opnum 3

106 class IpTransitionDeletev6Inv4Tunnel(NDRCALL):

107 opnum = 3

108 structure = (

109 ('TunnelGuid', GUID),

110 )

111

112 class IpTransitionDeletev6Inv4TunnelResponse(NDRCALL):

113 structure = (

114 ('ErrorCode', ULONG),

115 )

116

117################################################################################

118# OPNUMs and their corresponding structures

119################################################################################

120

121 OPNUMS = {

122 0 : (IpTransitionProtocolApplyConfigChanges, IpTransitionProtocolApplyConfigChangesResponse),

123 1 : (IpTransitionProtocolApplyConfigChangesEx, IpTransitionProtocolApplyConfigChangesExResponse),

124 2 : (IpTransitionCreatev6Inv4Tunnel, IpTransitionCreatev6Inv4TunnelResponse),

125 3 : (IpTransitionDeletev6Inv4Tunnel, IpTransitionDeletev6Inv4TunnelResponse)

126}

127

128################################################################################

129# HELPER FUNCTIONS

130################################################################################

131 def checkNullString(string):

132 if string == NULL:

133 return string

134

135 if string[-1:] != '\x00':

136 return string + '\x00'

137 else:

138 return string

139

140# For all notifications except EX

141 def hIpTransitionProtocolApplyConfigChanges(dce, notification_num):

142 request = IpTransitionProtocolApplyConfigChanges()

143 request['NotificationNum'] = notification_num

144

145 return dce.request(request)

146

147# Only for NOTIFICATION_DA_SITE_MGR_LOCAL_CONFIGURATION_CHANGE_EX

148# No admin required

149 def hIpTransitionProtocolApplyConfigChangesEx(dce, notification_num, notification_data):

150 request = IpTransitionProtocolApplyConfigChangesEx()

151 request['NotificationNum'] = notification_num

152 request['DataLength'] = len(notification_data)

153 request['Data'] = notification_data

154

155 return dce.request(request)

156

157# Same as netsh interface ipv6 add v6v4tunnel "Test Tunnel" 192.168.0.1 10.0.0.5

158 def hIpTransitionCreatev6Inv4Tunnel(dce, local_address, remote_address, interface_name):

159 request = IpTransitionCreatev6Inv4Tunnel()

160 request['LocalAddress'] = inet_aton(local_address)

161 request['RemoteAddress'] = inet_aton(remote_address)

162

163 request['InterfaceName'] = checkNullString(interface_name)

164 request.fields['InterfaceName'].fields['MaximumCount'] = 256

165

166 return dce.request(request)

167

168 def hIpTransitionDeletev6Inv4Tunnel(dce, tunnel_guid):

169 request = IpTransitionDeletev6Inv4Tunnel()

170 request['TunnelGuid'] = uuid.string_to_bin(tunnel_guid)

171

172 return dce.request(request)