diff --git a/ntlm.h b/ntlm.h index 1469633..ad83520 100644 --- a/ntlm.h +++ b/ntlm.h @@ -32,8 +32,8 @@ uint32 msgType; tSmbStrHeader uDomain; uint32 flags; uint8 challengeData[8]; -uint8 reserved[8]; -tSmbStrHeader emptyString; +uint32 context[2]; +tSmbStrHeader targetInfo; uint8 buffer[1024]; uint32 bufIndex; }tSmbNtlmAuthChallenge; diff --git a/ntlmsubr.c b/ntlmsubr.c index f9d2733..63cbed8 100644 --- a/ntlmsubr.c +++ b/ntlmsubr.c @@ -55,7 +55,32 @@ int ntlm_helper(int sock, struct query *ctl, const char *proto) if ((result = gen_recv(sock, msgbuf, sizeof msgbuf))) goto cancelfail; - (void)from64tobits (&challenge, msgbuf, sizeof(challenge)); + if ((result = from64tobits (&challenge, msgbuf, sizeof(challenge))) < 0 + || result < ((void *)&challenge.context - (void *)&challenge)) + { + report (stderr, GT_("could not decode BASE64 challenge\n")); + /* We do not goto cancelfail; the server has already sent the + * tagged reply, so the protocol exchange has ended, no need + * for us to send the asterisk. */ + return PS_AUTHFAIL; + } + + /* validate challenge: + * - ident + * - message type + * - that offset points into buffer + * - that offset + length does not wrap + * - that offset + length is not bigger than buffer */ + if (0 != memcmp("NTLMSSP", challenge.ident, 8) + || challenge.msgType != 2 + || challenge.uDomain.offset > result + || challenge.uDomain.offset + challenge.uDomain.len < challenge.uDomain.offset + || challenge.uDomain.offset + challenge.uDomain.len > result) + { + report (stderr, GT_("NTLM challenge contains invalid data.\n")); + result = PS_AUTHFAIL; + goto cancelfail; + } if (outlevel >= O_DEBUG) dumpSmbNtlmAuthChallenge(stdout, &challenge);