2012-02-02 46 views
9

Tôi vừa bắt đầu tìm hiểu về lập trình socket và tìm hiểu về winsock và đạt được một số tiến bộ. câu hỏi của tôi về cơ bản là: Tôi muốn gửi email, tôi phải làm gì?Gửi email bằng C

điểm được đề cập:

  1. tôi đã học về khởi winsock. Cổng SMTP (25). tạo và kết nối với ổ cắm thành công. Tôi nên làm gì bây giờ?!!! (Tôi bị kẹt ở đây)
  2. Tôi không muốn mã sẵn sàng cho công việc. Tôi muốn học. Vì vậy, bất kỳ sách, tài liệu, hướng dẫn hoặc đề xuất bài viết là cần thiết.
  3. Tôi biết rằng C chính nó không biết gì về mạng, điều đó có nghĩa là tôi phải tải xuống một số thư viện? (Tôi đang sử dụng VS2010, Windows 7)

Dưới đây là các liên kết đến các trang Tôi đã đọc cho đến nay:

dẫn winsock cơ bản: http://msdn.microsoft.com/en-us/library/windows/desktop/ms737629(v=vs.85).aspx

Tôi đã đọc 14 trang đầu từ beej dẫn (không thể gửi liên kết, người dùng mới chỉ có thể đăng tối đa là hai siêu liên kết)

tôi đã học về các loại (WSADATA, addrinfo structure, sockaddr, SOCKET) và chức năng (WSAStartup(), WSACleanup(), getaddrinfo(), Shutdown(), WSAGetLastError(), socket() ...)

và tôi đã chỉ mới bắt đầu đọc bài viết này về SMTPhttp://www.faqs.org/rfcs/rfc821.html

đây là những gì tôi đã viết cho đến bây giờ:

#include <stdio.h> 
#include <WinSock2.h> 
#include <WS2tcpip.h> 

#pragma comment(lib, "Ws2_32.lib") // Applications that use Winsock must be linked with the Ws2_32.lib library file. 

#define HTTP_PORT "80" 
#define SMTP_PORT "25" 
#define HOSTNAME_PORT "101" 

/* 
All ports and web services names (which are string aliases of the ports 

can be found here: 
%WINDIR%\system32\drivers\etc\services 

*/ 

int main(void) 
{ 
    WSADATA wsdata; 
    int iresult, retval; //iresult : instant result 
    SOCKET connect_socket; 
    struct addrinfo *result, *ptr, hints; 

    iresult = WSAStartup(MAKEWORD(2, 2), &wsdata); 
    if(iresult != 0) printf("Initiation of Winsock succeeded.\n"); 
    else 
    { 
     printf("WinSock initialization failed..\n"); 
     WSACleanup(); 
     return 0; 
    } 

    if(LOBYTE(wsdata.wVersion) == 2 && HIBYTE(wsdata.wVersion) == 2) printf("winsock.dll is found.\n"); 
    else 
    { 
     printf("Can not find the required winsock.dll file.\n"); 
     WSACleanup(); 
     return 0; 
    } 

    ZeroMemory(&hints, sizeof(hints)); 
    hints.ai_family = AF_UNSPEC; // IPv4 or IPv6 
    hints.ai_protocol = IPPROTO_TCP; // TCP connection (full duplex) 
    hints.ai_socktype = SOCK_STREAM; // Provides sequenced, reliable, two-way, connection-based byte streams 

    connect_socket = socket(hints.ai_family, hints.ai_socktype, hints.ai_protocol); 
    if(connect_socket == INVALID_SOCKET) 
    { 
     printf("Socket Creation failed..\n"); 
     WSACleanup(); 
     return 0; 
    } 
    else printf("Socket Creation Succeeded ..\n"); 
    WSACleanup(); 
    return 1; 
} 

am Tôi tắt khóa học?

+0

tôi khuyên bạn nên đọc tuyệt vời Stevens' TCP/IP Illustrated "cuốn sách, và cũng có thể của mình "Nâng cao Lập trình trong môi trường Unix ". Có, tôi biết nó nói Unix, nhưng nó thực sự là một cuốn sách tuyệt vời và 'winsock' về cơ bản là một thực hiện của API socket BSD. – cha0site

Trả lời

3

Bạn nên có một cái nhìn tại some examples on smtp via telnet :)

Về cơ bản bạn cần phải nhập trong bản rõ một cái gì đó như thế này:

HELO local.domain.name 
MAIL FROM: [email protected] 
RCPT TO: [email protected] 
DATA 
... 

EDIT theo this example, mã của bạn nên là:

// Not sure about this one, maybe just "\n" 
#define SEPARATOR "\n\r" 

int sendData(Socket *socket, const char *data) { 
    int iResult; 
    iResult = send(socket, data, (int) strlen(data), 0); 
    if(iResult == SOCKET_ERROR){ 
     // Do error handling as you like 
    } 
    return iResult; 
} 

sendData(socket, "HELO local.doman.name" SEPARATOR); 
sendData(socket, "MAIL FROM: [email protected]" SEPARATOR); 
sendData(socket, "RCPT TO: [email protected]" SEPARATOR); 
sendData(socket, "DATA" SEPARATOR); 
sendData(socket, "This is subject of my mail" SEPARATOR SEPARATOR); 
sendData(socket, "And this is text" SEPARATOR); 
sendData(socket, "." SEPARATOR); // Send mail 
+0

Tôi đã chạy trên một cái gì đó như thế này, nhưng không thể hiểu phải làm gì với điều đó? Tôi có nghĩa là nơi để đặt văn bản này? và tại sao? "HELO" có nghĩa là gì (tôi nghĩ nói lời chào với máy chủ)? – joker

+0

@joker đặt nó trong telnet: http://en.wikipedia.org/wiki/Telnet thậm chí còn có một chương trình cho rằng trong cửa sổ được đặt tên giống nhau. – Flavius

+0

@joker: 'Trong lệnh HELO, máy chủ gửi lệnh xác định số ; lệnh có thể được hiểu là "Xin chào, tôi là " ' – cha0site

4

Bạn nên đọc cách sử dụng smtp trên telnet. Sau đó bạn có thể dễ dàng thực hiện nó ..

+0

cảm ơn, đã bắt đầu đọc ngay bây giờ. tôi hy vọng rằng sẽ giúp – joker

+0

Tôi đã đọc các trang u liên kết đến. Tôi đã học được một vài điều, nhưng có vẻ như đã lỗi thời. Tôi phải tìm kiếm "menu kết nối" và cổng để mở máy chủ thư yahoo (kể từ 25 được nhập, kết nối không thành công) trợ giúp của bạn được đánh giá cao – joker

2

tôi sẽ khuyên bạn bài viết này:

SMTP Client - CodeProject

Bạn có thể biên dịch nó dưới Linux và Windows cũng có.

+0

+1 bạn có thể viết ứng dụng SMTP của riêng mình, nhưng nó chắc chắn dễ sử dụng hơn một trong nhiều thứ có thể được tìm thấy trên Interwebs. – JeremyP

+0

Ngoài ra, bạn có thể kiểm tra mã nguồn của các ứng dụng thư khách nguồn mở như sendmail. – rkosegi

+0

+1, cho một phần có giá trị của thông tin :-) –

0

RFC 5321 là đặc tả chính thức cho giao thức SMTP cơ bản.

RFC 2822 là đặc điểm kỹ thuật chính thức cho định dạng email cơ bản.

Lưu ý rằng có nhiều RFC bổ sung mở rộng các quy tắc cơ bản. Ví dụ: RFC 1651 mở rộng SMTP để các tính năng bổ sung có thể được triển khai, chẳng hạn như xác thực bảo mật qua AUTH extension. Và MIME (RFC 2045, 2046, 2047, 2048, và 2049) thường được sử dụng trong các hệ thống thư điện tử hiện đại cho phép file đính kèm, HTML/RTF vv

Đến IETF's website để xem tất cả các thông số kỹ thuật RFC có sẵn được sử dụng bởi hầu hết các giao thức Interpet .

0
bytes_to_receive = sizeof(packet) 

received_bytes = 0; làm { received_bytes + = recv (đệm + received_bytes, bytes_to_receive - received_bytes) } while (received_bytes = bytes_to_receive!)

+0

Bạn có thể giải thích thêm câu trả lời của mình thêm một chút mô tả về giải pháp bạn cung cấp không? – abarisone