/*------------------------------------------------------------------------------*\ StateConnect() - Initiates network-connection to POP-server \*------------------------------------------------------------------------------*/ void BmPopper::StateConnect() { BNetAddress addr; if (addr.SetTo( mPopAccount->Server().String(), mPopAccount->PortNr()) != B_OK) { BmString s = BmString("Could not determine address of POP-Server ") << mPopAccount->Server(); throw BM_network_error( s); } if (!Connect( &addr)) { BmString s = BmString("Could not connect to POP-Server ") << mPopAccount->Server() << "\n\bError:\n\t" << mErrorString; throw BM_network_error( s); } BmString encryptionType = mPopAccount->EncryptionType(); if (TheNetEndpointRoster->SupportsEncryption() && (encryptionType.ICompare(BmPopAccount::ENCR_TLS) == 0 || encryptionType.ICompare(BmPopAccount::ENCR_SSL) == 0)) { // straight TLS or SSL, we start the encryption layer: if (!StartEncryption(encryptionType.String())) return; } // accept server greeting (either encrypted or unencrypted): CheckForPositiveAnswer(); Regexx rx; if (rx.exec( StatusText(), "(<.+?>)\\s*$", Regexx::newline)) { mServerTimestamp = rx.match[0]; } }
/*------------------------------------------------------------------------------*\ StateConnect() - Initiates network-connection to SMTP-server \*------------------------------------------------------------------------------*/ void BmSmtp::StateConnect() { BNetAddress addr; if (addr.SetTo( mSmtpAccount->SMTPServer().String(), mSmtpAccount->PortNr()) != B_OK) { BmString s = BmString("Could not determine address of SMTP-Server ") << mSmtpAccount->SMTPServer(); throw BM_network_error( s); } if (!Connect( &addr)) { BmString s = BmString("Could not connect to SMTP-Server ") << mSmtpAccount->SMTPServer() << "\n\bError:\n\t"<< mErrorString; throw BM_network_error( s); } BmString encryptionType = mSmtpAccount->EncryptionType(); if (TheNetEndpointRoster->SupportsEncryption() && (encryptionType.ICompare(BmSmtpAccount::ENCR_TLS) == 0 || encryptionType.ICompare(BmSmtpAccount::ENCR_SSL) == 0)) { // straight TLS or SSL, we start the encryption layer: if (!StartEncryption(encryptionType.String())) return; } // accept server greeting (either encrypted or unencrypted): CheckForPositiveAnswer(); }
status_t BNetEndpoint::Connect(const BNetAddress& address) { if (fSocket < 0 && _SetupSocket() != B_OK) return fStatus; sockaddr_in addr; if (address.GetAddr(addr) != B_OK) return B_ERROR; if (connect(fSocket, (sockaddr *) &addr, sizeof(addr)) < 0) { Close(); fStatus = errno; return B_ERROR; } socklen_t addrSize = sizeof(addr); if (getpeername(fSocket, (sockaddr *) &addr, &addrSize) < 0) { Close(); fStatus = errno; return B_ERROR; } fPeer.SetTo(addr); return B_OK; }
status_t BNetEndpoint::Bind(const BNetAddress& address) { if (fSocket < 0 && _SetupSocket() != B_OK) return fStatus; struct sockaddr_in addr; status_t status = address.GetAddr(addr); if (status != B_OK) return status; if (bind(fSocket, (struct sockaddr *)&addr, sizeof(addr)) < 0) { fStatus = errno; Close(); return B_ERROR; } socklen_t addrSize = sizeof(addr); if (getsockname(fSocket, (struct sockaddr *)&addr, &addrSize) < 0) { fStatus = errno; Close(); return B_ERROR; } fAddr.SetTo(addr); return B_OK; }
status_t CDDBQuery::_Connect() { if (fConnected) _Disconnect(); BNetAddress address; status_t status = address.SetTo(fServerName.String(), fPort); if (status != B_OK) return status; status = fSocket.Connect(address); if (status != B_OK) return status; fConnected = true; BString tmp; _ReadLine(tmp); _IdentifySelf(); return B_OK; }
int32 BNetEndpoint::SendTo(const void* buffer, size_t length, const BNetAddress& address, int flags) { if (fSocket < 0 && _SetupSocket() != B_OK) return fStatus; struct sockaddr_in addr; if (address.GetAddr(addr) != B_OK) return B_ERROR; ssize_t bytesSent = sendto(fSocket, buffer, length, flags, (struct sockaddr *) &addr, sizeof(addr)); if (bytesSent < 0) fStatus = errno; return bytesSent; }
int32 BNetEndpoint::ReceiveFrom(void* buffer, size_t length, BNetAddress& address, int flags) { if (fSocket < 0 && _SetupSocket() != B_OK) return fStatus; if (fTimeout >= 0 && IsDataPending(fTimeout) == false) return 0; struct sockaddr_in addr; socklen_t addrSize = sizeof(addr); ssize_t bytesReceived = recvfrom(fSocket, buffer, length, flags, (struct sockaddr *)&addr, &addrSize); if (bytesReceived < 0) fStatus = errno; else address.SetTo(addr); return bytesReceived; }
bool FtpClient::_OpenDataConnection() { string host, cmd, replyString; unsigned short port; BNetAddress addr; int i, code, codeType; bool rc = false; struct sockaddr_in sa; delete fData; fData = 0; fData = new BNetEndpoint; if (_TestState(ftp_passive)) { // Here we send a "pasv" command and connect to the remote server // on the port it sends back to us cmd = "PASV"; if (_SendRequest(cmd)) { if (_GetReply(replyString, code, codeType)) { if (codeType == 2) { // It should give us something like: // "227 Entering Passive Mode (192,168,1,1,10,187)" int paddr[6]; unsigned char ucaddr[6]; i = replyString.find('('); i++; replyString = replyString.substr(i, replyString.find(')') - i); if (sscanf(replyString.c_str(), "%d,%d,%d,%d,%d,%d", &paddr[0], &paddr[1], &paddr[2], &paddr[3], &paddr[4], &paddr[5]) != 6) { // cannot do passive. Do a little harmless rercursion here _ClearState(ftp_passive); return _OpenDataConnection(); } for (i = 0; i < 6; i++) ucaddr[i] = (unsigned char)(paddr[i] & 0xff); memcpy(&sa.sin_addr, &ucaddr[0], (size_t) 4); memcpy(&sa.sin_port, &ucaddr[4], (size_t) 2); addr.SetTo(sa); if (fData->Connect(addr) == B_NO_ERROR) rc = true; } } } else { // cannot do passive. Do a little harmless rercursion here _ClearState(ftp_passive); rc = _OpenDataConnection(); } } else { // Here we bind to a local port and send a PORT command if (fData->Bind() == B_NO_ERROR) { char buf[255]; fData->Listen(); addr = fData->LocalAddr(); addr.GetAddr(buf, &port); host = buf; i = 0; while (i >= 0) { i = host.find('.', i); if (i >= 0) host[i] = ','; } sprintf(buf, ",%d,%d", (port & 0xff00) >> 8, port & 0x00ff); cmd = "PORT "; cmd += host; cmd += buf; _SendRequest(cmd); _GetReply(replyString, code, codeType); // PORT failure is in the 500-range if (codeType == 2) rc = true; } }
bool FtpClient::Connect(const string& server, const string& login, const string& passwd) { bool rc = false; int code, codeType; string cmd, replyString; BNetAddress addr; delete fControl; delete fData; fControl = new BNetEndpoint; if (fControl->InitCheck() != B_NO_ERROR) return false; addr.SetTo(server.c_str(), "tcp", "ftp"); if (fControl->Connect(addr) == B_NO_ERROR) { // read the welcome message, do the login if (_GetReply(replyString, code, codeType)) { if (code != 421 && codeType != 5) { cmd = "USER "; cmd += login; _SendRequest(cmd); if (_GetReply(replyString, code, codeType)) { switch (code) { case 230: case 202: rc = true; break; case 331: // password needed cmd = "PASS "; cmd += passwd; _SendRequest(cmd); if (_GetReply(replyString, code, codeType)) { if (codeType == 2) rc = true; } break; default: break; } } } } } if (rc == true) _SetState(ftp_connected); else { delete fControl; fControl = 0; } return rc; }
int32 DownloadLoop(void *pDummy) { char *pDetails, *pFile, *pIP, *pPort, *pUser , *pTemp, *pLength, *pLeaf, *pFilenameEnd; uint32 iIPAddress, iFileLength, iDataLength; int32 iPort, iBytesReceived; status_t stReturnCode; BNetEndpoint bneSong; BNetAddress bnaSong; BNetBuffer bnbSong; BFile *bfSong; Preferences *myPrefs; DownloadView *dlView; DownloadWindow *myDownloadWindow; myPrefs = (Preferences *)pDummy; pDetails = myPrefs->pDownloadDetails; pUser = pDetails; pTemp = strchr(pDetails, ' '); *pTemp = '\0'; pTemp++; pIP = pTemp; pTemp = strchr(pTemp, ' '); *pTemp = '\0'; iIPAddress = strtoul(pIP, NULL, 10); pTemp++; pPort = pTemp; pTemp = strchr(pTemp, ' '); *pTemp = '\0'; iPort = atol(pPort); pTemp++; pTemp = strchr(pTemp, '"'); pFile = pTemp; pTemp++; pTemp = strchr(pTemp, '"') + 1; *pTemp = '\0'; pFilenameEnd = pTemp - 1; bnbSong.AppendData(myPrefs->GetUser(), strlen(myPrefs->GetUser())); bnbSong.AppendData(" ", 1); bnbSong.AppendData(pFile, strlen(pFile)); bnbSong.AppendData(" ", 1); bnbSong.AppendData("0", 1); for(pLeaf = pTemp; *pLeaf != '\\' && *pLeaf != '/'; pLeaf-- ); pLeaf++; *pFilenameEnd = '\0'; BPath Path(myPrefs->GetDownloadPath(), NULL, true); if(Path.InitCheck() == B_OK) { // Making sure we have a valid path. Path.Append(pLeaf); bfSong = new BFile(Path.Path(), B_WRITE_ONLY|B_CREATE_FILE|B_OPEN_AT_END); } else // No valid path, use default (current directory) bfSong = new BFile(pLeaf, B_WRITE_ONLY|B_CREATE_FILE|B_OPEN_AT_END); if(bfSong->InitCheck() == B_OK) { stReturnCode = bnaSong.SetTo(iIPAddress, iPort); stReturnCode = bneSong.Connect(bnaSong); // now we need to recieve the mysterious '1'; char *pReceiveBuffer = (char *)malloc(4096); iBytesReceived = bneSong.Receive(pReceiveBuffer, 1); if(iBytesReceived == 1) { pLength = (char *)malloc(50); // more than enough to hold a big number :) printf("sending get command\n"); bneSong.Send("GET",3); pTemp = (char *)bnbSong.Data(); bneSong.Send(pTemp, strlen(pTemp)); pTemp = pLength - 1; // the other client now sends a length followed by the mp3 // according to the unoffical protocol you can not tell how long // the length is. but the mp3 starts // with 0xFF while(isdigit((unsigned char)*pReceiveBuffer) != 0) { pTemp++; iBytesReceived = bneSong.Receive(pReceiveBuffer, 1); *pTemp = *pReceiveBuffer; } *pTemp = '\0'; iFileLength = strtoul(pLength, NULL, 10); //create the download window now we know all the details myDownloadWindow = new DownloadWindow(BRect(100,100, 400, 200), "BeNapster Download", B_DOCUMENT_WINDOW_LOOK, B_NORMAL_WINDOW_FEEL, B_NOT_RESIZABLE, B_CURRENT_WORKSPACE); myDownloadWindow->Show(); myDownloadWindow->Lock(); dlView = myDownloadWindow->AddTransfer(pFile, iFileLength); myDownloadWindow->Unlock(); // The 0xFF is part of the mp3 so we need to write it out bfSong->Write(pReceiveBuffer, iBytesReceived); iDataLength = iBytesReceived; myDownloadWindow->Lock(); dlView->AddBytesReceived(iBytesReceived); myDownloadWindow->Unlock(); iBytesReceived = bneSong.Receive(pReceiveBuffer, 4096); bfSong->Write(pReceiveBuffer, iBytesReceived); iDataLength += iBytesReceived; myDownloadWindow->Lock(); dlView->AddBytesReceived(iBytesReceived); myDownloadWindow->Unlock(); while(iDataLength != iFileLength) { iBytesReceived = bneSong.Receive(pReceiveBuffer, 4096); if (iBytesReceived < 0) { break; } bfSong->Write(pReceiveBuffer, iBytesReceived); iDataLength += iBytesReceived; myDownloadWindow->Lock(); dlView->AddBytesReceived(iBytesReceived); myDownloadWindow->Unlock(); } bfSong->Unset(); delete (bfSong); myDownloadWindow->PostMessage(B_QUIT_REQUESTED); } } return(0); }