diff --git a/nselib/msrpc.lua b/nselib/msrpc.lua index 9e699a5eb..443474bf2 100644 --- a/nselib/msrpc.lua +++ b/nselib/msrpc.lua @@ -395,6 +395,65 @@ local function call_function(smbstate, opnum, arguments) return true, result end +---LANMAN API calls use different conventions than everything else, so make a separate function for them. +function call_lanmanapi(smbstate, opnum, server_type) + local status, result + local parameters = "" + local data + local convert, entry_count, available_entries + local entries = {} + local pos + + parameters = bin.pack("msrpctypes function that converts a ShareType to an english string. -- I implemented this as a proxy so scripts don't have to make direct calls to msrpctypes -- functions. diff --git a/nselib/smb.lua b/nselib/smb.lua index 050d380ee..d4e753624 100644 --- a/nselib/smb.lua +++ b/nselib/smb.lua @@ -1972,18 +1972,23 @@ end -- It is probably best to think of this as another protocol layer. This function will wrap SMB stuff around a -- MSRPC call, make the call, then unwrap the SMB stuff from it before returning. -- ---@param smb The SMB object associated with the connection ---@param function_parameters The parameter data to pass to the function. This is untested, since none of the --- transactions I've done have required parameters. ---@param function_data The data to send with the packet. This is basically the next protocol layer ---@param pipe [optional] The pipe to transact on. Default: "\PIPE\". +--@param smb The SMB object associated with the connection +--@param function_parameters The parameter data to pass to the function. This is untested, since none of the +-- transactions I've done have required parameters. +--@param function_data The data to send with the packet. This is basically the next protocol layer +--@param pipe [optional] The pipe to transact on. Default: "\PIPE\". +--@param no_setup [optional] If set, the 'setup' is set to 0 and some parameters are left off. This occurs while +-- using the LANMAN Remote API. Default: false. --@return (status, result) If status is false, result is an error message. Otherwise, result is a table -- containing 'parameters' and 'data', representing the parameters and data returned by the server. -function send_transaction_named_pipe(smb, function_parameters, function_data, pipe) +function send_transaction_named_pipe(smb, function_parameters, function_data, pipe, no_setup) local header1, header2, header3, header4, command, status, flags, flags2, pid_high, signature, unused, pid, mid local header, parameters, data - local parameters_offset, data_offset - local total_word_count, total_data_count, reserved1, parameter_count, parameter_offset, parameter_displacement, data_count, data_offset, data_displacement, setup_count, reserved2 + local parameter_offset = 0 + local parameter_size = 0 + local data_offset = 0 + local data_size = 0 + local total_word_count, total_data_count, reserved1, parameter_count, parameter_displacement, data_count, data_displacement, setup_count, reserved2 local response = {} if(pipe == nil) then @@ -1994,34 +1999,52 @@ function send_transaction_named_pipe(smb, function_parameters, function_data, pi header = smb_encode_header(smb, command_codes['SMB_COM_TRANSACTION']) -- 0x25 = SMB_COM_TRANSACTION -- 0x20 for SMB header, 0x01 for parameters header, 0x20 for parameters length, 0x02 for data header, 0x07 for "\PIPE\" - parameters_offset = 0x20 + 0x01 + 0x20 + 0x02 + (#pipe + 1) - data_offset = 0x20 + 0x01 + 0x20 + 0x02 + (#pipe + 1) + string.len(function_parameters) + if(function_parameters) then + parameter_offset = 0x20 + 0x01 + 0x20 + 0x02 + (#pipe + 1) + parameter_size = #function_parameters + end + + if(function_data) then + data_offset = 0x20 + 0x01 + 0x20 + 0x02 + (#pipe + 1) + parameter_size + data_size = #function_data + end -- Parameters are 0x20 bytes long. - parameters = bin.pack("