ruby_smb 2.0.3 → 2.0.8

Sign up to get free protection for your applications and to get access to all the features.
Files changed (70) hide show
  1. checksums.yaml +4 -4
  2. checksums.yaml.gz.sig +0 -0
  3. data.tar.gz.sig +1 -2
  4. data/.github/workflows/verify.yml +56 -0
  5. data/README.md +0 -1
  6. data/examples/delete_file.rb +0 -0
  7. data/examples/net_share_enum_all.rb +0 -0
  8. data/examples/pipes.rb +0 -0
  9. data/examples/rename_file.rb +0 -0
  10. data/lib/ruby_smb.rb +3 -2
  11. data/lib/ruby_smb/client.rb +12 -8
  12. data/lib/ruby_smb/client/authentication.rb +5 -10
  13. data/lib/ruby_smb/client/echo.rb +2 -4
  14. data/lib/ruby_smb/client/negotiation.rb +4 -6
  15. data/lib/ruby_smb/client/tree_connect.rb +2 -4
  16. data/lib/ruby_smb/client/utils.rb +16 -10
  17. data/lib/ruby_smb/client/winreg.rb +1 -1
  18. data/lib/ruby_smb/compression.rb +7 -0
  19. data/lib/ruby_smb/compression/lznt1.rb +164 -0
  20. data/lib/ruby_smb/dcerpc.rb +3 -1
  21. data/lib/ruby_smb/dcerpc/ndr.rb +97 -0
  22. data/lib/ruby_smb/dcerpc/netlogon.rb +101 -0
  23. data/lib/ruby_smb/dcerpc/netlogon/netr_server_authenticate3_request.rb +37 -0
  24. data/lib/ruby_smb/dcerpc/netlogon/netr_server_authenticate3_response.rb +26 -0
  25. data/lib/ruby_smb/dcerpc/netlogon/netr_server_password_set2_request.rb +37 -0
  26. data/lib/ruby_smb/dcerpc/netlogon/netr_server_password_set2_response.rb +23 -0
  27. data/lib/ruby_smb/dcerpc/netlogon/netr_server_req_challenge_request.rb +32 -0
  28. data/lib/ruby_smb/dcerpc/netlogon/netr_server_req_challenge_response.rb +24 -0
  29. data/lib/ruby_smb/dcerpc/request.rb +6 -0
  30. data/lib/ruby_smb/dcerpc/winreg.rb +2 -2
  31. data/lib/ruby_smb/dispatcher/socket.rb +1 -1
  32. data/lib/ruby_smb/error.rb +21 -5
  33. data/lib/ruby_smb/generic_packet.rb +11 -1
  34. data/lib/ruby_smb/smb1/file.rb +8 -15
  35. data/lib/ruby_smb/smb1/packet/trans2/find_first2_response.rb +0 -1
  36. data/lib/ruby_smb/smb1/packet/trans2/find_next2_response.rb +0 -1
  37. data/lib/ruby_smb/smb1/packet/trans2/open2_response.rb +1 -2
  38. data/lib/ruby_smb/smb1/packet/trans2/set_file_information_response.rb +1 -13
  39. data/lib/ruby_smb/smb1/pipe.rb +8 -8
  40. data/lib/ruby_smb/smb1/tree.rb +13 -9
  41. data/lib/ruby_smb/smb2/file.rb +8 -16
  42. data/lib/ruby_smb/smb2/packet/compression_transform_header.rb +4 -0
  43. data/lib/ruby_smb/smb2/pipe.rb +8 -8
  44. data/lib/ruby_smb/smb2/tree.rb +12 -8
  45. data/lib/ruby_smb/version.rb +1 -1
  46. data/spec/lib/ruby_smb/client_spec.rb +17 -12
  47. data/spec/lib/ruby_smb/compression/lznt1_spec.rb +32 -0
  48. data/spec/lib/ruby_smb/dcerpc/netlogon/netr_server_authenticate3_request_spec.rb +69 -0
  49. data/spec/lib/ruby_smb/dcerpc/netlogon/netr_server_authenticate3_response_spec.rb +53 -0
  50. data/spec/lib/ruby_smb/dcerpc/netlogon/netr_server_password_set2_request_spec.rb +69 -0
  51. data/spec/lib/ruby_smb/dcerpc/netlogon/netr_server_password_set2_response_spec.rb +37 -0
  52. data/spec/lib/ruby_smb/dcerpc/netlogon/netr_server_req_challenge_request_spec.rb +45 -0
  53. data/spec/lib/ruby_smb/dcerpc/netlogon/netr_server_req_challenge_response_spec.rb +37 -0
  54. data/spec/lib/ruby_smb/dcerpc/winreg_spec.rb +12 -0
  55. data/spec/lib/ruby_smb/error_spec.rb +34 -5
  56. data/spec/lib/ruby_smb/generic_packet_spec.rb +7 -0
  57. data/spec/lib/ruby_smb/smb1/file_spec.rb +2 -4
  58. data/spec/lib/ruby_smb/smb1/packet/trans2/find_first2_response_spec.rb +0 -1
  59. data/spec/lib/ruby_smb/smb1/packet/trans2/find_next2_response_spec.rb +0 -1
  60. data/spec/lib/ruby_smb/smb1/packet/trans2/open2_response_spec.rb +0 -5
  61. data/spec/lib/ruby_smb/smb1/packet/trans2/set_file_information_response_spec.rb +0 -6
  62. data/spec/lib/ruby_smb/smb1/pipe_spec.rb +23 -5
  63. data/spec/lib/ruby_smb/smb1/tree_spec.rb +22 -0
  64. data/spec/lib/ruby_smb/smb2/file_spec.rb +1 -3
  65. data/spec/lib/ruby_smb/smb2/pipe_spec.rb +2 -5
  66. data/spec/lib/ruby_smb/smb2/tree_spec.rb +23 -0
  67. data/spec/spec_helper.rb +1 -1
  68. metadata +42 -19
  69. metadata.gz.sig +0 -0
  70. data/.travis.yml +0 -6
@@ -55,7 +55,7 @@ module RubySMB
55
55
 
56
56
  # Read a packet off the wire and parse it into a string
57
57
  #
58
- # @param full_response [Boolean] whether to include the NetBios Session Service header in the repsonse
58
+ # @param full_response [Boolean] whether to include the NetBios Session Service header in the response
59
59
  # @return [String] the raw response (including the NetBios Session Service header if full_response is true)
60
60
  # @raise [RubySMB::Error::NetBiosSessionService] if there's an error reading the first 4 bytes,
61
61
  # which are assumed to be the NetBiosSessionService header.
@@ -16,23 +16,26 @@ module RubySMB
16
16
  # Raised when trying to parse raw binary into a Packet and the data
17
17
  # is invalid.
18
18
  class InvalidPacket < RubySMBError
19
+ attr_reader :status_code
19
20
  def initialize(args = nil)
20
21
  if args.nil?
21
22
  super
22
23
  elsif args.is_a? String
23
24
  super(args)
24
25
  elsif args.is_a? Hash
25
- expected_proto = args[:expected_proto] ? translate_protocol(args[:expected_proto]) : "???"
26
- expected_cmd = args[:expected_cmd] || "???"
27
- received_proto = args[:received_proto] ? translate_protocol(args[:received_proto]) : "???"
28
- received_cmd = args[:received_cmd] || "???"
26
+ expected_proto = args[:expected_proto] ? translate_protocol(args[:expected_proto]) : '???'
27
+ expected_cmd = args[:expected_cmd] || '???'
28
+ received_proto = args[:packet]&.packet_smb_version || '???'
29
+ received_cmd = get_cmd(args[:packet]) || '???'
30
+ @status_code = args[:packet]&.status_code
29
31
  super(
30
32
  "Expecting #{expected_proto} protocol "\
31
33
  "with command=#{expected_cmd}"\
32
34
  "#{(" (" + args[:expected_custom] + ")") if args[:expected_custom]}, "\
33
35
  "got #{received_proto} protocol "\
34
36
  "with command=#{received_cmd}"\
35
- "#{(" (" + args[:received_custom] + ")") if args[:received_custom]}"
37
+ "#{(" (" + args[:received_custom] + ")") if args[:received_custom]}"\
38
+ "#{(", Status: #{@status_code}") if @status_code}"
36
39
  )
37
40
  else
38
41
  raise ArgumentError, "InvalidPacket expects a String or a Hash, got a #{args.class}"
@@ -50,6 +53,19 @@ module RubySMB
50
53
  end
51
54
  end
52
55
  private :translate_protocol
56
+
57
+ def get_cmd(packet)
58
+ return nil unless packet
59
+ case packet.packet_smb_version
60
+ when 'SMB1'
61
+ packet.smb_header.command
62
+ when 'SMB2'
63
+ packet.smb2_header.command
64
+ else
65
+ nil
66
+ end
67
+ end
68
+ private :get_cmd
53
69
  end
54
70
 
55
71
  # Raised when a response packet has a NTStatus code that was unexpected.
@@ -49,7 +49,17 @@ module RubySMB
49
49
  when /SMB1/
50
50
  packet = RubySMB::SMB1::Packet::EmptyPacket.read(val)
51
51
  when /SMB2/
52
- packet = RubySMB::SMB2::Packet::ErrorPacket.read(val)
52
+ begin
53
+ packet = RubySMB::SMB2::Packet::ErrorPacket.read(val)
54
+ rescue RubySMB::Error::InvalidPacket
55
+ # Handle the case where an SMB2 error packet is expected, but the
56
+ # server sent an SMB1 empty packet instead. This behavior has been
57
+ # observed with older versions of Samba when something goes wrong
58
+ # on the server side. We just want to give it a chance and try to
59
+ # parse it as an SMB1 empty packet to keep information and avoid
60
+ # failing as much as possible.
61
+ packet = RubySMB::SMB1::Packet::EmptyPacket.read(val)
62
+ end
53
63
  else
54
64
  raise RubySMB::Error::InvalidPacket, 'Not a valid SMB packet'
55
65
  end
@@ -86,8 +86,7 @@ module RubySMB
86
86
  raise RubySMB::Error::InvalidPacket.new(
87
87
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
88
88
  expected_cmd: RubySMB::SMB1::Packet::CloseResponse::COMMAND,
89
- received_proto: response.smb_header.protocol,
90
- received_cmd: response.smb_header.command
89
+ packet: response
91
90
  )
92
91
  end
93
92
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
@@ -118,8 +117,7 @@ module RubySMB
118
117
  raise RubySMB::Error::InvalidPacket.new(
119
118
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
120
119
  expected_cmd: RubySMB::SMB1::Packet::ReadAndxResponse::COMMAND,
121
- received_proto: response.smb_header.protocol,
122
- received_cmd: response.smb_header.command
120
+ packet: response
123
121
  )
124
122
  end
125
123
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
@@ -167,8 +165,7 @@ module RubySMB
167
165
  raise RubySMB::Error::InvalidPacket.new(
168
166
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
169
167
  expected_cmd: RubySMB::SMB1::Packet::ReadAndxResponse::COMMAND,
170
- received_proto: response.smb_header.protocol,
171
- received_cmd: response.smb_header.command
168
+ packet: response
172
169
  )
173
170
  end
174
171
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
@@ -189,8 +186,7 @@ module RubySMB
189
186
  raise RubySMB::Error::InvalidPacket.new(
190
187
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
191
188
  expected_cmd: RubySMB::SMB1::Packet::Trans2::SetFileInformationResponse::COMMAND,
192
- received_proto: response.smb_header.protocol,
193
- received_cmd: response.smb_header.command
189
+ packet: response
194
190
  )
195
191
  end
196
192
  response.status_code
@@ -231,8 +227,7 @@ module RubySMB
231
227
  raise RubySMB::Error::InvalidPacket.new(
232
228
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
233
229
  expected_cmd: RubySMB::SMB1::Packet::WriteAndxResponse::COMMAND,
234
- received_proto: response.smb_header.protocol,
235
- received_cmd: response.smb_header.command
230
+ packet: response
236
231
  )
237
232
  end
238
233
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
@@ -271,8 +266,7 @@ module RubySMB
271
266
  raise RubySMB::Error::InvalidPacket.new(
272
267
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
273
268
  expected_cmd: RubySMB::SMB1::Packet::WriteAndxResponse::COMMAND,
274
- received_proto: response.smb_header.protocol,
275
- received_cmd: response.smb_header.command
269
+ packet: response
276
270
  )
277
271
  end
278
272
  response.parameter_block.count_low
@@ -290,8 +284,7 @@ module RubySMB
290
284
  raise RubySMB::Error::InvalidPacket.new(
291
285
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
292
286
  expected_cmd: RubySMB::SMB1::Packet::Trans2::SetFileInformationResponse::COMMAND,
293
- received_proto: response.smb_header.protocol,
294
- received_cmd: response.smb_header.command
287
+ packet: response
295
288
  )
296
289
  end
297
290
  response.status_code
@@ -308,7 +301,7 @@ module RubySMB
308
301
  passthrough_info_level = RubySMB::Fscc::FileInformation::FILE_RENAME_INFORMATION +
309
302
  RubySMB::Fscc::FileInformation::SMB_INFO_PASSTHROUGH
310
303
  rename_request.data_block.trans2_parameters.information_level = passthrough_info_level
311
- rename_request.data_block.trans2_data.info_level_struct.file_name = new_file_name.encode('utf-16le')
304
+ rename_request.data_block.trans2_data.info_level_struct.file_name = new_file_name
312
305
  set_trans2_params(rename_request)
313
306
  end
314
307
 
@@ -40,7 +40,6 @@ module RubySMB
40
40
 
41
41
  # The {RubySMB::SMB1::DataBlock} specific to this packet type.
42
42
  class DataBlock < RubySMB::SMB1::Packet::Trans2::DataBlock
43
- uint8 :name, label: 'Name', initial_value: 0x00
44
43
  string :pad1, length: -> { pad1_length }
45
44
  trans2_parameters :trans2_parameters, label: 'Trans2 Parameters'
46
45
  string :pad2, length: -> { pad2_length }
@@ -39,7 +39,6 @@ module RubySMB
39
39
 
40
40
  # The {RubySMB::SMB1::DataBlock} specific to this packet type.
41
41
  class DataBlock < RubySMB::SMB1::Packet::Trans2::DataBlock
42
- uint8 :name, label: 'Name', initial_value: 0x00
43
42
  string :pad1, length: -> { pad1_length }
44
43
  trans2_parameters :trans2_parameters, label: 'Trans2 Parameters'
45
44
  string :pad2, length: -> { pad2_length }
@@ -44,8 +44,7 @@ module RubySMB
44
44
  class DataBlock < RubySMB::SMB1::Packet::Trans2::DataBlock
45
45
  string :pad1, length: -> { pad1_length }
46
46
  trans2_parameters :trans2_parameters, label: 'Trans2 Parameters'
47
- string :pad2, length: -> { pad2_length }
48
- string :trans2_data, label: 'Trans2 Data', length: 0
47
+ # trans2_data: No data is sent by this message.
49
48
  end
50
49
 
51
50
  smb_header :smb_header
@@ -23,23 +23,11 @@ module RubySMB
23
23
  end
24
24
  end
25
25
 
26
- # The Trans2 Data Block for this particular Subcommand
27
- class Trans2Data < BinData::Record
28
-
29
- # Returns the length of the Trans2Data struct
30
- # in number of bytes
31
- def length
32
- do_num_bytes
33
- end
34
- end
35
-
36
26
  # The {RubySMB::SMB1::DataBlock} specific to this packet type.
37
27
  class DataBlock < RubySMB::SMB1::Packet::Trans2::DataBlock
38
- uint8 :name, label: 'Name', initial_value: 0x00
39
28
  string :pad1, length: -> { pad1_length }
40
29
  trans2_parameters :trans2_parameters, label: 'Trans2 Parameters'
41
- string :pad2, length: -> { pad2_length }
42
- trans2_data :trans2_data, label: 'Trans2 Data'
30
+ # trans2_data: No data is sent by this message.
43
31
  end
44
32
 
45
33
  smb_header :smb_header
@@ -16,12 +16,14 @@ module RubySMB
16
16
  def initialize(tree:, response:, name:)
17
17
  raise ArgumentError, 'No Name Provided' if name.nil?
18
18
  case name
19
- when 'srvsvc'
19
+ when 'netlogon', '\\netlogon'
20
+ extend RubySMB::Dcerpc::Netlogon
21
+ when 'srvsvc', '\\srvsvc'
20
22
  extend RubySMB::Dcerpc::Srvsvc
21
- when 'winreg'
22
- extend RubySMB::Dcerpc::Winreg
23
- when 'svcctl'
23
+ when 'svcctl', '\\svcctl'
24
24
  extend RubySMB::Dcerpc::Svcctl
25
+ when 'winreg', '\\winreg'
26
+ extend RubySMB::Dcerpc::Winreg
25
27
  end
26
28
  super(tree: tree, response: response, name: name)
27
29
  end
@@ -43,8 +45,7 @@ module RubySMB
43
45
  raise RubySMB::Error::InvalidPacket.new(
44
46
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
45
47
  expected_cmd: RubySMB::SMB1::Packet::Trans::PeekNmpipeRequest::COMMAND,
46
- received_proto: response.smb_header.protocol,
47
- received_cmd: response.smb_header.command
48
+ packet: response
48
49
  )
49
50
  end
50
51
 
@@ -102,8 +103,7 @@ module RubySMB
102
103
  raise RubySMB::Error::InvalidPacket.new(
103
104
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
104
105
  expected_cmd: RubySMB::SMB1::Packet::Trans::TransactNmpipeResponse::COMMAND,
105
- received_proto: trans_nmpipe_response.smb_header.protocol,
106
- received_cmd: trans_nmpipe_response.smb_header.command
106
+ packet: trans_nmpipe_response
107
107
  )
108
108
  end
109
109
  unless [WindowsError::NTStatus::STATUS_SUCCESS,
@@ -49,13 +49,20 @@ module RubySMB
49
49
  raise RubySMB::Error::InvalidPacket.new(
50
50
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
51
51
  expected_cmd: RubySMB::SMB1::Packet::TreeDisconnectResponse::COMMAND,
52
- received_proto: response.smb_header.protocol,
53
- received_cmd: response.smb_header.command
52
+ packet: response
54
53
  )
55
54
  end
56
55
  response.status_code
57
56
  end
58
57
 
58
+ def open_pipe(opts)
59
+ # Make sure we don't modify the caller's hash options
60
+ opts = opts.dup
61
+ opts[:filename] = opts[:filename].dup
62
+ opts[:filename].prepend('\\') unless opts[:filename].start_with?('\\')
63
+ open_file(opts)
64
+ end
65
+
59
66
  # Open a file on the remote share.
60
67
  #
61
68
  # @example
@@ -135,15 +142,14 @@ module RubySMB
135
142
  raise RubySMB::Error::InvalidPacket.new(
136
143
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
137
144
  expected_cmd: RubySMB::SMB1::Packet::NtCreateAndxResponse::COMMAND,
138
- received_proto: response.smb_header.protocol,
139
- received_cmd: response.smb_header.command
145
+ packet: response
140
146
  )
141
147
  end
142
148
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
143
149
  raise RubySMB::Error::UnexpectedStatusCode, response.status_code
144
150
  end
145
151
 
146
- case response.parameter_block.resource_type
152
+ case response.parameter_block.resource_type
147
153
  when RubySMB::SMB1::ResourceType::BYTE_MODE_PIPE, RubySMB::SMB1::ResourceType::MESSAGE_MODE_PIPE
148
154
  RubySMB::SMB1::Pipe.new(name: filename, tree: self, response: response)
149
155
  when RubySMB::SMB1::ResourceType::DISK
@@ -195,8 +201,7 @@ module RubySMB
195
201
  raise RubySMB::Error::InvalidPacket.new(
196
202
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
197
203
  expected_cmd: RubySMB::SMB1::Packet::Trans2::FindFirst2Response::COMMAND,
198
- received_proto: response.smb_header.protocol,
199
- received_cmd: response.smb_header.command
204
+ packet: response
200
205
  )
201
206
  end
202
207
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
@@ -230,8 +235,7 @@ module RubySMB
230
235
  raise RubySMB::Error::InvalidPacket.new(
231
236
  expected_proto: RubySMB::SMB1::SMB_PROTOCOL_ID,
232
237
  expected_cmd: RubySMB::SMB1::Packet::Trans2::FindNext2Response::COMMAND,
233
- received_proto: response.smb_header.protocol,
234
- received_cmd: response.smb_header.command
238
+ packet: response
235
239
  )
236
240
  end
237
241
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
@@ -95,8 +95,7 @@ module RubySMB
95
95
  raise RubySMB::Error::InvalidPacket.new(
96
96
  expected_proto: RubySMB::SMB2::SMB2_PROTOCOL_ID,
97
97
  expected_cmd: RubySMB::SMB2::Packet::CloseResponse::COMMAND,
98
- received_proto: response.smb2_header.protocol,
99
- received_cmd: response.smb2_header.command
98
+ packet: response
100
99
  )
101
100
  end
102
101
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
@@ -130,8 +129,7 @@ module RubySMB
130
129
  raise RubySMB::Error::InvalidPacket.new(
131
130
  expected_proto: RubySMB::SMB2::SMB2_PROTOCOL_ID,
132
131
  expected_cmd: RubySMB::SMB2::Packet::ReadResponse::COMMAND,
133
- received_proto: response.smb2_header.protocol,
134
- received_cmd: response.smb2_header.command
132
+ packet: response
135
133
  )
136
134
  end
137
135
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
@@ -153,8 +151,7 @@ module RubySMB
153
151
  raise RubySMB::Error::InvalidPacket.new(
154
152
  expected_proto: RubySMB::SMB2::SMB2_PROTOCOL_ID,
155
153
  expected_cmd: RubySMB::SMB2::Packet::ReadResponse::COMMAND,
156
- received_proto: response.smb2_header.protocol,
157
- received_cmd: response.smb2_header.command
154
+ packet: response
158
155
  )
159
156
  end
160
157
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
@@ -189,8 +186,7 @@ module RubySMB
189
186
  raise RubySMB::Error::InvalidPacket.new(
190
187
  expected_proto: RubySMB::SMB2::SMB2_PROTOCOL_ID,
191
188
  expected_cmd: RubySMB::SMB2::Packet::ReadResponse::COMMAND,
192
- received_proto: response.smb2_header.protocol,
193
- received_cmd: response.smb2_header.command
189
+ packet: response
194
190
  )
195
191
  end
196
192
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
@@ -210,8 +206,7 @@ module RubySMB
210
206
  raise RubySMB::Error::InvalidPacket.new(
211
207
  expected_proto: RubySMB::SMB2::SMB2_PROTOCOL_ID,
212
208
  expected_cmd: RubySMB::SMB2::Packet::SetInfoResponse::COMMAND,
213
- received_proto: response.smb2_header.protocol,
214
- received_cmd: response.smb2_header.command
209
+ packet: response
215
210
  )
216
211
  end
217
212
  response.smb2_header.nt_status.to_nt_status
@@ -262,8 +257,7 @@ module RubySMB
262
257
  raise RubySMB::Error::InvalidPacket.new(
263
258
  expected_proto: RubySMB::SMB2::SMB2_PROTOCOL_ID,
264
259
  expected_cmd: RubySMB::SMB2::Packet::WriteResponse::COMMAND,
265
- received_proto: response.smb2_header.protocol,
266
- received_cmd: response.smb2_header.command
260
+ packet: response
267
261
  )
268
262
  end
269
263
  status = response.smb2_header.nt_status.to_nt_status
@@ -297,8 +291,7 @@ module RubySMB
297
291
  raise RubySMB::Error::InvalidPacket.new(
298
292
  expected_proto: RubySMB::SMB2::SMB2_PROTOCOL_ID,
299
293
  expected_cmd: RubySMB::SMB2::Packet::WriteResponse::COMMAND,
300
- received_proto: response.smb2_header.protocol,
301
- received_cmd: response.smb2_header.command
294
+ packet: response
302
295
  )
303
296
  end
304
297
  unless response.status_code == WindowsError::NTStatus::STATUS_SUCCESS
@@ -319,8 +312,7 @@ module RubySMB
319
312
  raise RubySMB::Error::InvalidPacket.new(
320
313
  expected_proto: RubySMB::SMB2::SMB2_PROTOCOL_ID,
321
314
  expected_cmd: RubySMB::SMB2::Packet::SetInfoResponse::COMMAND,
322
- received_proto: response.smb2_header.protocol,
323
- received_cmd: response.smb2_header.command
315
+ packet: response
324
316
  )
325
317
  end
326
318
  response.smb2_header.nt_status.to_nt_status
@@ -3,6 +3,9 @@ module RubySMB
3
3
  module Packet
4
4
  # An SMB2 COMPRESSION_TRANSFORM_HEADER Packet as defined in
5
5
  # [2.2.42 SMB2 COMPRESSION_TRANSFORM_HEADER](https://docs.microsoft.com/en-us/openspecs/windows_protocols/ms-smb2/1d435f21-9a21-4f4c-828e-624a176cf2a0)
6
+ # NOTE: On 2021-04-06 the official documentation split the definition of COMPRESSION_TRANSFORM_HEADER into the following two variants:
7
+ # * SMB2_COMPRESSION_TRANSFORM_HEADER_CHAINED
8
+ # * SMB2_COMPRESSION_TRANSFORM_HEADER_UNCHAINED
6
9
  class CompressionTransformHeader < BinData::Record
7
10
  endian :little
8
11
 
@@ -11,6 +14,7 @@ module RubySMB
11
14
  uint16 :compression_algorithm, label: 'Compression Algorithm'
12
15
  uint16 :flags, label: 'Flags'
13
16
  uint32 :offset, label: 'Offset / Length'
17
+ array :compressed_data, label: 'Compressed Data', type: :uint8, read_until: :eof
14
18
  end
15
19
 
16
20
  # An SMB2 SMB2_COMPRESSION_TRANSFORM_HEADER_PAYLOAD Packet as defined in
@@ -13,12 +13,14 @@ module RubySMB
13
13
  def initialize(tree:, response:, name:)
14
14
  raise ArgumentError, 'No Name Provided' if name.nil?
15
15
  case name
16
- when 'srvsvc'
16
+ when 'netlogon', '\\netlogon'
17
+ extend RubySMB::Dcerpc::Netlogon
18
+ when 'srvsvc', '\\srvsvc'
17
19
  extend RubySMB::Dcerpc::Srvsvc
18
- when 'winreg'
19
- extend RubySMB::Dcerpc::Winreg
20
- when 'svcctl'
20
+ when 'svcctl', '\\svcctl'
21
21
  extend RubySMB::Dcerpc::Svcctl
22
+ when 'winreg', '\\winreg'
23
+ extend RubySMB::Dcerpc::Winreg
22
24
  end
23
25
  super(tree: tree, response: response, name: name)
24
26
  end
@@ -42,8 +44,7 @@ module RubySMB
42
44
  raise RubySMB::Error::InvalidPacket.new(
43
45
  expected_proto: RubySMB::SMB2::SMB2_PROTOCOL_ID,
44
46
  expected_cmd: RubySMB::SMB2::Packet::IoctlResponse::COMMAND,
45
- received_proto: response.smb2_header.protocol,
46
- received_cmd: response.smb2_header.command
47
+ packet: response
47
48
  )
48
49
  end
49
50
 
@@ -100,8 +101,7 @@ module RubySMB
100
101
  raise RubySMB::Error::InvalidPacket.new(
101
102
  expected_proto: RubySMB::SMB2::SMB2_PROTOCOL_ID,
102
103
  expected_cmd: RubySMB::SMB2::Packet::IoctlRequest::COMMAND,
103
- received_proto: ioctl_response.smb2_header.protocol,
104
- received_cmd: ioctl_response.smb2_header.command
104
+ packet: ioctl_response
105
105
  )
106
106
  end
107
107
  unless [WindowsError::NTStatus::STATUS_SUCCESS,