smtp邮件发送客户端c++ 正在用Visual C++6.0开发平台实现基于SMTP协议邮件发送程序。应用的是MFC AppWizard [exe] 基于基本对话框的Windows Sockets编程。现在已经可以向收件人发送邮件。问题是:但若以附件形式发送邮件,在接收方没有附件显示,无法下载附件。并且,抄送和暗送功能没有实现。请大家帮帮忙!先谢谢了^_^ 解决方案 » 免费领取超大流量手机卡,每月29元包185G流量+100分钟通话, 中国电信官方发货 我写了一个dll,也是实现了这个功能了,但是跟楼主差不多,关键是我没有可以去写这个 抄送和暗送仅仅是重复的 RCPT TO: 命令附件则需要处理:multipart/mixed; boundary以定义边界(通常base64编码)的方式发送数据 你参考下这个代码吧,可以用的#include <winsock2.h>#include <string.h>#include <stdio.h>const int BASE64_MAXLINE = 76;const char EOL[] = "\r\n";const char BASE64_TAB[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ" "abcdefghijklmnopqrstuvwxyz0123456789+/";const char HEADER[] = "HELO support.com\r\n" //"AUTH LOGIN\r\n" //+ BASE64 USER + BASE64 PASS "MAIL FROM: [email protected]\r\n" "RCPT TO: [email protected]\r\n" "DATA\r\n" "FROM: [email protected]\r\n" "TO: [email protected]\r\n" "SUBJECT: this is a test\r\n" "Date: 2002-5-14\r\n" "X-Mailer: shadowstar's mailer\r\n" "MIME-Version: 1.0\r\n" "Content-type: multipart/mixed; boundary=\"#BOUNDARY#\"\r\n" //"Content-Type: text/plain; charset=gb2312\r\n" "\r\n";const char CONTENT[] = "\r\n--#BOUNDARY#\r\n" "Content-Type: text/plain; charset=gb2312\r\n" "Content-Transfer-Encoding: quoted-printable\r\n" "\r\n" "/*************************************************************" " * smtp.cpp - Use SMTP to send an eMail with an Attachment and verify *" " * Copyright (C) 2001-2002 by ShadowStar. *" " * Use and modify freely. *" " * http://shadowstar.126.com/ *" " *************************************************************" " */\r\n" "\r\n";const char ATT_HEADER[] = "\r\n--#BOUNDARY#\r\n" "Content-Type: application/octet-stream; name=smtp.exe\r\n" "Content-Disposition: attachment; filename=smtp.exe\r\n" "Content-Transfer-Encoding: base64\r\n" "\r\n";//---------------------------------------------------------------------------int ANSIToBase64(const char *szInANSI, int nInLen, char *szOutBase64, int nOutLen);int main(int argc, char* argv[]){ WSADATA wsaData; int SockFD; struct sockaddr_in ServAddr; char buf[0x100]; int x; FILE *fp; char *aatt = new char[0x400000]; char *batt = new char[0x555556]; WSAStartup(MAKEWORD(2,2), &wsaData); LPHOSTENT pHost = gethostbyname("172.16.234.111"); SockFD = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); ServAddr.sin_family = AF_INET; ServAddr.sin_addr.s_addr = *(ULONG *)pHost->h_addr_list[0]; ServAddr.sin_port = htons(25); connect(SockFD, (struct sockaddr *)&ServAddr, sizeof(ServAddr)); //send HEADER send(SockFD, HEADER, strlen(HEADER), 0); //send CONTENT send(SockFD, CONTENT, strlen(CONTENT), 0); //send ATT_HEADER send(SockFD, ATT_HEADER, strlen(ATT_HEADER), 0); //read attachment fp = fopen(argv[0], "rb"); fseek(fp, 0, 2); x = ftell(fp); if (x > 0x400000) x = 0; rewind(fp); fread(aatt, x, 1, fp); fclose(fp); x = ANSIToBase64(aatt, x, batt, 0x555556); //send base64 attachment send(SockFD, batt, x, 0); send(SockFD, ".\r\n", strlen(".\r\n"), 0); //end send(SockFD, "QUIT\r\n", strlen("QUIT\r\n"), 0); //quit closesocket(SockFD); WSACleanup(); delete []aatt; delete []batt; return 0;}//---------------------------------------------------------------------------int ANSIToBase64(const char *szInANSI, int nInLen, char *szOutBase64, int nOutLen){ //Input Parameter validation if ((szInANSI == NULL) || (nInLen == 0) || (szOutBase64 == NULL) || (nOutLen == 0)) return 0; if (nOutLen < (nInLen*4/3 + 1 + nInLen*4/3/BASE64_MAXLINE*2 + 1 + 4)) return 0; //Set up the parameters prior to the main encoding loop int nInPos = 0; int nOutPos = 0; int nLineLen = 0; int c1, c2, c3; int i; // Get three characters at a time from the input buffer and encode them for (i=0; i<nInLen/3; ++i) { //Get the next 2 characters c1 = szInANSI[nInPos++] & 0xFF; c2 = szInANSI[nInPos++] & 0xFF; c3 = szInANSI[nInPos++] & 0xFF; //Encode into the 4 6 bit characters szOutBase64[nOutPos++] = BASE64_TAB[c1 >> 2]; szOutBase64[nOutPos++] = BASE64_TAB[((c1 << 4) | (c2 >> 4)) & 0x3F]; szOutBase64[nOutPos++] = BASE64_TAB[((c2 << 2) | (c3 >> 6)) & 0x3F]; szOutBase64[nOutPos++] = BASE64_TAB[c3 & 0x3F]; nLineLen += 4; //Handle the case where we have gone over the max line boundary if (nLineLen > BASE64_MAXLINE - 4) { szOutBase64[nOutPos++] = EOL[0]; szOutBase64[nOutPos++] = EOL[1]; nLineLen = 0; } } // Encode the remaining one or two characters in the input buffer switch (nInLen % 3) { case 0: { szOutBase64[nOutPos++] = EOL[0]; szOutBase64[nOutPos++] = EOL[1]; break; } case 1: { c1 = szInANSI[nInPos] & 0xFF; szOutBase64[nOutPos++] = BASE64_TAB[(c1 & 0xFC) >> 2]; szOutBase64[nOutPos++] = BASE64_TAB[((c1 & 0x03) << 4)]; szOutBase64[nOutPos++] = '='; szOutBase64[nOutPos++] = '='; szOutBase64[nOutPos++] = EOL[0]; szOutBase64[nOutPos++] = EOL[1]; break; } case 2: { c1 = szInANSI[nInPos++] & 0xFF; c2 = szInANSI[nInPos] & 0xFF; szOutBase64[nOutPos++] = BASE64_TAB[(c1 & 0xFC) >> 2]; szOutBase64[nOutPos++] = BASE64_TAB[((c1 & 0x03) << 4) | ((c2 & 0xF0) >> 4)]; szOutBase64[nOutPos++] = BASE64_TAB[((c2 & 0x0F) << 2)]; szOutBase64[nOutPos++] = '='; szOutBase64[nOutPos++] = EOL[0]; szOutBase64[nOutPos++] = EOL[1]; break; } default: { return 0; } } szOutBase64[nOutPos] = 0; return nOutPos;} 你能解释一下基于SMTP协议的邮件发送客户端是工作原理、工作过程吗?比如点击“发送”按钮后会发生什么事情,哪些函数是怎么配合彼此工作的.... 还是看看SMTP/ESMTP的资料吧http://www.ietf.org/rfc/rfc0821.txthttp://www.ietf.org/rfc/rfc2821.txt 中文:http://www.longen.org/s-z/details~z/smtp.htmhttp://dev.21tx.com/2002/11/19/10070.html 用Jmail组件吧,可以轻松实现邮件发送接收等各种功能 高分求救 ,waitcommevent函数总是返回FALSE ,Getlasterror返回值87 MFC向导生成的程序运行时怎么失去了xp样式? 用什么方法能很简单的播放一个网络上的AVI文件? 找对地方啦,问一下怎么不使用navigate2函数直接显示网页? 关于onkeydown的菜鸟问题 位图复制问题(高手请进) 如何拷贝另外一个工程中对话框资源和类? 请问如何使窗口在屏幕中显示却在底部任务栏中不现实? 关于设备的guid的问题 大家帮帮我这个小妹妹吧! 一个棘手的动态库问题! 关于内存共享节的问题。。。比较诡异呀。。。
附件则需要处理:multipart/mixed; boundary
以定义边界(通常base64编码)的方式发送数据
#include <string.h>
#include <stdio.h>const int BASE64_MAXLINE = 76;
const char EOL[] = "\r\n";
const char BASE64_TAB[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
"abcdefghijklmnopqrstuvwxyz0123456789+/";
const char HEADER[] =
"HELO support.com\r\n"
//"AUTH LOGIN\r\n" //+ BASE64 USER + BASE64 PASS
"MAIL FROM: [email protected]\r\n"
"RCPT TO: [email protected]\r\n"
"DATA\r\n"
"FROM: [email protected]\r\n"
"TO: [email protected]\r\n"
"SUBJECT: this is a test\r\n"
"Date: 2002-5-14\r\n"
"X-Mailer: shadowstar's mailer\r\n"
"MIME-Version: 1.0\r\n"
"Content-type: multipart/mixed; boundary=\"#BOUNDARY#\"\r\n"
//"Content-Type: text/plain; charset=gb2312\r\n"
"\r\n";
const char CONTENT[] =
"\r\n--#BOUNDARY#\r\n"
"Content-Type: text/plain; charset=gb2312\r\n"
"Content-Transfer-Encoding: quoted-printable\r\n"
"\r\n"
"/*************************************************************"
" * smtp.cpp - Use SMTP to send an eMail with an Attachment and verify *"
" * Copyright (C) 2001-2002 by ShadowStar. *"
" * Use and modify freely. *"
" * http://shadowstar.126.com/ *"
" *************************************************************"
" */\r\n"
"\r\n";
const char ATT_HEADER[] =
"\r\n--#BOUNDARY#\r\n"
"Content-Type: application/octet-stream; name=smtp.exe\r\n"
"Content-Disposition: attachment; filename=smtp.exe\r\n"
"Content-Transfer-Encoding: base64\r\n"
"\r\n";//---------------------------------------------------------------------------
int ANSIToBase64(const char *szInANSI, int nInLen, char *szOutBase64, int nOutLen);int main(int argc, char* argv[])
{
WSADATA wsaData;
int SockFD;
struct sockaddr_in ServAddr;
char buf[0x100];
int x;
FILE *fp;
char *aatt = new char[0x400000];
char *batt = new char[0x555556]; WSAStartup(MAKEWORD(2,2), &wsaData); LPHOSTENT pHost = gethostbyname("172.16.234.111");
SockFD = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
ServAddr.sin_family = AF_INET;
ServAddr.sin_addr.s_addr = *(ULONG *)pHost->h_addr_list[0];
ServAddr.sin_port = htons(25); connect(SockFD, (struct sockaddr *)&ServAddr, sizeof(ServAddr));
//send HEADER
send(SockFD, HEADER, strlen(HEADER), 0);
//send CONTENT
send(SockFD, CONTENT, strlen(CONTENT), 0);
//send ATT_HEADER
send(SockFD, ATT_HEADER, strlen(ATT_HEADER), 0);
//read attachment
fp = fopen(argv[0], "rb");
fseek(fp, 0, 2);
x = ftell(fp);
if (x > 0x400000)
x = 0;
rewind(fp);
fread(aatt, x, 1, fp);
fclose(fp);
x = ANSIToBase64(aatt, x, batt, 0x555556);
//send base64 attachment
send(SockFD, batt, x, 0); send(SockFD, ".\r\n", strlen(".\r\n"), 0); //end
send(SockFD, "QUIT\r\n", strlen("QUIT\r\n"), 0); //quit closesocket(SockFD);
WSACleanup(); delete []aatt;
delete []batt;
return 0;
}
//---------------------------------------------------------------------------
int ANSIToBase64(const char *szInANSI, int nInLen, char *szOutBase64, int nOutLen)
{
//Input Parameter validation
if ((szInANSI == NULL) || (nInLen == 0) || (szOutBase64 == NULL) || (nOutLen == 0))
return 0;
if (nOutLen < (nInLen*4/3 + 1 + nInLen*4/3/BASE64_MAXLINE*2 + 1 + 4))
return 0; //Set up the parameters prior to the main encoding loop
int nInPos = 0;
int nOutPos = 0;
int nLineLen = 0;
int c1, c2, c3;
int i; // Get three characters at a time from the input buffer and encode them
for (i=0; i<nInLen/3; ++i)
{
//Get the next 2 characters
c1 = szInANSI[nInPos++] & 0xFF;
c2 = szInANSI[nInPos++] & 0xFF;
c3 = szInANSI[nInPos++] & 0xFF; //Encode into the 4 6 bit characters
szOutBase64[nOutPos++] = BASE64_TAB[c1 >> 2];
szOutBase64[nOutPos++] = BASE64_TAB[((c1 << 4) | (c2 >> 4)) & 0x3F];
szOutBase64[nOutPos++] = BASE64_TAB[((c2 << 2) | (c3 >> 6)) & 0x3F];
szOutBase64[nOutPos++] = BASE64_TAB[c3 & 0x3F];
nLineLen += 4; //Handle the case where we have gone over the max line boundary
if (nLineLen > BASE64_MAXLINE - 4)
{
szOutBase64[nOutPos++] = EOL[0];
szOutBase64[nOutPos++] = EOL[1];
nLineLen = 0;
}
} // Encode the remaining one or two characters in the input buffer
switch (nInLen % 3)
{
case 0:
{
szOutBase64[nOutPos++] = EOL[0];
szOutBase64[nOutPos++] = EOL[1];
break;
}
case 1:
{
c1 = szInANSI[nInPos] & 0xFF;
szOutBase64[nOutPos++] = BASE64_TAB[(c1 & 0xFC) >> 2];
szOutBase64[nOutPos++] = BASE64_TAB[((c1 & 0x03) << 4)];
szOutBase64[nOutPos++] = '=';
szOutBase64[nOutPos++] = '=';
szOutBase64[nOutPos++] = EOL[0];
szOutBase64[nOutPos++] = EOL[1];
break;
}
case 2:
{
c1 = szInANSI[nInPos++] & 0xFF;
c2 = szInANSI[nInPos] & 0xFF;
szOutBase64[nOutPos++] = BASE64_TAB[(c1 & 0xFC) >> 2];
szOutBase64[nOutPos++] = BASE64_TAB[((c1 & 0x03) << 4) | ((c2 & 0xF0) >> 4)];
szOutBase64[nOutPos++] = BASE64_TAB[((c2 & 0x0F) << 2)];
szOutBase64[nOutPos++] = '=';
szOutBase64[nOutPos++] = EOL[0];
szOutBase64[nOutPos++] = EOL[1];
break;
}
default:
{
return 0;
}
} szOutBase64[nOutPos] = 0; return nOutPos;
}
http://dev.21tx.com/2002/11/19/10070.html