📄 transfersocket.cpp
字号:
m_pOwner->ShowStatus(str, 1);
Close();
if (!m_bSentClose)
{
m_nMode|=CSMODE_TRANSFERERROR;
m_bSentClose=TRUE;
m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode);
}
}
else
{
/* Set internal socket send buffer to twice the programs buffer size
* this should fix the speed problems some users have reported
*/
DWORD value;
int len = sizeof(value);
GetSockOpt(SO_SNDBUF, &value, &len);
if (value < (BUFSIZE*2))
{
value = BUFSIZE * 2;
SetSockOpt(SO_SNDBUF, &value, sizeof(value));
}
}
if (m_nTransferState == STATE_STARTING)
{
m_nTransferState = STATE_STARTED;
m_TransferedFirst = m_StartTime = CTime::GetCurrentTime();
m_LastActiveTime=CTime::GetCurrentTime();
if (m_pSslLayer)
{
AddLayer(m_pSslLayer);
int res = m_pSslLayer->InitSSLConnection(true);
if (res == SSL_FAILURE_LOADDLLS)
m_pOwner->ShowStatus(IDS_ERRORMSG_CANTLOADSSLDLLS, 1);
else if (res == SSL_FAILURE_INITSSL)
m_pOwner->ShowStatus(IDS_ERRORMSG_CANTINITSSL, 1);
if (res)
{
Close();
if (!m_bSentClose)
{
m_nMode |= CSMODE_TRANSFERERROR;
m_bSentClose = TRUE;
m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode);
}
return;
}
}
if (m_pGssLayer)
{
AddLayer(m_pGssLayer);
}
}
}
void CTransferSocket::OnClose(int nErrorCode)
{
LogMessage(__FILE__, __LINE__, this, FZ_LOG_DEBUG, _T("OnClose(%d)"), nErrorCode);
if (m_nTransferState == STATE_WAITING)
{
m_nNotifyWaiting |= FD_CLOSE;
return;
}
OnReceive(0);
Close();
if (!m_bSentClose)
{
m_bSentClose=TRUE;
m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode);
}
}
int CTransferSocket::CheckForTimeout(int delay)
{
UpdateStatusBar(false);
if (!m_bCheckTimeout)
return 1;
CTimeSpan span = CTime::GetCurrentTime()-m_LastActiveTime;
if (span.GetTotalSeconds()>=delay)
{
m_pOwner->ShowStatus(IDS_ERRORMSG_TIMEOUT, 1);
Close();
if (!m_bSentClose)
{
m_nMode |= CSMODE_TRANSFERTIMEOUT;
m_bSentClose = TRUE;
VERIFY(m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode));
}
return 2;
}
return 1;
}
void CTransferSocket::SetActive()
{
LogMessage(__FILE__, __LINE__, this, FZ_LOG_DEBUG, _T("SetActive()"));
if (m_nTransferState == STATE_WAITING)
m_nTransferState = STATE_STARTING;
m_bCheckTimeout = TRUE;
m_LastActiveTime = CTime::GetCurrentTime();
if (m_nNotifyWaiting & FD_READ)
OnReceive(0);
if (m_nNotifyWaiting & FD_WRITE)
OnSend(0);
if (m_nNotifyWaiting & FD_CLOSE)
OnClose(0);
}
void CTransferSocket::OnSend(int nErrorCode)
{
if (m_nTransferState == STATE_WAITING)
{
m_nNotifyWaiting |= FD_WRITE;
return;
}
if (m_bSentClose)
return;
if (m_bListening)
return;
if (!(m_nMode&CSMODE_UPLOAD))
return;
if (m_nTransferState == STATE_STARTING)
OnConnect(0);
if (m_useZlib)
{
if (!m_pBuffer)
{
m_pBuffer = new char[BUFSIZE];
m_bufferpos = 0;
m_zlibStream.next_out = (Bytef *)m_pBuffer;
m_zlibStream.avail_out = BUFSIZE;
}
if (!m_pBuffer2)
{
m_pBuffer2 = new char[BUFSIZE];
m_zlibStream.next_in = (Bytef *)m_pBuffer2;
}
bool beenWaiting = false;
while (true)
{
int numsend;
if (!m_zlibStream.avail_in)
{
if (m_pFile)
{
DWORD numread;
numread = ReadDataFromFile(m_pBuffer2, BUFSIZE);
if (numread < 0)
return;
m_transferdata.transferleft -= numread;
m_zlibStream.next_in = (Bytef *)m_pBuffer2;
m_zlibStream.avail_in = numread;
if (numread < BUFSIZE)
m_pFile = 0;
}
}
if (!m_zlibStream.avail_out)
{
if (m_bufferpos >= BUFSIZE)
{
m_bufferpos = 0;
m_zlibStream.next_out = (Bytef *)m_pBuffer;
m_zlibStream.avail_out = BUFSIZE;
}
}
int res = Z_OK;
if (m_zlibStream.avail_out)
{
res = deflate(&m_zlibStream, m_pFile ? 0 : Z_FINISH);
if (res != Z_OK && (!m_pFile && res != Z_STREAM_END))
{
m_pOwner->ShowStatus("ZLib error", 1);
Close();
if (!m_bSentClose)
{
m_nMode |= CSMODE_TRANSFERERROR;
m_bSentClose = TRUE;
m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode);
}
return;
}
}
numsend = BUFSIZE;
int len = BUFSIZE - m_bufferpos - m_zlibStream.avail_out;
if (!len && !m_pFile)
break;
if (len < BUFSIZE)
numsend = len;
int nLimit = (int)m_pOwner->GetAbleToUploadSize(beenWaiting);
if (nLimit != -1 && GetState() != closed && numsend > nLimit)
numsend = nLimit;
if (!numsend)
{
TriggerEvent(FD_WRITE);
return;
}
int numsent = Send(m_pBuffer + m_bufferpos, numsend);
if (numsent == SOCKET_ERROR)
{
/* Give control back to the system. Else FileZilla would
* consume most CPU power until the data was sent.
* This behaviour is very strange, and I can't explain it,
* maybe it's just another bug in Windows
*/
Sleep(0);
int nError = GetLastError();
if (nError == WSAENOTCONN)
{
//Not yet connected
return;
}
else if (m_pSslLayer && nError == WSAESHUTDOWN)
{
// Do nothing, wait for shutdown complete notification.
return;
}
else if (nError != WSAEWOULDBLOCK)
{
if (ShutDown() || GetLastError() != WSAEWOULDBLOCK)
{
Close();
if (!m_bSentClose)
{
m_nMode |= CSMODE_TRANSFERERROR;
m_bSentClose = TRUE;
m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode);
}
}
}
UpdateStatusBar(false);
return;
}
Transfered( numsent, CTime::GetCurrentTime());
m_pOwner->SpeedLimitAddUploadedBytes(numsent);
m_LastActiveTime = CTime::GetCurrentTime();
UpdateSendLed();
m_bufferpos += numsent;
UpdateStatusBar(false);
if (!m_zlibStream.avail_in && !m_pFile && m_zlibStream.avail_out &&
m_zlibStream.avail_out + m_bufferpos == BUFSIZE && res == Z_STREAM_END)
{
if (ShutDown() || GetLastError() != WSAEWOULDBLOCK)
{
Close();
if (!m_bSentClose)
{
m_bSentClose = TRUE;
m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode);
}
}
return;
}
//Check if there are other commands in the command queue.
MSG msg;
if (PeekMessage(&msg,0, 0, 0, PM_NOREMOVE))
{
TriggerEvent(FD_WRITE);
return;
}
}
}
else
{
if (!m_pFile)
return;
if (!m_pBuffer)
m_pBuffer = new char[BUFSIZE];
int numread;
bool beenWaiting = false;
_int64 currentBufferSize;
if (GetState() != closed)
currentBufferSize = m_pOwner->GetAbleToUploadSize(beenWaiting);
else
currentBufferSize = BUFSIZE;
if (!currentBufferSize && !m_bufferpos)
{
// Not allowed to send yet, try later
TriggerEvent(FD_WRITE);
return;
}
else if (m_bufferpos < currentBufferSize)
{
numread = ReadDataFromFile(m_pBuffer + m_bufferpos, static_cast<int>(currentBufferSize - m_bufferpos));
if (numread < 0 )
return;
else if (!numread && !m_bufferpos)
{
if (ShutDown() || GetLastError() != WSAEWOULDBLOCK)
{
Close();
if (!m_bSentClose)
{
m_bSentClose = TRUE;
m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode);
}
}
return;
}
}
else
numread = 0;
ASSERT((numread+m_bufferpos) <= BUFSIZE);
ASSERT(numread>=0);
ASSERT(m_bufferpos>=0);
if (numread+m_bufferpos <= 0)
{
if (ShutDown() || GetLastError()!=WSAEWOULDBLOCK)
{
Close();
if (!m_bSentClose)
{
m_bSentClose=TRUE;
m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode);
}
}
return;
}
int numsent = Send(m_pBuffer, numread + m_bufferpos);
while (TRUE)
{
if (numsent != SOCKET_ERROR)
{
Transfered(numsent, CTime::GetCurrentTime());
m_pOwner->SpeedLimitAddUploadedBytes(numsent);
m_LastActiveTime = CTime::GetCurrentTime();
UpdateSendLed();
m_transferdata.transferleft -= numsent;
}
if (numsent==SOCKET_ERROR || !numsent)
{
/* Give control back to the system. Else FileZilla would
* consume most CPU power until the data was sent.
* This behaviour is very strange, and I can't explain it,
* maybe it's just another bug in Windows
*/
Sleep(0);
int nError = GetLastError();
if (nError == WSAENOTCONN)
{
//Not yet connected
m_bufferpos += numread;
return;
}
else if (nError == WSAEWOULDBLOCK)
m_bufferpos += numread;
else if (m_pSslLayer && nError == WSAESHUTDOWN)
{
m_bufferpos += numread;
// Do nothing, wait for shutdown complete notification.
return;
}
else
{
if (ShutDown() || GetLastError() != WSAEWOULDBLOCK)
{
Close();
if (!m_bSentClose)
{
m_nMode |= CSMODE_TRANSFERERROR;
m_bSentClose = TRUE;
m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode);
}
}
}
UpdateStatusBar(false);
return;
}
else
{
int pos = numread + m_bufferpos - numsent;
if (pos < 0 || (numsent + pos) > BUFSIZE)
{
LogMessage(__FILE__, __LINE__, this, FZ_LOG_WARNING, _T("Index out of range"));
if (ShutDown() || GetLastError() != WSAEWOULDBLOCK)
{
Close();
if (!m_bSentClose)
{
m_nMode |= CSMODE_TRANSFERERROR;
m_bSentClose = TRUE;
m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode);
}
}
return;
}
else if (!pos && numread < (currentBufferSize-m_bufferpos) && m_bufferpos != currentBufferSize)
{
if (ShutDown() || GetLastError() != WSAEWOULDBLOCK)
{
Close();
if (!m_bSentClose)
{
m_bSentClose = TRUE;
m_pOwner->m_pOwner->PostThreadMessage(m_nInternalMessageID, FZAPI_THREADMSG_TRANSFEREND, m_nMode);
}
}
return;
}
else if (!pos)
m_bufferpos = 0;
else
{
memmove(m_pBuffer, m_pBuffer+numsent, pos);
m_bufferpos=pos;
}
}
//Check if there are other commands in the command queue.
MSG msg;
if (PeekMessage(&msg, 0, m_nInternalMessageID, m_nInternalMessageID, PM_NOREMOVE))
{
//Send resume message
LogMessage(__FILE__, __LINE__, this, FZ_LOG_DEBUG, _T("Message waiting in queue, resuming later"));
TriggerEvent(FD_WRITE);
UpdateStatusBar(false);
return;
}
UpdateStatusBar(false);
if (GetState() != closed)
currentBufferSize = m_pOwner->GetAbleToUploadSize( beenWaiting);
else
currentBufferSize = BUFSIZE;
if (m_bufferpos < currentBufferSize)
{
numread = ReadDataFromFile(m_pBuffer + m_bufferpos, static_cast<int>(currentBufferSize - m_bufferpos));
if (numread < 0 )
return;
else if (!numread && !m_bufferpos)
{
if (ShutDown() || GetLastError() != WSAEWOULDBLOCK)
{
Close();
if (!m_bSentClose)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -