From fd67a89688262e4e58337c33728488f5f29196a8 Mon Sep 17 00:00:00 2001 From: Szymon Tokarz Date: Wed, 17 Oct 2012 21:05:02 +0000 Subject: Tlen protocol adopted - code moved to trunk\protocols folder - update project files (based on rev: 27, 228, 204, 350, 279, 280, 1374, 278) - changed code organisation to c++ convention (based on rev: 1092, 503, 504) - changed code to Miranda NG convention (based on rev: 49, 54, 312, 401, 321, 358, 410, 441, 477, 483, 496, 507, 515, 644, 652, 743, 956, 1206, 667, 1040, 1590, 1857) - folders restructurization (based on rev: 1890) - code cleaning (based on rev: 270, 398, 409) - this commit includes adopted sources of tlen_czaty.dll (former mucc.dll) plugin witch is now deprecated and will be removed -- wsx22{at}o2.pl git-svn-id: http://svn.miranda-ng.org/main/trunk@1972 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c --- protocols/Tlen/src/tlen_p2p_old.cpp | 535 ++++++++++++++++++++++++++++++++++++ 1 file changed, 535 insertions(+) create mode 100644 protocols/Tlen/src/tlen_p2p_old.cpp (limited to 'protocols/Tlen/src/tlen_p2p_old.cpp') diff --git a/protocols/Tlen/src/tlen_p2p_old.cpp b/protocols/Tlen/src/tlen_p2p_old.cpp new file mode 100644 index 0000000000..7c1f706d49 --- /dev/null +++ b/protocols/Tlen/src/tlen_p2p_old.cpp @@ -0,0 +1,535 @@ +/* + +Tlen Protocol Plugin for Miranda NG +Copyright (C) 2004-2007 Piotr Piastucki + +This program is free software; you can redistribute it and/or +modify it under the terms of the GNU General Public License +as published by the Free Software Foundation; either version 2 +of the License, or (at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + +*/ +#include "tlen_p2p_old.h" +#include +#include +#include +#include +#include "jabber_list.h" + + +void TlenP2PFreeFileTransfer(TLEN_FILE_TRANSFER *ft) +{ + int i; + if (ft->jid) mir_free(ft->jid); + if (ft->iqId) mir_free(ft->iqId); + if (ft->id2) mir_free(ft->id2); + if (ft->hostName) mir_free(ft->hostName); + if (ft->localName) mir_free(ft->localName); + if (ft->szSavePath) mir_free(ft->szSavePath); + if (ft->szDescription) mir_free(ft->szDescription); + if (ft->filesSize) mir_free(ft->filesSize); + if (ft->files) { + for (i=0; ifileCount; i++) { + if (ft->files[i]) mir_free(ft->files[i]); + } + mir_free(ft->files); + } + mir_free(ft); +} + +TLEN_FILE_PACKET *TlenP2PPacketCreate(int datalen) +{ + TLEN_FILE_PACKET *packet; + + if ((packet=(TLEN_FILE_PACKET *) mir_alloc(sizeof(TLEN_FILE_PACKET))) == NULL) + return NULL; + packet->packet = NULL; + if (datalen > 0) { + if ((packet->packet=(char *) mir_alloc(datalen)) == NULL) { + mir_free(packet); + return NULL; + } + } + packet->maxDataLen = datalen; + packet->type=0; + packet->len=0; + return packet; +} + +void TlenP2PPacketFree(TLEN_FILE_PACKET *packet) +{ + if (packet != NULL) { + if (packet->packet != NULL) + mir_free(packet->packet); + mir_free(packet); + } +} + +void TlenP2PPacketSetType(TLEN_FILE_PACKET *packet, DWORD type) +{ + if (packet != NULL) { + packet->type = type; + } +} + +void TlenP2PPacketSetLen(TLEN_FILE_PACKET *packet, DWORD len) +{ + if (packet != NULL) { + packet->len = len; + } +} + +void TlenP2PPacketPackDword(TLEN_FILE_PACKET *packet, DWORD data) +{ + if (packet != NULL && packet->packet != NULL) { + if (packet->len + sizeof(DWORD) <= packet->maxDataLen) { + (*((DWORD*)((packet->packet)+(packet->len)))) = data; + packet->len += sizeof(DWORD); + } + } +} + +void TlenP2PPacketPackBuffer(TLEN_FILE_PACKET *packet, char *buffer, int len) +{ + if (packet != NULL && packet->packet != NULL) { + if (packet->len + len <= packet->maxDataLen) { + memcpy((packet->packet)+(packet->len), buffer, len); + packet->len += len; + } + } +} + +void TlenP2PInit() { +} + +void TlenP2PUninit() { +} + +int TlenP2PPacketSend(JABBER_SOCKET s, TLEN_FILE_PACKET *packet) +{ + DWORD sendResult; + if (packet != NULL && packet->packet != NULL) { + Netlib_Send(s, (char *)&packet->type, 4, MSG_NODUMP); + Netlib_Send(s, (char *)&packet->len, 4, MSG_NODUMP); + sendResult=Netlib_Send(s, packet->packet, packet->len, MSG_NODUMP); + if (sendResult == SOCKET_ERROR || sendResult != packet->len) return 0; + } + return 1; +} + +TLEN_FILE_PACKET* TlenP2PPacketReceive(JABBER_SOCKET s) +{ + TLEN_FILE_PACKET *packet; + DWORD recvResult; + DWORD type, len, pos; + recvResult = Netlib_Recv(s, (char *)&type, 4, MSG_NODUMP); + if (recvResult == 0 || recvResult == SOCKET_ERROR) return NULL; + recvResult = Netlib_Recv(s, (char *)&len, 4, MSG_NODUMP); + if (recvResult == 0 || recvResult == SOCKET_ERROR) return NULL; + packet = TlenP2PPacketCreate(len); + TlenP2PPacketSetType(packet, type); + TlenP2PPacketSetLen(packet, len); + pos = 0; + while (len > 0) { + recvResult = Netlib_Recv(s, packet->packet+pos, len, MSG_NODUMP); + if (recvResult == 0 || recvResult == SOCKET_ERROR) { + TlenP2PPacketFree(packet); + return NULL; + } + len -= recvResult; + pos += recvResult; + } + return packet; +} + +void TlenP2PEstablishOutgoingConnection(TLEN_FILE_TRANSFER *ft, BOOL sendAck) +{ + char *hash; + char str[300]; + TLEN_FILE_PACKET *packet; + TlenProtocol *proto = ft->proto; + + JabberLog(proto, "Establishing outgoing connection."); + ft->state = FT_ERROR; + if ((packet = TlenP2PPacketCreate(2*sizeof(DWORD) + 20)) != NULL) { + TlenP2PPacketSetType(packet, TLEN_FILE_PACKET_CONNECTION_REQUEST); + TlenP2PPacketPackDword(packet, 1); + TlenP2PPacketPackDword(packet, (DWORD) atoi(ft->iqId)); + _snprintf(str, sizeof(str), "%08X%s%d", atoi(ft->iqId), proto->threadData->username, atoi(ft->iqId)); + hash = TlenSha1(str, (int)strlen(str)); + TlenP2PPacketPackBuffer(packet, hash, 20); + mir_free(hash); + TlenP2PPacketSend(ft->s, packet); + TlenP2PPacketFree(packet); + packet = TlenP2PPacketReceive(ft->s); + if (packet != NULL) { + if (packet->type == TLEN_FILE_PACKET_CONNECTION_REQUEST_ACK) { // acknowledge + if ((int)(*((DWORD*)packet->packet)) == atoi(ft->iqId)) { + ft->state = FT_CONNECTING; + if (sendAck) { + ProtoBroadcastAck(proto->m_szModuleName, ft->hContact, ACKTYPE_FILE, ACKRESULT_CONNECTED, ft, 0); + } + } + } + TlenP2PPacketFree(packet); + } + } +} + +TLEN_FILE_TRANSFER* TlenP2PEstablishIncomingConnection(TlenProtocol *proto, JABBER_SOCKET s, JABBER_LIST list, BOOL sendAck) +{ + JABBER_LIST_ITEM *item = NULL; + TLEN_FILE_PACKET *packet; + int i; + char str[300]; + DWORD iqId; + // TYPE: 0x1 + // LEN: + // (DWORD) 0x1 + // (DWORD) id + // (BYTE) hash[20] + packet = TlenP2PPacketReceive(s); + if (packet == NULL || packet->type != TLEN_FILE_PACKET_CONNECTION_REQUEST || packet->len<28) { + if (packet != NULL) { + TlenP2PPacketFree(packet); + } + return NULL; + } + iqId = *((DWORD *)(packet->packet+sizeof(DWORD))); + i = 0; + while ((i=JabberListFindNext(proto, list, i)) >= 0) { + if ((item=JabberListGetItemPtrFromIndex(proto, i)) != NULL) { + _snprintf(str, sizeof(str), "%d", iqId); + if (!strcmp(item->ft->iqId, str)) { + char *hash, *nick; + int j; + nick = JabberNickFromJID(item->ft->jid); + _snprintf(str, sizeof(str), "%08X%s%d", iqId, nick, iqId); + mir_free(nick); + hash = TlenSha1(str, (int)strlen(str)); + for (j=0;j<20;j++) { + if (hash[j] != packet->packet[2*sizeof(DWORD)+j]) break; + } + mir_free(hash); + if (j == 20) break; + } + } + i++; + } + TlenP2PPacketFree(packet); + if (i >=0) { + if ((packet=TlenP2PPacketCreate(sizeof(DWORD))) != NULL) { + // Send connection establishment acknowledgement + TlenP2PPacketSetType(packet, TLEN_FILE_PACKET_CONNECTION_REQUEST_ACK); + TlenP2PPacketPackDword(packet, (DWORD) atoi(item->ft->iqId)); + TlenP2PPacketSend(s, packet); + TlenP2PPacketFree(packet); + item->ft->state = FT_CONNECTING; + if (sendAck) { + ProtoBroadcastAck(item->ft->proto->m_szModuleName, item->ft->hContact, ACKTYPE_FILE, ACKRESULT_CONNECTED, item->ft, 0); + } + return item->ft; + } + } + return NULL; +} + +static void __cdecl TlenFileBindSocks4Thread(TLEN_FILE_TRANSFER* ft) +{ + BYTE buf[8]; + int status; + +// JabberLog("Waiting for the file to be sent via SOCKS..."); + status = Netlib_Recv(ft->s, (char*)buf, 8, MSG_NODUMP); +// JabberLog("accepted connection !!!"); + if ( status == SOCKET_ERROR || status < 8 || buf[1] != 90) { + status = 1; + } else { + status = 0; + } + if (!status) { + ft->pfnNewConnectionV2(ft->s, 0, NULL); + } else { + if (ft->state != FT_SWITCH) { + ft->state = FT_ERROR; + } + } + JabberLog(ft->proto, "Closing connection for this file transfer..."); +// Netlib_CloseHandle(ft->s); + if (ft->hFileEvent != NULL) + SetEvent(ft->hFileEvent); + +} +static void __cdecl TlenFileBindSocks5Thread(TLEN_FILE_TRANSFER* ft) +{ + BYTE buf[256]; + int status; + +// JabberLog("Waiting for the file to be sent via SOCKS..."); + status = Netlib_Recv(ft->s, (char*)buf, sizeof(buf), MSG_NODUMP); +// JabberLog("accepted connection !!!"); + if ( status == SOCKET_ERROR || status < 7 || buf[1] != 0) { + status = 1; + } else { + status = 0; + } + if (!status) { + ft->pfnNewConnectionV2(ft->s, 0, NULL); + } else { + if (ft->state != FT_SWITCH) { + ft->state = FT_ERROR; + } + } +// JabberLog("Closing connection for this file transfer..."); +// Netlib_CloseHandle(ft->s); + if (ft->hFileEvent != NULL) + SetEvent(ft->hFileEvent); + +} + +static JABBER_SOCKET TlenP2PBindSocks4(SOCKSBIND * sb, TLEN_FILE_TRANSFER *ft) +{ //rfc1928 + int len; + BYTE buf[256]; + int status; + struct in_addr in; + NETLIBOPENCONNECTION nloc; + JABBER_SOCKET s; + + nloc.cbSize = NETLIBOPENCONNECTION_V1_SIZE;//sizeof(NETLIBOPENCONNECTION); + nloc.szHost = sb->szHost; + nloc.wPort = sb->wPort; + nloc.flags = 0; + s = (HANDLE) CallService(MS_NETLIB_OPENCONNECTION, (WPARAM) ft->proto->hFileNetlibUser, (LPARAM) &nloc); + if (s == NULL) { +// JabberLog("Connection failed (%d), thread ended", WSAGetLastError()); + return NULL; + } + buf[0] = 4; //socks4 + buf[1] = 2; //2-bind, 1-connect + *(PWORD)(buf+2) = htons(0); // port + *(PDWORD)(buf+4) = INADDR_ANY; + if (sb->useAuth) { + strcpy((char*)buf+8, sb->szUser); + len = (int)strlen(sb->szUser); + } else { + buf[8] = 0; + len = 0; + } + len += 9; + status = Netlib_Send(s, (char*)buf, len, MSG_NODUMP); + if (status == SOCKET_ERROR || status < len) { +// JabberLog("Send failed (%d), thread ended", WSAGetLastError()); + Netlib_CloseHandle(s); + return NULL; + } + status = Netlib_Recv(s, (char*)buf, 8, MSG_NODUMP); + if (status == SOCKET_ERROR || status < 8 || buf[1] != 90) { +// JabberLog("SOCKS4 negotiation failed"); + Netlib_CloseHandle(s); + return NULL; + } + status = Netlib_Recv(s, (char*)buf, sizeof(buf), MSG_NODUMP); + if ( status == SOCKET_ERROR || status < 7 || buf[0] != 5 || buf[1] != 0) { +// JabberLog("SOCKS5 request failed"); + Netlib_CloseHandle(s); + return NULL; + } + in.S_un.S_addr = *(PDWORD)(buf+4); + strcpy(sb->szHost, inet_ntoa(in)); + sb->wPort = htons(*(PWORD)(buf+2)); + ft->s = s; + JabberForkThread((void (__cdecl *)(void*))TlenFileBindSocks4Thread, 0, ft); + return s; +} + +static JABBER_SOCKET TlenP2PBindSocks5(SOCKSBIND * sb, TLEN_FILE_TRANSFER *ft) +{ //rfc1928 + BYTE buf[512]; + int len, status; + NETLIBOPENCONNECTION nloc; + struct in_addr in; + JABBER_SOCKET s; + + nloc.cbSize = NETLIBOPENCONNECTION_V1_SIZE;//sizeof(NETLIBOPENCONNECTION); + nloc.szHost = sb->szHost; + nloc.wPort = sb->wPort; + nloc.flags = 0; + s = (HANDLE) CallService(MS_NETLIB_OPENCONNECTION, (WPARAM) ft->proto->hFileNetlibUser, (LPARAM) &nloc); + if (s == NULL) { + JabberLog(ft->proto, "Connection failed (%d), thread ended", WSAGetLastError()); + return NULL; + } + buf[0] = 5; //yep, socks5 + buf[1] = 1; //one auth method + buf[2] = sb->useAuth?2:0; // authorization + status = Netlib_Send(s, (char*)buf, 3, MSG_NODUMP); + if (status == SOCKET_ERROR || status < 3) { + JabberLog(ft->proto, "Send failed (%d), thread ended", WSAGetLastError()); + Netlib_CloseHandle(s); + return NULL; + } + status = Netlib_Recv(s, (char*)buf, 2, MSG_NODUMP); + if (status == SOCKET_ERROR || status < 2 || (buf[1] != 0 && buf[1] != 2)) { + JabberLog(ft->proto, "SOCKS5 negotiation failed"); + Netlib_CloseHandle(s); + return NULL; + } + if (buf[1] == 2) { //rfc1929 + int nUserLen, nPassLen; + PBYTE pAuthBuf; + + nUserLen = (int)strlen(sb->szUser); + nPassLen = (int)strlen(sb->szPassword); + pAuthBuf = (PBYTE)mir_alloc(3+nUserLen+nPassLen); + pAuthBuf[0] = 1; //auth version + pAuthBuf[1] = nUserLen; + memcpy(pAuthBuf+2, sb->szUser, nUserLen); + pAuthBuf[2+nUserLen]=nPassLen; + memcpy(pAuthBuf+3+nUserLen,sb->szPassword,nPassLen); + status = Netlib_Send(s, (char*)pAuthBuf, 3+nUserLen+nPassLen, MSG_NODUMP); + mir_free(pAuthBuf); + if (status == SOCKET_ERROR || status < 3 + nUserLen+nPassLen) { + JabberLog(ft->proto, "Send failed (%d), thread ended", WSAGetLastError()); + Netlib_CloseHandle(s); + return NULL; + } + status = Netlib_Recv(s, (char*)buf, sizeof(buf), MSG_NODUMP); + if (status == SOCKET_ERROR || status < 2 || buf[1] != 0) { + JabberLog(ft->proto, "SOCKS5 sub-negotiation failed"); + Netlib_CloseHandle(s); + return NULL; + } + } + + { PBYTE pInit; + int nHostLen=4; + DWORD hostIP=INADDR_ANY; + pInit=(PBYTE)mir_alloc(6+nHostLen); + pInit[0]=5; //SOCKS5 + pInit[1]=2; //bind + pInit[2]=0; //reserved + pInit[3]=1; + *(PDWORD)(pInit+4)=hostIP; + *(PWORD)(pInit+4+nHostLen)=htons(0); + status = Netlib_Send(s, (char*)pInit, 6+nHostLen, MSG_NODUMP); + mir_free(pInit); + if (status == SOCKET_ERROR || status < 6 + nHostLen) { +// JabberLog("Send failed (%d), thread ended", WSAGetLastError()); + Netlib_CloseHandle(s); + return NULL; + } + } + status = Netlib_Recv(s, (char*)buf, sizeof(buf), MSG_NODUMP); + if ( status == SOCKET_ERROR || status < 7 || buf[0] != 5 || buf[1] != 0) { +// JabberLog("SOCKS5 request failed"); + Netlib_CloseHandle(s); + return NULL; + } + if (buf[2] == 1) { // domain + len = buf[4]; + memcpy(sb->szHost, buf+5, len); + sb->szHost[len]=0; + len += 4; + } else { // ip address + in.S_un.S_addr = *(PDWORD)(buf+4); + strcpy(sb->szHost, inet_ntoa(in)); + len = 8; + } + sb->wPort = htons(*(PWORD)(buf+len)); + ft->s = s; + + JabberForkThread((void (__cdecl *)(void*))TlenFileBindSocks5Thread, 0, ft); + return s; +} + + +JABBER_SOCKET TlenP2PListen(TLEN_FILE_TRANSFER *ft) +{ + NETLIBBIND nlb = {0}; + JABBER_SOCKET s = NULL; + int useProxy; + DBVARIANT dbv; + SOCKSBIND sb; + struct in_addr in; + TlenProtocol *proto = ft->proto; + useProxy=0; + if (ft->localName != NULL) mir_free(ft->localName); + ft->localName = NULL; + ft->wPort = 0; + if (DBGetContactSettingByte(NULL, proto->m_szModuleName, "UseFileProxy", FALSE)) { + if (!DBGetContactSetting(NULL, proto->m_szModuleName, "FileProxyHost", &dbv)) { + strcpy(sb.szHost, dbv.pszVal); + DBFreeVariant(&dbv); + sb.wPort = DBGetContactSettingWord(NULL, proto->m_szModuleName, "FileProxyPort", 0); + sb.useAuth = FALSE; + strcpy(sb.szUser, ""); + strcpy(sb.szPassword, ""); + if (DBGetContactSettingByte(NULL, proto->m_szModuleName, "FileProxyAuth", FALSE)) { + sb.useAuth = TRUE; + if (!DBGetContactSetting(NULL, proto->m_szModuleName, "FileProxyUsername", &dbv)) { + strcpy(sb.szUser, dbv.pszVal); + DBFreeVariant(&dbv); + } + if (!DBGetContactSetting(NULL, proto->m_szModuleName, "FileProxyPassword", &dbv)) { + CallService(MS_DB_CRYPT_DECODESTRING, strlen(dbv.pszVal)+1, (LPARAM) dbv.pszVal); + strcpy(sb.szPassword, dbv.pszVal); + DBFreeVariant(&dbv); + } + } + switch (DBGetContactSettingWord(NULL, proto->m_szModuleName, "FileProxyType", 0)) { + case 0: // forwarding + useProxy = 1; + break; + case 1: // socks4 + s = TlenP2PBindSocks4(&sb, ft); + useProxy = 2; + break; + case 2: // socks5 + s = TlenP2PBindSocks5(&sb, ft); + useProxy = 2; + break; + } + ft->localName = mir_strdup(sb.szHost); + ft->wPort = sb.wPort; + ft->wLocalPort = sb.wPort; + } + } + if (useProxy<2) { + nlb.cbSize = sizeof(NETLIBBIND); + nlb.pfnNewConnectionV2 = ft->pfnNewConnectionV2; + nlb.wPort = 0; // Use user-specified incoming port ranges, if available + nlb.pExtra = proto; + JabberLog(ft->proto, "Calling MS_NETLIB_BINDPORT"); + s = (HANDLE) CallService(MS_NETLIB_BINDPORT, (WPARAM) ft->proto->hNetlibUser, (LPARAM) &nlb); + JabberLog(ft->proto, "listening on %d",s); + } + if (useProxy == 0) { + in.S_un.S_addr = htonl(nlb.dwExternalIP); + ft->localName = mir_strdup(inet_ntoa(in)); + ft->wPort = nlb.wPort; + ft->wLocalPort = nlb.wExPort; + } + if (s != NULL) { +// listenCount++; + } + return s; +} + +void TlenP2PStopListening(JABBER_SOCKET s) { + if (s != NULL) { +// listenCount--; +// if (listenCount <= 0) { +// Netlib_CloseHandle(s); +// } + } +} -- cgit v1.2.3