00001
00002
00003
00004
00005
00006 #include "stdafx.h"
00007 #include "fsArchiveInternetStream.h"
00008 #include "fsInternetDownloader.h"
00009 #include "inetutil.h"
00010 #include "vmsInternetSession.h"
00011
00012 #ifdef _DEBUG
00013 #undef THIS_FILE
00014 static char THIS_FILE[]=__FILE__;
00015 #define new DEBUG_NEW
00016 #endif
00017
00018 using namespace fsArchive;
00019
00020 fsArchiveInternetStream::fsArchiveInternetStream()
00021 {
00022 m_bNeedStop = FALSE;
00023 m_bOpened = FALSE;
00024 m_irLastErr = IR_SUCCESS;
00025 m_cMaxRetries = 1;
00026 }
00027
00028 fsArchiveInternetStream::~fsArchiveInternetStream()
00029 {
00030
00031 }
00032
00033 fsInternetResult fsArchiveInternetStream::Open(fsInternetDownloader *dldr, UINT64 uStartPos)
00034 {
00035 m_dldr = dldr;
00036 m_bNeedStop = FALSE;
00037
00038 for (UINT i = 0; i < m_cMaxRetries; i++)
00039 {
00040 Close ();
00041 m_irLastErr = Open_imp (uStartPos);
00042
00043 if (m_bNeedStop)
00044 {
00045 m_irLastErr = IR_S_FALSE;
00046 break;
00047 }
00048
00049 if (m_irLastErr == IR_SUCCESS)
00050 break;
00051 }
00052
00053 return m_irLastErr;
00054 }
00055
00056 int fsArchiveInternetStream::Read(LPVOID pBuffer, int cBytes)
00057 {
00058 DWORD cRead = 0;
00059 DWORD cToRead;
00060 int c0Reads = 0;
00061
00062 while (cRead < (DWORD)cBytes)
00063 {
00064 if (m_bNeedStop)
00065 return -1;
00066
00067 cToRead = cBytes - cRead;
00068 m_irLastErr = m_file.Read (LPBYTE (pBuffer) + cRead, cToRead, &cToRead);
00069 if (m_irLastErr != IR_SUCCESS)
00070 {
00071 m_dwLastError = ASE_NOMOREDATA;
00072 return -1;
00073 }
00074
00075 if (cToRead)
00076 c0Reads = 0;
00077 else
00078 c0Reads++;
00079
00080 cRead += cToRead;
00081 m_uCurPos += cToRead;
00082
00083 if (c0Reads > 100)
00084 {
00085 m_dwLastError = ASE_NOMOREDATA;
00086 return -1;
00087 }
00088 }
00089
00090 return cBytes;
00091 }
00092
00093 int fsArchiveInternetStream::Write(LPVOID , int )
00094 {
00095 return -1;
00096 }
00097
00098 BOOL fsArchiveInternetStream::Seek(UINT64 uDistance, fsSeekType enType)
00099 {
00100 Close ();
00101
00102 UINT64 posTo;
00103
00104 switch (enType)
00105 {
00106 case ST_CURRENT:
00107 posTo = m_uCurPos + uDistance;
00108 break;
00109
00110 case ST_BEGIN:
00111 posTo = uDistance;
00112 break;
00113
00114 default:
00115 return FALSE;
00116 }
00117
00118 if (IR_SUCCESS != (m_irLastErr = Open (m_dldr, posTo)))
00119 return FALSE;
00120
00121 return TRUE;
00122 }
00123
00124 void fsArchiveInternetStream::Close()
00125 {
00126 m_file.CloseHandle ();
00127 m_bOpened = FALSE;
00128 }
00129
00130 void fsArchiveInternetStream::Stop()
00131 {
00132 m_bNeedStop = TRUE;
00133 Close ();
00134 }
00135
00136 fsInternetResult fsArchiveInternetStream::Open_imp(UINT64 uStartPos)
00137 {
00138 fsInternetResult ir;
00139 fsDownload_NetworkProperties* dnp = m_dldr->DNP ();
00140
00141 if (m_bOpened == FALSE)
00142 {
00143 vmsInternetSession* pSession = new vmsInternetSession;
00144 ir = pSession->Create (dnp->pszAgent, dnp->enAccType, dnp->pszProxyName, dnp->enProtocol);
00145 if (ir != IR_SUCCESS)
00146 {
00147 delete pSession;
00148 return ir;
00149 }
00150
00151 m_dldr->ApplyProxySettings (pSession, dnp);
00152
00153 ir = m_file.Initialize (pSession, TRUE);
00154 if (ir != IR_SUCCESS)
00155 {
00156 delete pSession;
00157 return ir;
00158 }
00159 }
00160
00161 m_dldr->ApplyProperties (&m_file, dnp);
00162 m_file.FtpSetTransferType (FTT_BINARY);
00163
00164 LPCSTR pszHost = m_bOpened ? NULL : dnp->pszServerName;
00165 if (dnp->enProtocol != NP_FTP)
00166 pszHost = dnp->pszServerName;
00167
00168 ir = m_file.Open (fsNPToScheme (dnp->enProtocol), pszHost,
00169 dnp->pszUserName, dnp->pszPassword, dnp->uServerPort,
00170 dnp->pszPathName, uStartPos);
00171
00172 if (m_bNeedStop)
00173 return IR_S_FALSE;
00174
00175 if (ir != IR_SUCCESS)
00176 {
00177 if (ir == IR_NEEDREDIRECT)
00178 {
00179 if (m_dldr->GetNumberOfSections ())
00180 return IR_SERVERUNKERROR;
00181
00182 LPCSTR pszUrlTo = m_file.GetLastError ();
00183
00184 fsURL url;
00185 LPSTR pszUrl = new char [10000];
00186 DWORD dwLen = 10000;
00187
00188 if (url.Crack (pszUrlTo) != IR_SUCCESS)
00189 {
00190 LPSTR pszUrlPath = new char [10000];
00191
00192 if (*pszUrlTo == 0)
00193 strcpy (pszUrlPath, "/");
00194 else if (*pszUrlTo != '/' && *pszUrlTo != '\\')
00195 {
00196 fsPathFromUrlPath (dnp->pszPathName, dnp->enProtocol == NP_FTP, FALSE, pszUrlPath, 10000);
00197
00198 if (pszUrlPath [lstrlen (pszUrlPath)-1] != '\\' &&
00199 pszUrlPath [lstrlen (pszUrlPath)-1] != '/')
00200 lstrcat (pszUrlPath, "\\");
00201
00202 strcat (pszUrlPath, pszUrlTo);
00203 }
00204 else
00205 strcpy (pszUrlPath, pszUrlTo);
00206
00207 url.Create (fsNPToScheme (dnp->enProtocol), dnp->pszServerName, dnp->uServerPort,
00208 dnp->pszUserName, dnp->pszPassword, pszUrlPath, pszUrl, &dwLen);
00209
00210 delete [] pszUrlPath;
00211 }
00212 else
00213 strcpy (pszUrl, pszUrlTo);
00214
00215 LPSTR pszUser = new char [10000], pszPassword = new char [10000];
00216 if (dnp->pszUserName)
00217 strcpy (pszUser, dnp->pszUserName);
00218 else
00219 *pszUser = 0;
00220
00221 if (dnp->pszPassword)
00222 strcpy (pszPassword, dnp->pszPassword);
00223 else
00224 *pszPassword = 0;
00225
00226
00227 ir = fsDNP_ApplyUrl (dnp, pszUrl);
00228
00229 delete [] pszUrl;
00230
00231 if (ir != IR_SUCCESS)
00232 return ir;
00233
00234 if (dnp->pszUserName == NULL || *dnp->pszUserName == 0)
00235 {
00236 SAFE_DELETE_ARRAY (dnp->pszUserName);
00237 dnp->pszUserName = new char [strlen (pszUser) + 1];
00238 strcpy (dnp->pszUserName, pszUser);
00239
00240 SAFE_DELETE_ARRAY (dnp->pszPassword);
00241 dnp->pszPassword = new char [strlen (pszPassword) + 1];
00242 strcpy (dnp->pszPassword, pszPassword);
00243 }
00244
00245 delete [] pszUser; delete [] pszPassword;
00246
00247 if (m_bNeedStop == FALSE)
00248 return Open (m_dldr, uStartPos);
00249 else
00250 return IR_S_FALSE;
00251 }
00252
00253 return ir;
00254 }
00255
00256 m_uCurPos = uStartPos;
00257 m_bOpened = TRUE;
00258 return IR_SUCCESS;
00259 }
00260
00261 fsInternetResult fsArchiveInternetStream::GetLastNetworkErr()
00262 {
00263 return m_irLastErr;
00264 }
00265
00266 void fsArchiveInternetStream::Set_MaxRetriesCount(UINT cMax)
00267 {
00268 m_cMaxRetries = cMax;
00269 }