Click here to Skip to main content
15,917,645 members
Home / Discussions / C / C++ / MFC
   

C / C++ / MFC

 
GeneralRe: A console input/output from a multiline edit control Pin
David Crow4-Sep-03 3:00
David Crow4-Sep-03 3:00 
GeneralRe: A console input/output from a multiline edit control Pin
Jerome Conus4-Sep-03 3:51
Jerome Conus4-Sep-03 3:51 
GeneralRe: A console input/output from a multiline edit control Pin
David Crow4-Sep-03 4:10
David Crow4-Sep-03 4:10 
GeneralRe: A console input/output from a multiline edit control Pin
lagdaemon6-Nov-09 5:30
lagdaemon6-Nov-09 5:30 
Questionhow to save the drawings in an appropriate format Pin
Member 5541134-Sep-03 0:29
Member 5541134-Sep-03 0:29 
AnswerRe: how to save the drawings in an appropriate format Pin
vcplusplus4-Sep-03 3:03
vcplusplus4-Sep-03 3:03 
AnswerRe: how to save the drawings in an appropriate format Pin
Simon.W4-Sep-03 3:12
Simon.W4-Sep-03 3:12 
GeneralCAsyncSocket with http supported file-resume Pin
zjkw4-Sep-03 0:22
zjkw4-Sep-03 0:22 
my trouble is: Is necessary to send two request for downloading a file and after download some piece data of a file
Way it stop for ever?

1、To support resume,Download a file from server(the Server has't "keep-alive" feature but support resume), I think we must send
two request, the first one get the size of the file and other feature, the second request for download.(the way may be wrong, please figure it )
2、i want to study progrmming CAsyncSocket,derived a class "CHttpAsyncSocket" from CAsyncSocket:

// define download status in HttpAsyncSocket.h
typedef enum { CONNECT_NONE = 0, CONNECT_FILEINFO = 1, RECEIVE_FILEINFO = 2, CONNECT_DOWNLOAD = 3, RECEIVE_DOWNLOAD = 4} DOWNLOADSTATUS;
DOWNLOADSTATUS m_dsCurStatus;

// CHttpAsyncSocket.cpp

//connect server
void CHttpAsyncSocket::BeginDownload()
{
if(Connect(m_strServerIP, m_nServerPort) == SOCKET_ERROR)
{
Close();

m_dsCurStatus = CONNECT_NONE;
}
else
{
m_dsCurStatus = CONNECT_FILEINFO;
}
}

//if connect successfully, then send one of the two request
void CHttpAsyncSocket::OnConnect(int nErrorCode)
{
CAsyncSocket::OnConnect(nErrorCode);
if (nErrorCode)
{
Close();
m_dsCurStatus = CONNECT_NONE;
}
else if(m_dsCurStatus == CONNECT_FILEINFO) //send request that can Get the size of the file in server and may support resume
{
CString strSend;
strSend.Format( "GET %s HTTP/1.1\r\n"
"Host: %s:%d\r\n"
"Accept: */*\r\n"
"Pragma: no-cache\r\n"
"Cache-Control: no-cache\r\n"
"Connection: close\r\n"
"Range: bytes=100-\r\n"
"\r\n",
m_strFileUrl, m_strServerIP, m_nServerPort);

int ret = Send(strSend.GetBuffer(0), strSend.GetLength());
if(ret == SOCKET_ERROR)
{
Close();

m_dsCurStatus = CONNECT_NONE;

}
else
{
m_dsCurStatus = RECEIVE_FILEINFO;
}
}
else if(m_dsCurStatus == CONNECT_DOWNLOAD) //send request for download
{
CString strSend;
strSend.Format( "GET %s HTTP/1.1\r\n"
"Host: %s:%d\r\n"
"Accept: */*\r\n"
"Pragma: no-cache\r\n"
"Cache-Control: no-cache\r\n"
"Connection: close\r\n"
"Range: bytes=%d-%d\r\n"
"\r\n",
m_strFileUrl, m_strServerIP, m_nServerPort, m_dwLocalFileSize, m_dwServerFileSize);
//m_dwLocalFileSize, m_dwServerFileSize are separately the size of local and server

int ret = Send(strSend.GetBuffer(0), strSend.GetLength());

if(ret == SOCKET_ERROR)
{
Close();

m_dsCurStatus = CONNECT_NONE;
}
else
{
m_dsCurStatus = RECEIVE_DOWNLOAD;
m_bAlreadyGetHeader = FALSE; //has decode the header of package
}
}
else
{
ASSERT(FALSE);
}
}

//received data
const int MAX_RECV_BUFFER = 1024;

void CHttpAsyncSocket::OnReceive(int nErrorCode)
{
CAsyncSocket::OnReceive(nErrorCode);

char szReadBuf[MAX_RECV_BUFFER];
ZeroMemory(szReadBuf, MAX_RECV_BUFFER);

if (nErrorCode)
{
Close();
m_dsCurStatus = CONNECT_NONE;
}

if(m_dsCurStatus == RECEIVE_FILEINFO) //get size of file in server , etc
{
m_dwServerFileSize = 0;
BOOL bSupportResume = FALSE;

if(ParseHttpHeader(&m_dwServerFileSize, &bSupportResume) == TRUE) //parse the header of packet
{
Close(); //Is it necessary? -------------
Create(); //create a new socket and connect to server again

if(Connect(m_strServerIP, m_nServerPort) == SOCKET_ERROR)
{
Close();

m_dsCurStatus = CONNECT_NONE;
}
else
{
m_dsCurStatus = CONNECT_DOWNLOAD;
}
}
else
{
Close();

m_dsCurStatus = CONNECT_NONE;
}
}
else if(m_dsCurStatus == RECEIVE_DOWNLOAD)
{
//open local file and receive data
CFile file;
int bOpenSuc = file.Open(m_strLocalFile, CFile::modeCreate | CFile::modeWrite | CFile::modeNoTruncate | CFile::typeBinary | CFile::shareExclusive);

if(bOpenSuc == FALSE)
{
TRACE("Error in file open!\n");
Close();

m_dsCurStatus = CONNECT_NONE;
}
file.SeekToEnd();

int ret = 0, nHeadLength = 0;

if(m_bAlreadyGetHeader == FALSE)
{
//reject the header of the packet in first time
do
{
ret = Receive(szReadBuf, MAX_RECV_BUFFER);
nHeadLength = GetHeadLength(szReadBuf);
}while(ret <= nHeadLength);

if(ret > nHeadLength)
{
file.Write(szReadBuf + nHeadLength, ret - nHeadLength);
}

m_bAlreadyGetHeader = TRUE;
}

while(TRUE)
{
ZeroMemory(szReadBuf,MAX_RECV_BUFFER);

int num = Receive(szReadBuf, MAX_RECV_BUFFER);

if(num == 0 || num == SOCKET_ERROR) //download finish or meet net error
{
if (GetLastError() != WSAEWOULDBLOCK && num == 0)
{
file.Close(); //HERE: thread may come here, and can not continue receive data again when download about 10 - 600 K,
return; //why? maybe use timer?
}

break;
}

file.Write(szReadBuf, num);
}

file.Close();
}
}
else
{
ASSERT(FALSE);
}
}

First, thank you look through my code above!
I study socket just now, many question are "naive", need you direct or give some advice.... thanks again ^_^



C/C++ code fans
GeneralRe: CAsyncSocket with http supported file-resume Pin
valikac4-Sep-03 9:04
valikac4-Sep-03 9:04 
QuestionCMainFrame from CView? Pin
Dominik Reichl3-Sep-03 23:25
Dominik Reichl3-Sep-03 23:25 
AnswerRe: CMainFrame from CView? Pin
Dominik Reichl3-Sep-03 23:28
Dominik Reichl3-Sep-03 23:28 
GeneralRe: CMainFrame from CView? Pin
Anonymous4-Sep-03 0:07
Anonymous4-Sep-03 0:07 
GeneralCombo box Index and Edit Control Pin
Member 3971373-Sep-03 23:17
Member 3971373-Sep-03 23:17 
GeneralRe: Combo box Index and Edit Control Pin
David Crow4-Sep-03 3:02
David Crow4-Sep-03 3:02 
GeneralHelp...win 98 to win XP Pin
fynox3-Sep-03 23:12
fynox3-Sep-03 23:12 
GeneralRe: Help...win 98 to win XP Pin
Magnus Westin3-Sep-03 23:45
Magnus Westin3-Sep-03 23:45 
GeneralProblem with CListCtrl Pin
Ph@ntom3-Sep-03 22:52
Ph@ntom3-Sep-03 22:52 
GeneralStrange Behavior with ::CreateDialogIndirect Pin
Bernhard3-Sep-03 22:20
Bernhard3-Sep-03 22:20 
GeneralRe: Strange Behavior with ::CreateDialogIndirect Pin
Iain Clarke, Warrior Programmer3-Sep-03 22:29
Iain Clarke, Warrior Programmer3-Sep-03 22:29 
GeneralRe: Strange Behavior with ::CreateDialogIndirect Pin
Bernhard3-Sep-03 22:37
Bernhard3-Sep-03 22:37 
GeneralThreads, Dialog based appl Pin
KKR3-Sep-03 21:50
KKR3-Sep-03 21:50 
GeneralRe: Threads, Dialog based appl Pin
VIKASK_773-Sep-03 23:52
VIKASK_773-Sep-03 23:52 
GeneralRe: Threads, Dialog based appl Pin
jhwurmbach4-Sep-03 2:59
jhwurmbach4-Sep-03 2:59 
QuestionHow to get the Handle of a WebCam? Pin
nwillie3-Sep-03 21:43
nwillie3-Sep-03 21:43 
GeneralStupid problem Pin
Rohit  Sinha3-Sep-03 21:17
Rohit  Sinha3-Sep-03 21:17 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.