⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 smtp.c

📁 ATmega103、ATmega128做的开发板web server源码
💻 C
字号:
/******************************************************************
* smtp.c: Simple Mail transfer protocol
* 
* Copyright (c) 2001 Atmel Corporation.
* All Rights Reserved.
*
* You are autorized to use, copy and distribute this software only at 
* a single site (the term "site" meaning a single company location). 
* This copyright notice must be included in any copy, modification 
* or portion of this software merged into another program.
* 
* This software is licenced solely for use with Atmel AVR micro 
* controller family. The software may not be modified to execute on 
* any other microcontroller architectures
*
* This software is provided "as is"; Without warranties either express
* or implied, including any warranty regarding merchantability, 
* fitness for a particular purpose or noninfringement. 
*
* In no event shall Atmel or its suppliers be liable for any special, 
* indirect,incidential or concequential damages resulting from the 
* use or inability to use this software.
*
* Revision history:
*
* January 17, 2001:   Version 1.0   Created by JB
* July 13, 2001		  Version 1.2     JB
* 					- Changed to IAR compiler V2.25
*					- Renamed flash file functions to avoid conflict with 
*					  standard file I/O names	
*					- Bug fixes in HTTP
*					- Speed optimization in TCP 
*
*
*******************************************************************/
#define ENABLE_BIT_DEFINITIONS
#include "comp_a90.h"
#include "tcp.h"
#include "main.h"
#include "ffile.h" 
#include "smtp.h"
#include "config.h"
#include <iom103.h>
#include <string.h>
#include <stdio.h> 
#include <pgmspace.h>

/*states*/
#define SMTP_STATE_CONNECT  0
#define SMTP_STATE_HELO     1
#define SMTP_STATE_MAIL     2
#define SMTP_STATE_RCPT     3
#define SMTP_STATE_DATA1    4
#define SMTP_STATE_DATA2    5
#define SMTP_STATE_QUIT     6

/*constant strings to placed in flash*/
flash char SMTP_CLRF[]            ="\r\n";
flash char SMTP_CLRF_DOT_CLRF[]   ="\r\n.\r\n";
flash char SMTP_HEADER_FROM[]     ="From: ";
flash char SMTP_HEADER_TO[]       ="To: ";
flash char SMTP_HEADER_SUBJECT[]  ="Subject: ";
flash char SMTP_COMMAND_HELO[]    ="HELO ";
flash char SMTP_COMMAND_MAIL[]    ="MAIL FROM:";
flash char SMTP_COMMAND_RCPT[]    ="RCPT TO:";
flash char SMTP_COMMAND_DATA[]    ="DATA\r\n";
flash char SMTP_COMMAND_QUIT[]    ="QUIT\r\n";




/*sends a mail to the adress specified in server.ini,
  returns 1 if successful, 0 otherwise*/
unsigned char sendMail(char * subject, char * message)
{
  unsigned char smtpState;                    //state of the state-machine
  char buffer[SMTP_BUFFER];                   //multipurpose buffer
  char mailSender[SMTP_BUFFER_READ_MAIL];     //the sending mail address, read from server.ini
  char mailReceiver[SMTP_BUFFER_READ_MAIL];   //the receiving mail address, read from server.ini
  char mailHostName[SMTP_BUFFER_READ_HOST];   //the identification given to the mailserver, read from server.ini
  unsigned int mailIp0,mailIp1;               //the mailserver IP-address, read from server.ini
  
  SOCKET *sock;
   
  /*read setings from server.ini*/
  if (!getOption("SMTP\0","sender\0",mailSender) || !getOption("SMTP\0","receiver\0",mailReceiver)
        || !getOption("SMTP\0","host\0",mailHostName))
  {
    return 0;                   //error reading from server.ini
  }
  
  if (!getOption("SMTP\0","mailIp0\0",buffer))
  {
    return 0;                   //error reading from server.ini
  } 
  sscanf(buffer,"%x",&mailIp0);
  
  if (!getOption("SMTP\0","mailIp1\0",buffer))
    return 0;                   //error reading from server.ini
  sscanf(buffer,"%x",&mailIp1);

  smtpState=SMTP_STATE_CONNECT; //initial state  

  sock=TCPaopen(SMTP_SERVER_PORT,mailIp0,mailIp1,0);//connect to the mail server

    /*state machine*/
    for (;;)
    {
      switch (smtpState)
      {
        case SMTP_STATE_CONNECT:
        
          if (SMTPwait(sock))		            //if new data received
          {
            TCPreadln(sock,SMTP_BUFFER,buffer,1);
            if (!strncmp(buffer,"220",3))
            {
              TCPbufferFlush(sock);                 //clear the receivebuffer
              
              /*send HELO command*/
              TCPsend_P(sock,strlen_P(SMTP_COMMAND_HELO),SMTP_COMMAND_HELO);
              TCPsend(sock,strlen(mailHostName),mailHostName);
              TCPsend_P(sock,strlen_P(SMTP_CLRF),SMTP_CLRF);
              
              smtpState=SMTP_STATE_HELO;
            }
            else if (!strncmp(buffer,"421",3))      //Service not available
            {
              TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
              TCPclose(sock);
              return 0;
            }
          }
          else//timeout
          {
            TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
            TCPclose(sock);
            return 0;
          }         
          break;
        case SMTP_STATE_HELO:
        
          if (SMTPwait(sock))                       //if new data received
          {
            TCPreadln(sock,SMTP_BUFFER,buffer,1);
            if (!strncmp(buffer,"250",3))
            {
              TCPbufferFlush(sock);                 //clear the receivebuffer
              
              /*send MAIL command*/
              TCPsend_P(sock,strlen_P(SMTP_COMMAND_MAIL),SMTP_COMMAND_MAIL);              
              TCPsend(sock,strlen(mailSender),mailSender);
              TCPsend_P(sock,strlen_P(SMTP_CLRF),SMTP_CLRF);
              
              smtpState=SMTP_STATE_MAIL;
            }
            else if (!strncmp(buffer,"421",3) || !strncmp(buffer,"500",3) || !strncmp(buffer,"501",3)
                        || !strncmp(buffer,"504",3))//error
            {
              TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
              TCPclose(sock);
              return 0;
            }
          }
          else//timeout
          {
            TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
            TCPclose(sock);
            return 0;
          } 
          break;    
    
        case SMTP_STATE_MAIL:
        
          if (SMTPwait(sock))                       //if new data received
          {
            TCPreadln(sock,SMTP_BUFFER,buffer,1);
            if (!strncmp(buffer,"250",3))
            {
              TCPbufferFlush(sock);                 //clear the receivebuffer
              
              /*send RCPT command*/
              TCPsend_P(sock,strlen_P(SMTP_COMMAND_RCPT),SMTP_COMMAND_RCPT);            
              TCPsend(sock,strlen(mailReceiver),mailReceiver);
              TCPsend_P(sock,strlen_P(SMTP_CLRF),SMTP_CLRF);            
              
              smtpState=SMTP_STATE_RCPT;
            }
            else if (!strncmp(buffer,"421",3) || !strncmp(buffer,"451",3) || !strncmp(buffer,"452",3) 
                     || !strncmp(buffer,"500",3) || !strncmp(buffer,"501",3) || !strncmp(buffer,"552",3))//error
            {
              TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
              TCPclose(sock);
              return 0;
            }
          }
          else//timeout
          {
            TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
            TCPclose(sock);
            return 0;
          } 
          break;
        
        case SMTP_STATE_RCPT:
          
          if (SMTPwait(sock))                       //if new data received
          {
            TCPreadln(sock,SMTP_BUFFER,buffer,1);
            if (!strncmp(buffer,"250",3) || !strncmp(buffer,"251",3))
            {
              TCPbufferFlush(sock);                 //clear the receivebuffer
              
              /*send DATA command*/
              TCPsend_P(sock,strlen_P(SMTP_COMMAND_DATA),SMTP_COMMAND_DATA);
              
              smtpState=SMTP_STATE_DATA1;
            }
            else if (!strncmp(buffer,"421",3) || !strncmp(buffer,"450",3) || !strncmp(buffer,"451",3)
                     || !strncmp(buffer,"452",3) || !strncmp(buffer,"500",3) || !strncmp(buffer,"501",3)
                     || !strncmp(buffer,"503",3) || !strncmp(buffer,"550",3) || !strncmp(buffer,"551",3)
                     || !strncmp(buffer,"552",3) || !strncmp(buffer,"553",3))//error
            {
              TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
              TCPclose(sock);
              return 0;
            }
          }
          else//timeout
          {
            TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
            TCPclose(sock);
            return 0;
          } 
          break;  
    
        case SMTP_STATE_DATA1:
        
          if (SMTPwait(sock))                       //if new data received
          {
            TCPreadln(sock,SMTP_BUFFER,buffer,1);
            if (!strncmp(buffer,"354",3))
            {
          
              TCPbufferFlush(sock);                 //clear the receivebuffer
   
              /*send the message*/
              TCPsend_P(sock,strlen_P(SMTP_HEADER_FROM),SMTP_HEADER_FROM);
              TCPsend(sock,strlen(mailSender),mailSender);
              TCPsend_P(sock,strlen_P(SMTP_CLRF),SMTP_CLRF);
              TCPsend_P(sock,strlen_P(SMTP_HEADER_TO),SMTP_HEADER_TO);
              TCPsend(sock,strlen(mailReceiver),mailReceiver);
              TCPsend_P(sock,strlen_P(SMTP_CLRF),SMTP_CLRF);
              TCPsend_P(sock,strlen_P(SMTP_HEADER_SUBJECT),SMTP_HEADER_SUBJECT);
              TCPsend(sock,strlen(subject),subject);
              TCPsend_P(sock,strlen_P(SMTP_CLRF),SMTP_CLRF);
              TCPsend_P(sock,strlen_P(SMTP_CLRF),SMTP_CLRF);
              TCPsend(sock,strlen(message),message);
              TCPsend_P(sock,strlen_P(SMTP_CLRF_DOT_CLRF),SMTP_CLRF_DOT_CLRF);
  
              smtpState=SMTP_STATE_DATA2;
            }
            else if (!strncmp(buffer,"421",3) || !strncmp(buffer,"451",3) || !strncmp(buffer,"452",3) 
                     || !strncmp(buffer,"500",3) || !strncmp(buffer,"501",3) || !strncmp(buffer,"503",3)
                     || !strncmp(buffer,"552",3) || !strncmp(buffer,"554",3))//error
            {
              TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
              TCPclose(sock);
              return 0;
            }
          }
          else //timeout
          {
            TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
            TCPclose(sock);
            return 0;
          } 
          break;  
       
        case SMTP_STATE_DATA2:
        
          if (SMTPwait(sock))                       //if new data received
          {
            TCPreadln(sock,SMTP_BUFFER,buffer,1);
            if (!strncmp(buffer,"250",3))
            {
              TCPbufferFlush(sock);                 //clear the receivebuffer
              
              /*send QUIT command*/
              TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
              
              smtpState=SMTP_STATE_QUIT;
            }
            else if (!strncmp(buffer,"500",3))      //error
            {
              TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
              TCPclose(sock);
              return 0;
            }
          }
          else//timeout
          {
            TCPsend_P(sock,strlen_P(SMTP_COMMAND_QUIT),SMTP_COMMAND_QUIT);            
            TCPclose(sock);
            return 0;
          }    
          break;
        
        case SMTP_STATE_QUIT:
        
          if (SMTPwait(sock))                       //if new data received
          {
            TCPreadln(sock,SMTP_BUFFER,buffer,1);
            if (!strncmp(buffer,"221",3))
            {
              TCPbufferFlush(sock);                 //clear the receivebuffer
              TCPclose(sock);
                return 1;
            }
            else if (!strncmp(buffer,"500",3))      //error
            {
              TCPclose(sock);
              /*return success, the message has succesfully been sent,
                even if closing the conection failed */
              return 1;
            }          
          }
          else//timeout
          {
            TCPclose(sock);
            /*return success, the message has succesfully been sent, 
              even if closing the conection failed */
            return 1;
          }    
          break;
    
    
      }
    }
}

/* waits for timeout or TCP data, returns 1 if data, 0 if timeout */
unsigned char SMTPwait(SOCKET * sock)
{
  TCCR1B|=(1<<CTC1 | 1<<CS12 | 1<<CS10);      //clear counter on compare match, clock divided by 1024
  OCR1A=SMTP_TIMEOUT;
  TIFR|=(1<<OCF1A);                           //output compare flag 1A is cleared by writing a logic one
  TCNT1=0;                                    //clear the counter
  for (;;)
  {
    if (TCPsize(sock))                        //poll TCP buffer
    {                      
      return 1;
    }
    else if (TIFR&(1<<OCF1A))                 //output compare flag 1A is set, timeout
    {
      return 0;
    }
  }
}

  

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -