OSCP notesExtended library
Browse tracks

25, 465, 587 - SMTP

Telnet

telnet 10.0.0.3 25

Netcat

nc -n 10.0.0.3 25

Openssl (SMTPS)

openssl s_client -starttls smtp -crlf -connect 10.0.0.3:587
Parameters
  • s_client: SSL/TLS client program.
  • -starttls <protocol>: send the protocol-specific message(s) to switch to TLS for communication.
  • -crlf: translate a line feed from the terminal into CR+LF.

Enumeration

smtp-commands NSE Script

nmap -p 25,465,587 --script smtp-commands 10.0.0.3

smtp-enum-users NSE Script

nmap -p 25,465,587 --script smtp-enum-users 10.0.0.3

NTLM Information Disclosure

On Windows, with NTLM authentication enabled, sending a SMTP NTLM authentication request with null credentials will cause the remote service to respond with a NTLMSSP message disclosing information to include NetBIOS, DNS, and OS build version.

Manually

telnet example.com 587
...
>> HELO
250 example.com Hello [x.x.x.x]
>>AUTH NTLM 334
NTLM supported
>>TlRMTVNTUAABAAAAB4IIAAAAAAAAAAAAAAAAAAAAAAA=
334 TlRMTVNTUAACAAAACgAKADgAAAAFgooCBqqVKFrKPCMAAAAAAAAAAEgASABCAAAABgOAJQAAAA9JAEkAUwAwADEAAgAKAEkASQBTADAAMQABAAoASQBJAFMAMAAxAAQACgBJAEkAUwAwADEAAwAKAEkASQBTADAAMQAHAAgAHwMI0VPy1QEAAAAA

smtp-ntlm-info NSE Script

nmap -p 587 --script smtp-ntlm-info --script-args smtp-ntlm-info.domain=example.com 10.0.0.3

Commands

HELO        Identify to the SMTP server.
EHLO        Alternative HELO for Extended SMTP protocol.
MAIL FROM:  Sender's email address.
RCPT TO:    Recipient's email address.
DATA        Initiate message content transfer. Command is terminated with a line containing only a .
RSET        Reset the session. Connection will not be closed.
VRFY        Verify username or mailbox.
NOOP        No-op. Keeps connection open.
QUIT        Ends session.

Note: Sessions must start with HELO and end with QUIT.

Configuration files

sendmail.cf
submit.cf

Other

The following inline Python 3 helper opens a TCP socket and issues one VRFY request. Save it as vrfy.py; it is created from these notes, not a separate downloaded tool:

#!/usr/bin/env python3
import socket
import sys

if len(sys.argv) != 3:
    raise SystemExit("Usage: vrfy.py TARGET USER")

with socket.create_connection((sys.argv[1], 25), timeout=5) as connection:
    print(connection.recv(1024).decode(errors="replace"))
    connection.sendall(("VRFY " + sys.argv[2] + "\r\n").encode())
    print(connection.recv(1024).decode(errors="replace"))
python3 vrfy.py TARGET USER

Interpret the server's response using the enumeration guidance above; a disabled or ambiguous VRFY response does not establish whether the account exists.