SMTP protocol learning notes

Source: Internet
Author: User

In the past few days, the publisher has not updated his blog in time. First, because of the complicated locks during work during the day, he has watched the SMTP protocol for two consecutive nights.

 

I like to prove everything with practice, so that I can deepen my understanding!

 

I. preparations:

1. Local Environment: Windows XP SP3, 10 m ADSL Optical Fiber

2. Development Tool: wildpackets omnipeek v5.1.4

Visual c ++ 6.0

Outlook express6.0

Flexedit v2.3.1871

 

Ii. SMTP command:

1. Helo identifies a user to the server
2. Mail initialization mail Transmission from: <XXX>
3. RCPT identifies a single email recipient. Multiple rcpt to: <XXX>
4. After one or more RCPT commands, data indicates that all Email recipients have been identified and data transmission is initiated to end.
5. No Noop operation. The server should respond to OK
6. rset resets the session and the current transmission is canceled.
7. Quit end the session

3. analyze data packets:

1. Open outlook express6.0 and create a new email with the following content:

 

2. Open omnipeek and select SMTP:

 

3. Start packet capture and send the following test email. The data packets obtained are as follows:

(Note the Source and Destination addresses, that is, the source and target addresses)

 

4. You only need to view 20th data packets. Others can be easily understood:

 

5. Other Tips

 

<CR> <LF> corresponds to "/R/n" in C/C ++"

 

For example, line 8: charset = "gb2312" <CR> <LF>, because escape characters are required

 

Therefore, the corresponding string should be char * sdata = "charset =/" gb2312/"/R/N ";

 

4. Related code:

1. The following Code establishes a connection with the SMTP server through a socket and verifies the identity. Open visual C ++, create a console project, and add a CPP file:

/*************************************** *******************************/<Br/> /* main. cpp smtp protocol learning notes-Logon verification <br/>/* by Koma 2009.9.10 <br/>/* http://blog.csdn.net/wangningyu <br/> /********** **************************************** * ********************/<br/> # include "stdio. H "<br/> # include" zbase64.h "<br/> # include" winsock2.h "<br/> # pragmacomment (Lib," ws2_32.lib ") </P> <p> int main (INT argc, Char * argv []) <br/>{< br/> sockaddr_insaserver; <br/> lphostentlphostent; <br/> wsadatawsadata; <br/> sockethsocket; </P> <p> intnret; <br/> char * host_name = "smtp.tom.com "; <br/> char * Req = <br/> // The server returns a response for each row sent. <br/> "ehlo komawang/R/N" <br/> "auth login/R/N "</P> <p> // two lines are the logon user and password (encrypted using base64) <br/> "BM ********** 20 =/R/N" <br/> "D2 ******* W4 =/R/ N "<br/>" Quit/R/N "; </P> <p> // initialize the socket <br/> If (wsastartup (makeword (2, 2), & wsadata) <br/> printf ("An error occurred while initializing the socket! "); </P> <p> // The default SMTP port is 25 <br/> lphostent = gethostbyname (host_name); <br/> If (lphostent = NULL) <br/> printf ("lphostent is empty! "); <Br/> hsocket = socket (af_inet, sock_stream, ipproto_tcp); <br/> saserver. sin_family = af_inet; <br/> saserver. sin_port = htons (25); <br/> saserver. sin_addr = * (lpin_addr) * lphostent-> h_addr_list); </P> <p> // Connect using Socket <br/> nret = connect (hsocket, (lpsockaddr) & saserver, sizeof (sockaddr_in); <br/> If (nret = socket_error) <br/>{< br/> printf ("An error occurred while establishing a connection! /N "); <br/> closesocket (hsocket); <br/> return 0; <br/>}</P> <p> // use socket to send <br/> nret = Send (hsocket, req, strlen (req), 0 ); <br/> If (nret = socket_error) <br/> {<br/> printf ("An error occurred while sending the data packet! "); <Br/> closesocket (hsocket); <br/>}</P> <p> char Dest [3000]; <br/> memset (DEST, 0, 000); <br/> nret = 1; <br/> while (nret> 0) <br/> {<br/> // receives the returned data packet <br/> nret = Recv (hsocket, (lpstr) DEST, sizeof (DEST), 0 ); <br/> If (nret> 0) <br/> Dest [nret] = 0; <br/> else <br/> Dest [0] = 0; </P> <p> // display the size and content of the returned data packet <br/> printf ("/n returned data packet size: % d/N", nret ); <br/> printf ("Returned packet content:/n % s", DEST); <br/>}< br/> return 0; <br/>}

 

2. The following is the base64 encryption/Decryption header and CPP file:

/*************************************** *******************************/<Br/> /* zbase64.h <br/> /********************************** ***********************************/< br/> # ifndef _ zbase64 <br/> # DEFINE _ zbase64 </P> <p> # pragma warning (Disable: (4786) <br/> # include <string> <br/> using namespace STD; </P> <p> class zbase64 <br/>{</P> <p> public: </P> <p>/* encoding <br/> databyte <br/> [in] the length of the input data, in bytes <br/> */<br/> string encode (const unsigned char * data, int databyte ); </P> <p>/* decoding <br/> databyte <br/> [in] the length of the input data, in bytes <br/> outbyte <br/> [out] the length of the output data, in bytes, do not calculate the length of the output data using the return value <br/> */<br/> string decode (const char * data, int databyte, Int & outbyte ); <br/>}; <br/> # endif

 

/*************************************** *******************************/<Br/> /* zbase64.cpp <br/> /********************************** ***********************************/< br/> # include "zbase64.h" </P> <p> string zbase64:: encode (const unsigned char * data, int databyte) <br/> {<br/> // encoding table <br/> const char encodetable [] = "abcdefghijklmnopqrstuvwxyzabcdefghijklmnopqrstuvwxyz0123456789 + /"; </P> <p> // return value <br /> String strencode; </P> <p> unsigned char TMP [3] = {0}; <br/> int linelength = 0; </P> <p> for (INT I = 0; I <(INT) (databyte/3); I ++) <br/> {<br/> TMP [1] = * Data ++; <br/> TMP [2] = * Data ++; <br/> TMP [3] = * Data ++; </P> <p> strencode + = encodetable [TMP [1]> 2]; <br/> strencode + = encodetable [(TMP [1] <4) | (TMP [2]> 4) & 0x3f]; <br/> strencode + = encodetable [(TMP [2] <2) | (TMP [3]> 6) & 0x3f]; <br/> strencod E + = encodetable [TMP [3] & 0x3f]; <br/> If (linelength + = 4, linelength = 76) {strencode + = "/R/N "; linelength = 0 ;}< br/>}</P> <p> // encode the remaining data <br/> int mod = databyte % 3; <br/> If (mod = 1) <br/> {<br/> TMP [1] = * Data ++; <br/> strencode + = encodetable [(TMP [1] & 0xfc)> 2]; <br/> strencode + = encodetable [(TMP [1] & 0x03) <4)]; <br/> strencode + = "= "; <br/>}< br/> else if (mod = 2) <br/>{< br/> TMP [1] = * Data ++; <br/> TM P [2] = * Data ++; <br/> strencode + = encodetable [(TMP [1] & 0xfc)> 2]; <br/> strencode + = encodetable [(TMP [1] & 0x03) <4) | (TMP [2] & 0xf0)> 4)]; <br/> strencode + = encodetable [(TMP [2] & 0x0f) <2)]; <br/> strencode + = "= "; <br/>}</P> <p> return strencode; <br/>}</P> <p> string zbase64: Decode (const char * data, int databyte, Int & outbyte) <br/> {<br/> // decoding table <br/> const char decodetable [] = <br/> {<br/> 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, <br/> 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, <br/> 62, // '+' <br/> 0, 0, 0, <br/> 63, // '/' <br/> 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, // '0'-'9' <br/> 0, 0, 0, 0, 0, 0, <br/> 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, <br/> 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, // 'a'-'Z' <br/> 0, 0, 0, 0, 0, 0, <br/> 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, <br/> 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, // 'a'-'Z' <br/> }; </P> <p> // return value <br/> string strdecode; </P> <p> int nvalue; <br/> int I = 0; </P> <p> while (I <databyte) <br/> {<br/> If (* Data! = '/R' & * Data! = '/N') <br/>{< br/> nvalue = decodetable [* Data ++] <18; <br/> nvalue + = decodetable [* Data ++] <12; <br/> strdecode + = (nvalue & 0x00ff0000)> 16; <br/> outbyte ++; </P> <p> If (* Data! = ') <Br/>{< br/> nvalue + = decodetable [* Data ++] <6; <br/> strdecode + = (nvalue & 0x0000ff00)> 8; <br/> outbyte ++; </P> <p> If (* Data! = ') <Br/>{< br/> nvalue + = decodetable [* Data ++]; <br/> strdecode + = nvalue & 0x000000ff; <br/> outbyte ++; <br/>}< br/> I + = 4; <br/>}< br/> else // press enter to wrap the line. <br/>{< br/> data ++; <br/> I ++; <br/>}< br/> return strdecode; <br/>}< br/>

 

3. program running effect:

 

 

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.