diff --git a/scripts/base/protocols/ntlm/main.bro b/scripts/base/protocols/ntlm/main.bro index ebe72ef9bf..0e3b869efc 100644 --- a/scripts/base/protocols/ntlm/main.bro +++ b/scripts/base/protocols/ntlm/main.bro @@ -39,7 +39,9 @@ export { 0x08c10002, # badLogonTime 0x08c20002, # passwordExpired 0xC0000022, # ACCESS_DENIED + 0xC0000061, # PRIVILEGE_NOT_HELD 0xC000006A, # WRONG_PASSWORD + 0xC000006D, # LOGON_FAILURE 0xC000006F, # INVALID_LOGON_HOURS 0xC0000070, # INVALID_WORKSTATION 0xC0000071, # PASSWORD_EXPIRED diff --git a/src/analyzer/protocol/ntlm/ntlm-analyzer.pac b/src/analyzer/protocol/ntlm/ntlm-analyzer.pac index bc55bf3c1c..be9f2532a9 100644 --- a/src/analyzer/protocol/ntlm/ntlm-analyzer.pac +++ b/src/analyzer/protocol/ntlm/ntlm-analyzer.pac @@ -97,13 +97,13 @@ refine connection NTLM_Conn += { RecordVal* result = new RecordVal(BifType::Record::NTLM::Negotiate); result->Assign(0, build_negotiate_flag_record(${val.flags})); - if ( ${val.flags.negotiate_oem_domain_supplied} ) + if ( ${val}->has_domain_name() ) result->Assign(1, utf16_bytestring_to_utf8_val(${val.domain_name.string.data})); - if ( ${val.flags.negotiate_oem_workstation_supplied} ) + if ( ${val}->has_workstation() ) result->Assign(2, utf16_bytestring_to_utf8_val(${val.workstation.string.data})); - if ( ${val.flags.negotiate_version} ) + if ( ${val}->has_version() ) result->Assign(3, build_version_record(${val.version})); BifEvent::generate_ntlm_negotiate(bro_analyzer(), @@ -118,13 +118,13 @@ refine connection NTLM_Conn += { RecordVal* result = new RecordVal(BifType::Record::NTLM::Challenge); result->Assign(0, build_negotiate_flag_record(${val.flags})); - if ( ${val.flags.request_target} ) + if ( ${val}->has_target_name() ) result->Assign(1, utf16_bytestring_to_utf8_val(${val.target_name.string.data})); - if ( ${val.flags.negotiate_version} ) + if ( ${val}->has_version() ) result->Assign(2, build_version_record(${val.version})); - if ( ${val.flags.negotiate_target_info} ) + if ( ${val}->has_target_info() ) result->Assign(3, build_av_record(${val.target_info})); BifEvent::generate_ntlm_challenge(bro_analyzer(), @@ -139,16 +139,16 @@ refine connection NTLM_Conn += { RecordVal* result = new RecordVal(BifType::Record::NTLM::Authenticate); result->Assign(0, build_negotiate_flag_record(${val.flags})); - if ( ${val.domain_name_fields.length} > 0 ) + if ( ${val}->has_domain_name() > 0 ) result->Assign(1, utf16_bytestring_to_utf8_val(${val.domain_name.string.data})); - if ( ${val.user_name_fields.length} > 0 ) + if ( ${val}->has_user_name() > 0 ) result->Assign(2, utf16_bytestring_to_utf8_val(${val.user_name.string.data})); - if ( ${val.workstation_fields.length} > 0 ) + if ( ${val}->has_workstation() > 0 ) result->Assign(3, utf16_bytestring_to_utf8_val(${val.workstation.string.data})); - if ( ${val.flags.negotiate_version} ) + if ( ${val}->has_version() ) result->Assign(4, build_version_record(${val.version})); BifEvent::generate_ntlm_authenticate(bro_analyzer(), diff --git a/src/analyzer/protocol/ntlm/ntlm-protocol.pac b/src/analyzer/protocol/ntlm/ntlm-protocol.pac index 136eddb9c7..c553330760 100644 --- a/src/analyzer/protocol/ntlm/ntlm-protocol.pac +++ b/src/analyzer/protocol/ntlm/ntlm-protocol.pac @@ -1,4 +1,9 @@ +function min(v1: uint32, v2: uint32): uint32 + %{ + return v1 < v2 ? v1 : v2; + %} + type NTLM_SSP_Token(is_orig: bool) = record { signature : bytestring &length=8; msg_type : uint32; @@ -14,13 +19,10 @@ type NTLM_Negotiate(offset: uint16) = record { flags : NTLM_Negotiate_Flags; domain_name_fields : NTLM_StringData; workstation_fields : NTLM_StringData; - version_present : case flags.negotiate_version of { - true -> version : NTLM_Version; - false -> no_version : empty; - }; payload : bytestring &restofdata; } &let { absolute_offset : uint16 = offsetof(payload) + offset; + version : NTLM_Version withinput payload &if(flags.negotiate_version && (absolute_offset < min(domain_name_fields.offset, workstation_fields.offset))); domain_name : NTLM_String(domain_name_fields, absolute_offset, flags.negotiate_unicode) withinput payload &if(flags.negotiate_oem_domain_supplied); workstation : NTLM_String(workstation_fields, absolute_offset, flags.negotiate_unicode) withinput payload &if(flags.negotiate_oem_workstation_supplied); }; @@ -31,13 +33,10 @@ type NTLM_Challenge(offset: uint16) = record { challenge : uint64; reserved : padding[8]; target_info_fields : NTLM_StringData; - version_present : case flags.negotiate_version of { - true -> version : NTLM_Version; - false -> no_version : empty; - }; payload : bytestring &restofdata; } &let { absolute_offset : uint16 = offsetof(payload) + offset; + version : NTLM_Version withinput payload &if(flags.negotiate_version && (absolute_offset < min(target_name_fields.offset, target_info_fields.offset))); target_name : NTLM_String(target_name_fields, absolute_offset, flags.negotiate_unicode) withinput payload &if(flags.request_target); target_info : NTLM_AV_Pair_Sequence(target_info_fields.offset - absolute_offset) withinput payload &if(flags.negotiate_target_info); }; @@ -50,10 +49,6 @@ type NTLM_Authenticate(offset: uint16) = record { workstation_fields : NTLM_StringData; encrypted_session_key_fields : NTLM_StringData; flags : NTLM_Negotiate_Flags; - version_present : case flags.negotiate_version of { - true -> version : NTLM_Version; - false -> no_version : empty; - }; # Windows NT, 2000, XP, and 2003 don't have the MIC field # TODO - figure out how to parse this for those that do have it @@ -62,6 +57,7 @@ type NTLM_Authenticate(offset: uint16) = record { payload : bytestring &restofdata; } &let { absolute_offset : uint16 = offsetof(payload) + offset; + version : NTLM_Version withinput payload &if(flags.negotiate_version && (absolute_offset < min(min(min(domain_name_fields.offset, user_name_fields.offset), workstation_fields.offset), encrypted_session_key_fields.offset))); domain_name : NTLM_String(domain_name_fields, absolute_offset, flags.negotiate_unicode) withinput payload &if(domain_name_fields.length > 0); user_name : NTLM_String(user_name_fields, absolute_offset, flags.negotiate_unicode) withinput payload &if(user_name_fields.length > 0); workstation : NTLM_String(workstation_fields, absolute_offset , flags.negotiate_unicode) withinput payload &if(workstation_fields.length > 0);