> For the complete documentation index, see [llms.txt](https://docs.h4rithd.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.h4rithd.com/tcp/25-smtp.md).

# SMTP | 25, 587

<table><thead><tr><th width="134" align="right">Command</th><th>Description</th></tr></thead><tbody><tr><td align="right">HELO</td><td>Introduces the client to the server (used in SMTP).</td></tr><tr><td align="right">EHLO</td><td>Extended HELO; used in ESMTP to request server capabilities.</td></tr><tr><td align="right">MAIL FROM:</td><td>Specifies the sender's email address.</td></tr><tr><td align="right">RCPT TO:</td><td>Specifies the recipient's email address.</td></tr><tr><td align="right">DATA</td><td>Indicates that the email content (headers + body) follows.</td></tr><tr><td align="right">RSET</td><td>Resets the current mail transaction.</td></tr><tr><td align="right">VRFY</td><td>Verifies if a user/email address exists on the server.</td></tr><tr><td align="right">EXPN</td><td>Expands a mailing list to show all recipients.</td></tr><tr><td align="right">NOOP</td><td>No operation; used to keep the connection alive.</td></tr><tr><td align="right">QUIT</td><td>Terminates the SMTP session.</td></tr><tr><td align="right">STARTTLS</td><td>Initiates a TLS-secured connection (if supported).</td></tr><tr><td align="right">AUTH</td><td>Begins the authentication process (e.g, LOGIN, PLAIN, CRAM-MD5).</td></tr></tbody></table>

<table><thead><tr><th width="90" align="right">Code</th><th width="131">Type</th><th>Meaning</th></tr></thead><tbody><tr><td align="right">211</td><td>Success</td><td>System status or help reply</td></tr><tr><td align="right">214</td><td>Success</td><td>Help message</td></tr><tr><td align="right">220</td><td>Success</td><td>Service ready</td></tr><tr><td align="right">221</td><td>Success</td><td>Service closing transmission channel</td></tr><tr><td align="right">250</td><td>Success</td><td>Requested action completed</td></tr><tr><td align="right">251</td><td>Success</td><td>User not local; will forward</td></tr><tr><td align="right">252</td><td>Success</td><td>Cannot verify user, but will accept message</td></tr><tr><td align="right">354</td><td>Intermediate</td><td>Start mail input; end with .</td></tr><tr><td align="right">421</td><td>Error</td><td>Service not available, closing transmission channel</td></tr><tr><td align="right">450</td><td>Error</td><td>Requested action not taken: mailbox unavailable</td></tr><tr><td align="right">451</td><td>Error</td><td>Requested action aborted: local error in processing</td></tr><tr><td align="right">452</td><td>Error</td><td>Requested action not taken: insufficient system storage</td></tr><tr><td align="right">500</td><td>Error</td><td>Syntax error, command unrecognized</td></tr><tr><td align="right">501</td><td>Error</td><td>Syntax error in parameters or arguments</td></tr><tr><td align="right">502</td><td>Error</td><td>Command not implemented</td></tr><tr><td align="right">503</td><td>Error</td><td>Bad sequence of commands</td></tr><tr><td align="right">504</td><td>Error</td><td>Command parameter not implemented</td></tr><tr><td align="right">550</td><td>Error</td><td>Requested action not taken: mailbox unavailable</td></tr><tr><td align="right">551</td><td>Error</td><td>User not local; please try</td></tr><tr><td align="right">552</td><td>Error</td><td>Requested mail action aborted: exceeded storage allocation</td></tr><tr><td align="right">553</td><td>Error</td><td>Requested action not taken: mailbox name not allowed</td></tr><tr><td align="right">554</td><td>Error</td><td>Transaction failed (message rejected)</td></tr></tbody></table>

* Nmap Script

```bash
sudo nmap --script smtp-enum-users -p25 <IP>
sudo nmap --script smtp-open-relay,smtp-commands,smtp-ntlm-info -p25 <IP>  
```

* Username enumerate

```bash
## ------------------| smtp-user-enum
smtp-user-enum -M VRFY -U /usr/share/seclists/Usernames/Names/names.txt -t 10.10.10.17
smtp-user-enum -U /usr/share/seclists/Usernames/Honeypot-Captures/multiplesources-users-fabian-fingerle.de.txt -m 50 -M RCPT -D humongousretail.com -t 10.10.10.17      

## ------------------| Metasploit
msfconsole
use auxiliary/scanner/smtp/smtp_enum
set RHOSTS $IP
set USER_FILE /usr/share/seclists/Usernames/Names/names.txt
set THREADS 10
set RPORT 25
run

## ------------------| Bash Script
for i in $(cat /usr/share/seclists/Usernames/Names/names.txt);do echo -e "HELO test.com\nVRFY $i\nQUIT" | nc -nv $IP 25 | grep -E "250|550"; done
```

* Check Auth

```bash
telnet <SMG_IP_address>  587
EHLO mailserver.com
AUTH LOGIN
<Username_in_base64> # echo -n "username" | base64
<Password_in_base64> # echo -n "password" | base64
```

* Send mail

<pre class="language-bash"><code class="lang-bash">## !! Be aware about from address. If you are using same domain for both from and to. they will ask auth. So please use info@h4rithd.com first !!
<strong>## ------------------| Using Swaks
</strong>swaks --from info@h4rithd.com --to admin@sneakymailer.htb --header 'Subject: Hello world' --body 'This is msg body' --server 10.10.10.197
    
## ------------------| Using sendEmail
sendEmail -m 'Hello machan' -f info@h4rithd.com  -t admin@sneakymailer.htb -s &#x3C;IP> -u "Message Subject" -a attachment.pdf                            
sendEmail -o message-file=message.txt -f info@h4rithd.com  -t admin@sneakymailer.htb -s &#x3C;IP> -u "Message Subject" -a attachment.pdf                            

## ------------------| Using Telnet
telnet &#x3C;IP> 25
HELO writer.htb
MAIL FROM:info@h4rithd.com
RCPT TO:root@writer.htb
DATA
Subject: Test mail
Hello h4rith
.
QUIT

## ------------------| Using NetCat  
nc &#x3C;IP> 25
HELO writer.htb
MAIL FROM:info@h4rithd.com
RCPT TO:root@writer.htb
DATA
Subject: Test mail
Hello h4rith
.
QUIT

## ------------------| Using NodeJS
const nodemailer = require('nodemailer');

const transporter = nodemailer.createTransport({
  host: 'smtp.example.com',       // Your provider's SMTP server
  port: 587,                      // Common: 587 (STARTTLS), 465 (SSL), 25 (non-auth, old)
  secure: false,                  // true for 465, false for other ports
  auth: {
    user: 'your@email.com',       // Your email address
    pass: 'your_password_or_app_password'
  }
});

// Optional: For self-signed certs or debugging
// tls: {
//   rejectUnauthorized: false
// }

const mailOptions = {
  from: '"HarithD" &#x3C;hello@h4rithd.com>',
  to: 'recipient@h4ritd.com',
  subject: 'SMTP Test',
  text: 'Test email',
  // html: '&#x3C;p>HTML body with &#x3C;strong>custom SMTP&#x3C;/strong>&#x3C;/p>'
};

transporter.sendMail(mailOptions, (error, info) => {
  if (error) {
    return console.error('Send error:', error);
  }
  console.log('Email sent:', info.response);
});
</code></pre>

* SMTP server

```python
## ------------------| Using smtpd (deprecated)
import smtpd
import asyncore

class CustomSMTPServer(smtpd.SMTPServer):
    def __init__(self, localaddr, remoteaddr):
        smtpd.SMTPServer.__init__(self, localaddr, remoteaddr)

    def process_message(self, peer, mailfrom, rcpttos, data):
        print('Received email from:', mailfrom)
        print('To:', rcpttos)
        print('Message:', data)

server = CustomSMTPServer(('0.0.0.0', 1025), None)
asyncore.loop()

## ------------------| Using asyncio
import asyncio
from aiosmtpd.controller import Controller

class CustomSMTPHandler:
    async def handle_RCPT(self, server, session, envelope, address, rcpt_options):
        envelope.rcpt_tos.append(address)
        return '250 OK'

    async def handle_DATA(self, server, session, envelope):
        print('Received email from:', envelope.mail_from)
        print('To:', envelope.rcpt_tos)
        print('Message:', envelope.content.decode('utf-8'))
        return '250 OK'

async def main(loop):
    handler = CustomSMTPHandler()
    controller = Controller(handler, hostname='localhost', port=1025)
    controller.start()

loop = asyncio.get_event_loop()
loop.run_until_complete(main(loop))

```
