SMB1Command: Improved implementation of ReadCommandResponse

This commit is contained in:
Tal Aloni 2017-09-01 18:59:35 +03:00
parent d17866f6f9
commit 9a2b1949f0

View file

@ -6,7 +6,7 @@
*/ */
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Text; using System.IO;
using Utilities; using Utilities;
namespace SMBLibrary.SMB1 namespace SMBLibrary.SMB1
@ -180,23 +180,101 @@ namespace SMBLibrary.SMB1
case CommandName.SMB_COM_RENAME: case CommandName.SMB_COM_RENAME:
return new RenameResponse(buffer, offset); return new RenameResponse(buffer, offset);
case CommandName.SMB_COM_QUERY_INFORMATION: case CommandName.SMB_COM_QUERY_INFORMATION:
{
if (wordCount * 2 == QueryInformationResponse.ParameterLength)
{
return new QueryInformationResponse(buffer, offset); return new QueryInformationResponse(buffer, offset);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
case CommandName.SMB_COM_SET_INFORMATION: case CommandName.SMB_COM_SET_INFORMATION:
return new SetInformationResponse(buffer, offset); return new SetInformationResponse(buffer, offset);
case CommandName.SMB_COM_READ: case CommandName.SMB_COM_READ:
{
if (wordCount * 2 == ReadResponse.ParametersLength)
{
return new ReadResponse(buffer, offset); return new ReadResponse(buffer, offset);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
case CommandName.SMB_COM_WRITE: case CommandName.SMB_COM_WRITE:
{
if (wordCount * 2 == WriteResponse.ParametersLength)
{
return new WriteResponse(buffer, offset); return new WriteResponse(buffer, offset);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
case CommandName.SMB_COM_CHECK_DIRECTORY: case CommandName.SMB_COM_CHECK_DIRECTORY:
return new CheckDirectoryResponse(buffer, offset); return new CheckDirectoryResponse(buffer, offset);
case CommandName.SMB_COM_WRITE_RAW: case CommandName.SMB_COM_WRITE_RAW:
{
if (wordCount * 2 == WriteRawInterimResponse.ParametersLength)
{
return new WriteRawInterimResponse(buffer, offset); return new WriteRawInterimResponse(buffer, offset);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
case CommandName.SMB_COM_WRITE_COMPLETE: case CommandName.SMB_COM_WRITE_COMPLETE:
{
if (wordCount * 2 == WriteRawFinalResponse.ParametersLength)
{
return new WriteRawFinalResponse(buffer, offset); return new WriteRawFinalResponse(buffer, offset);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
case CommandName.SMB_COM_SET_INFORMATION2: case CommandName.SMB_COM_SET_INFORMATION2:
return new SetInformation2Response(buffer, offset); return new SetInformation2Response(buffer, offset);
case CommandName.SMB_COM_LOCKING_ANDX: case CommandName.SMB_COM_LOCKING_ANDX:
{
if (wordCount * 2 == LockingAndXResponse.ParametersLength)
{
return new LockingAndXResponse(buffer, offset); return new LockingAndXResponse(buffer, offset);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
case CommandName.SMB_COM_TRANSACTION: case CommandName.SMB_COM_TRANSACTION:
{ {
if (wordCount * 2 == TransactionInterimResponse.ParametersLength) if (wordCount * 2 == TransactionInterimResponse.ParametersLength)
@ -209,7 +287,20 @@ namespace SMBLibrary.SMB1
} }
} }
case CommandName.SMB_COM_ECHO: case CommandName.SMB_COM_ECHO:
{
if (wordCount * 2 == EchoResponse.ParametersLength)
{
return new EchoResponse(buffer, offset); return new EchoResponse(buffer, offset);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
case CommandName.SMB_COM_OPEN_ANDX: case CommandName.SMB_COM_OPEN_ANDX:
{ {
if (wordCount * 2 == OpenAndXResponse.ParametersLength) if (wordCount * 2 == OpenAndXResponse.ParametersLength)
@ -220,15 +311,45 @@ namespace SMBLibrary.SMB1
{ {
throw new NotImplementedException(); throw new NotImplementedException();
} }
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else else
{ {
throw new InvalidRequestException(); ; throw new InvalidDataException();
} }
} }
case CommandName.SMB_COM_READ_ANDX: case CommandName.SMB_COM_READ_ANDX:
{
if (wordCount * 2 == ReadAndXResponse.ParametersLength)
{
return new ReadAndXResponse(buffer, offset, isUnicode); return new ReadAndXResponse(buffer, offset, isUnicode);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
case CommandName.SMB_COM_WRITE_ANDX: case CommandName.SMB_COM_WRITE_ANDX:
{
if (wordCount * 2 == WriteAndXResponse.ParametersLength)
{
return new WriteAndXResponse(buffer, offset); return new WriteAndXResponse(buffer, offset);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
case CommandName.SMB_COM_TRANSACTION2: case CommandName.SMB_COM_TRANSACTION2:
{ {
if (wordCount * 2 == Transaction2InterimResponse.ParametersLength) if (wordCount * 2 == Transaction2InterimResponse.ParametersLength)
@ -246,20 +367,30 @@ namespace SMBLibrary.SMB1
return new TreeDisconnectResponse(buffer, offset); return new TreeDisconnectResponse(buffer, offset);
case CommandName.SMB_COM_NEGOTIATE: case CommandName.SMB_COM_NEGOTIATE:
{ {
// Both NegotiateResponse and NegotiateResponseExtended have WordCount set to 17
if (wordCount * 2 == NegotiateResponse.ParametersLength) if (wordCount * 2 == NegotiateResponse.ParametersLength)
{ {
return new NegotiateResponse(buffer, offset, isUnicode); ServerCapabilities capabilities = (ServerCapabilities)LittleEndianConverter.ToUInt32(buffer, offset + 20);
} if ((capabilities & ServerCapabilities.ExtendedSecurity) > 0)
else if (wordCount * 2 == NegotiateResponseExtended.ParametersLength)
{ {
return new NegotiateResponseExtended(buffer, offset); return new NegotiateResponseExtended(buffer, offset);
} }
else else
{ {
throw new InvalidRequestException(); return new NegotiateResponse(buffer, offset, isUnicode);
}
}
if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
} }
} }
case CommandName.SMB_COM_SESSION_SETUP_ANDX: case CommandName.SMB_COM_SESSION_SETUP_ANDX:
{
if (wordCount * 2 == SessionSetupAndXResponse.ParametersLength) if (wordCount * 2 == SessionSetupAndXResponse.ParametersLength)
{ {
return new SessionSetupAndXResponse(buffer, offset, isUnicode); return new SessionSetupAndXResponse(buffer, offset, isUnicode);
@ -268,14 +399,45 @@ namespace SMBLibrary.SMB1
{ {
return new SessionSetupAndXResponseExtended(buffer, offset, isUnicode); return new SessionSetupAndXResponseExtended(buffer, offset, isUnicode);
} }
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else else
{ {
throw new InvalidRequestException(); ; throw new InvalidDataException();
}
} }
case CommandName.SMB_COM_LOGOFF_ANDX: case CommandName.SMB_COM_LOGOFF_ANDX:
{
if (wordCount * 2 == LogoffAndXResponse.ParametersLength)
{
return new LogoffAndXResponse(buffer, offset); return new LogoffAndXResponse(buffer, offset);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
case CommandName.SMB_COM_TREE_CONNECT_ANDX: case CommandName.SMB_COM_TREE_CONNECT_ANDX:
{
if (wordCount * 2 == TreeConnectAndXResponse.ParametersLength)
{
return new TreeConnectAndXResponse(buffer, offset, isUnicode); return new TreeConnectAndXResponse(buffer, offset, isUnicode);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
case CommandName.SMB_COM_NT_TRANSACT: case CommandName.SMB_COM_NT_TRANSACT:
{ {
if (wordCount * 2 == NTTransactInterimResponse.ParametersLength) if (wordCount * 2 == NTTransactInterimResponse.ParametersLength)
@ -288,7 +450,20 @@ namespace SMBLibrary.SMB1
} }
} }
case CommandName.SMB_COM_NT_CREATE_ANDX: case CommandName.SMB_COM_NT_CREATE_ANDX:
{
if (wordCount * 2 == NTCreateAndXResponse.ParametersLength)
{
return new NTCreateAndXResponse(buffer, offset); return new NTCreateAndXResponse(buffer, offset);
}
else if (wordCount == 0)
{
return new ErrorResponse(commandName);
}
else
{
throw new InvalidDataException();
}
}
default: default:
throw new NotImplementedException("SMB Command 0x" + commandName.ToString("X")); throw new NotImplementedException("SMB Command 0x" + commandName.ToString("X"));
} }