| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "net/url_request/url_request_ftp_job.h" | 5 #include "net/url_request/url_request_ftp_job.h" |
| 6 | 6 |
| 7 #include "base/compiler_specific.h" | 7 #include "base/compiler_specific.h" |
| 8 #include "base/message_loop/message_loop.h" | 8 #include "base/message_loop/message_loop.h" |
| 9 #include "base/strings/utf_string_conversions.h" | 9 #include "base/strings/utf_string_conversions.h" |
| 10 #include "net/base/auth.h" | 10 #include "net/base/auth.h" |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 54 | 54 |
| 55 bool URLRequestFtpJob::GetMimeType(std::string* mime_type) const { | 55 bool URLRequestFtpJob::GetMimeType(std::string* mime_type) const { |
| 56 if (proxy_info_.is_direct()) { | 56 if (proxy_info_.is_direct()) { |
| 57 if (ftp_transaction_->GetResponseInfo()->is_directory_listing) { | 57 if (ftp_transaction_->GetResponseInfo()->is_directory_listing) { |
| 58 *mime_type = "text/vnd.chromium.ftp-dir"; | 58 *mime_type = "text/vnd.chromium.ftp-dir"; |
| 59 return true; | 59 return true; |
| 60 } | 60 } |
| 61 } else { | 61 } else { |
| 62 // No special handling of MIME type is needed. As opposed to direct FTP | 62 // No special handling of MIME type is needed. As opposed to direct FTP |
| 63 // transaction, we do not get a raw directory listing to parse. | 63 // transaction, we do not get a raw directory listing to parse. |
| 64 return http_transaction_->GetResponseInfo()-> | 64 return http_transaction_->GetResponseInfo()->headers->GetMimeType( |
| 65 headers->GetMimeType(mime_type); | 65 mime_type); |
| 66 } | 66 } |
| 67 return false; | 67 return false; |
| 68 } | 68 } |
| 69 | 69 |
| 70 void URLRequestFtpJob::GetResponseInfo(HttpResponseInfo* info) { | 70 void URLRequestFtpJob::GetResponseInfo(HttpResponseInfo* info) { |
| 71 if (http_response_info_) | 71 if (http_response_info_) |
| 72 *info = *http_response_info_; | 72 *info = *http_response_info_; |
| 73 } | 73 } |
| 74 | 74 |
| 75 HostPortPair URLRequestFtpJob::GetSocketAddress() const { | 75 HostPortPair URLRequestFtpJob::GetSocketAddress() const { |
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 125 | 125 |
| 126 void URLRequestFtpJob::OnResolveProxyComplete(int result) { | 126 void URLRequestFtpJob::OnResolveProxyComplete(int result) { |
| 127 pac_request_ = NULL; | 127 pac_request_ = NULL; |
| 128 | 128 |
| 129 if (result != OK) { | 129 if (result != OK) { |
| 130 OnStartCompletedAsync(result); | 130 OnStartCompletedAsync(result); |
| 131 return; | 131 return; |
| 132 } | 132 } |
| 133 | 133 |
| 134 // Remove unsupported proxies from the list. | 134 // Remove unsupported proxies from the list. |
| 135 proxy_info_.RemoveProxiesWithoutScheme( | 135 proxy_info_.RemoveProxiesWithoutScheme(ProxyServer::SCHEME_DIRECT | |
| 136 ProxyServer::SCHEME_DIRECT | | 136 ProxyServer::SCHEME_HTTP | |
| 137 ProxyServer::SCHEME_HTTP | | 137 ProxyServer::SCHEME_HTTPS); |
| 138 ProxyServer::SCHEME_HTTPS); | |
| 139 | 138 |
| 140 // TODO(phajdan.jr): Implement proxy fallback, http://crbug.com/171495 . | 139 // TODO(phajdan.jr): Implement proxy fallback, http://crbug.com/171495 . |
| 141 if (proxy_info_.is_direct()) | 140 if (proxy_info_.is_direct()) |
| 142 StartFtpTransaction(); | 141 StartFtpTransaction(); |
| 143 else if (proxy_info_.is_http() || proxy_info_.is_https()) | 142 else if (proxy_info_.is_http() || proxy_info_.is_https()) |
| 144 StartHttpTransaction(); | 143 StartHttpTransaction(); |
| 145 else | 144 else |
| 146 OnStartCompletedAsync(ERR_NO_SUPPORTED_PROXIES); | 145 OnStartCompletedAsync(ERR_NO_SUPPORTED_PROXIES); |
| 147 } | 146 } |
| 148 | 147 |
| 149 void URLRequestFtpJob::StartFtpTransaction() { | 148 void URLRequestFtpJob::StartFtpTransaction() { |
| 150 // Create a transaction. | 149 // Create a transaction. |
| 151 DCHECK(!ftp_transaction_); | 150 DCHECK(!ftp_transaction_); |
| 152 | 151 |
| 153 ftp_request_info_.url = request_->url(); | 152 ftp_request_info_.url = request_->url(); |
| 154 ftp_transaction_.reset(ftp_transaction_factory_->CreateTransaction()); | 153 ftp_transaction_.reset(ftp_transaction_factory_->CreateTransaction()); |
| 155 | 154 |
| 156 // No matter what, we want to report our status as IO pending since we will | 155 // No matter what, we want to report our status as IO pending since we will |
| 157 // be notifying our consumer asynchronously via OnStartCompleted. | 156 // be notifying our consumer asynchronously via OnStartCompleted. |
| 158 SetStatus(URLRequestStatus(URLRequestStatus::IO_PENDING, 0)); | 157 SetStatus(URLRequestStatus(URLRequestStatus::IO_PENDING, 0)); |
| 159 int rv; | 158 int rv; |
| 160 if (ftp_transaction_) { | 159 if (ftp_transaction_) { |
| 161 rv = ftp_transaction_->Start( | 160 rv = ftp_transaction_->Start( |
| 162 &ftp_request_info_, | 161 &ftp_request_info_, |
| 163 base::Bind(&URLRequestFtpJob::OnStartCompleted, | 162 base::Bind(&URLRequestFtpJob::OnStartCompleted, base::Unretained(this)), |
| 164 base::Unretained(this)), | |
| 165 request_->net_log()); | 163 request_->net_log()); |
| 166 if (rv == ERR_IO_PENDING) | 164 if (rv == ERR_IO_PENDING) |
| 167 return; | 165 return; |
| 168 } else { | 166 } else { |
| 169 rv = ERR_FAILED; | 167 rv = ERR_FAILED; |
| 170 } | 168 } |
| 171 // The transaction started synchronously, but we need to notify the | 169 // The transaction started synchronously, but we need to notify the |
| 172 // URLRequest delegate via the message loop. | 170 // URLRequest delegate via the message loop. |
| 173 OnStartCompletedAsync(rv); | 171 OnStartCompletedAsync(rv); |
| 174 } | 172 } |
| 175 | 173 |
| 176 void URLRequestFtpJob::StartHttpTransaction() { | 174 void URLRequestFtpJob::StartHttpTransaction() { |
| 177 // Create a transaction. | 175 // Create a transaction. |
| 178 DCHECK(!http_transaction_); | 176 DCHECK(!http_transaction_); |
| 179 | 177 |
| 180 // Do not cache FTP responses sent through HTTP proxy. | 178 // Do not cache FTP responses sent through HTTP proxy. |
| 181 request_->SetLoadFlags(request_->load_flags() | | 179 request_->SetLoadFlags(request_->load_flags() | LOAD_DISABLE_CACHE | |
| 182 LOAD_DISABLE_CACHE | | 180 LOAD_DO_NOT_SAVE_COOKIES | LOAD_DO_NOT_SEND_COOKIES); |
| 183 LOAD_DO_NOT_SAVE_COOKIES | | |
| 184 LOAD_DO_NOT_SEND_COOKIES); | |
| 185 | 181 |
| 186 http_request_info_.url = request_->url(); | 182 http_request_info_.url = request_->url(); |
| 187 http_request_info_.method = request_->method(); | 183 http_request_info_.method = request_->method(); |
| 188 http_request_info_.load_flags = request_->load_flags(); | 184 http_request_info_.load_flags = request_->load_flags(); |
| 189 | 185 |
| 190 int rv = request_->context()->http_transaction_factory()->CreateTransaction( | 186 int rv = request_->context()->http_transaction_factory()->CreateTransaction( |
| 191 priority_, &http_transaction_); | 187 priority_, &http_transaction_); |
| 192 if (rv == OK) { | 188 if (rv == OK) { |
| 193 rv = http_transaction_->Start( | 189 rv = http_transaction_->Start( |
| 194 &http_request_info_, | 190 &http_request_info_, |
| 195 base::Bind(&URLRequestFtpJob::OnStartCompleted, | 191 base::Bind(&URLRequestFtpJob::OnStartCompleted, base::Unretained(this)), |
| 196 base::Unretained(this)), | |
| 197 request_->net_log()); | 192 request_->net_log()); |
| 198 if (rv == ERR_IO_PENDING) | 193 if (rv == ERR_IO_PENDING) |
| 199 return; | 194 return; |
| 200 } | 195 } |
| 201 // The transaction started synchronously, but we need to notify the | 196 // The transaction started synchronously, but we need to notify the |
| 202 // URLRequest delegate via the message loop. | 197 // URLRequest delegate via the message loop. |
| 203 OnStartCompletedAsync(rv); | 198 OnStartCompletedAsync(rv); |
| 204 } | 199 } |
| 205 | 200 |
| 206 void URLRequestFtpJob::OnStartCompleted(int result) { | 201 void URLRequestFtpJob::OnStartCompleted(int result) { |
| (...skipping 25 matching lines...) Expand all Loading... |
| 232 return; | 227 return; |
| 233 } else { | 228 } else { |
| 234 NotifyDone(URLRequestStatus(URLRequestStatus::FAILED, result)); | 229 NotifyDone(URLRequestStatus(URLRequestStatus::FAILED, result)); |
| 235 } | 230 } |
| 236 } | 231 } |
| 237 | 232 |
| 238 void URLRequestFtpJob::OnStartCompletedAsync(int result) { | 233 void URLRequestFtpJob::OnStartCompletedAsync(int result) { |
| 239 base::MessageLoop::current()->PostTask( | 234 base::MessageLoop::current()->PostTask( |
| 240 FROM_HERE, | 235 FROM_HERE, |
| 241 base::Bind(&URLRequestFtpJob::OnStartCompleted, | 236 base::Bind(&URLRequestFtpJob::OnStartCompleted, |
| 242 weak_factory_.GetWeakPtr(), result)); | 237 weak_factory_.GetWeakPtr(), |
| 238 result)); |
| 243 } | 239 } |
| 244 | 240 |
| 245 void URLRequestFtpJob::OnReadCompleted(int result) { | 241 void URLRequestFtpJob::OnReadCompleted(int result) { |
| 246 read_in_progress_ = false; | 242 read_in_progress_ = false; |
| 247 if (result == 0) { | 243 if (result == 0) { |
| 248 NotifyDone(URLRequestStatus()); | 244 NotifyDone(URLRequestStatus()); |
| 249 } else if (result < 0) { | 245 } else if (result < 0) { |
| 250 NotifyDone(URLRequestStatus(URLRequestStatus::FAILED, result)); | 246 NotifyDone(URLRequestStatus(URLRequestStatus::FAILED, result)); |
| 251 } else { | 247 } else { |
| 252 // Clear the IO_PENDING status | 248 // Clear the IO_PENDING status |
| (...skipping 22 matching lines...) Expand all Loading... |
| 275 base::Unretained(this))); | 271 base::Unretained(this))); |
| 276 } | 272 } |
| 277 if (rv == ERR_IO_PENDING) | 273 if (rv == ERR_IO_PENDING) |
| 278 return; | 274 return; |
| 279 | 275 |
| 280 OnStartCompletedAsync(rv); | 276 OnStartCompletedAsync(rv); |
| 281 } | 277 } |
| 282 | 278 |
| 283 LoadState URLRequestFtpJob::GetLoadState() const { | 279 LoadState URLRequestFtpJob::GetLoadState() const { |
| 284 if (proxy_info_.is_direct()) { | 280 if (proxy_info_.is_direct()) { |
| 285 return ftp_transaction_ ? | 281 return ftp_transaction_ ? ftp_transaction_->GetLoadState() |
| 286 ftp_transaction_->GetLoadState() : LOAD_STATE_IDLE; | 282 : LOAD_STATE_IDLE; |
| 287 } else { | 283 } else { |
| 288 return http_transaction_ ? | 284 return http_transaction_ ? http_transaction_->GetLoadState() |
| 289 http_transaction_->GetLoadState() : LOAD_STATE_IDLE; | 285 : LOAD_STATE_IDLE; |
| 290 } | 286 } |
| 291 } | 287 } |
| 292 | 288 |
| 293 bool URLRequestFtpJob::NeedsAuth() { | 289 bool URLRequestFtpJob::NeedsAuth() { |
| 294 return auth_data_.get() && auth_data_->state == AUTH_STATE_NEED_AUTH; | 290 return auth_data_.get() && auth_data_->state == AUTH_STATE_NEED_AUTH; |
| 295 } | 291 } |
| 296 | 292 |
| 297 void URLRequestFtpJob::GetAuthChallengeInfo( | 293 void URLRequestFtpJob::GetAuthChallengeInfo( |
| 298 scoped_refptr<AuthChallengeInfo>* result) { | 294 scoped_refptr<AuthChallengeInfo>* result) { |
| 299 DCHECK(NeedsAuth()); | 295 DCHECK(NeedsAuth()); |
| (...skipping 13 matching lines...) Expand all Loading... |
| 313 } | 309 } |
| 314 | 310 |
| 315 void URLRequestFtpJob::SetAuth(const AuthCredentials& credentials) { | 311 void URLRequestFtpJob::SetAuth(const AuthCredentials& credentials) { |
| 316 DCHECK(ftp_transaction_ || http_transaction_); | 312 DCHECK(ftp_transaction_ || http_transaction_); |
| 317 DCHECK(NeedsAuth()); | 313 DCHECK(NeedsAuth()); |
| 318 | 314 |
| 319 auth_data_->state = AUTH_STATE_HAVE_AUTH; | 315 auth_data_->state = AUTH_STATE_HAVE_AUTH; |
| 320 auth_data_->credentials = credentials; | 316 auth_data_->credentials = credentials; |
| 321 | 317 |
| 322 if (ftp_transaction_) { | 318 if (ftp_transaction_) { |
| 323 ftp_auth_cache_->Add(request_->url().GetOrigin(), | 319 ftp_auth_cache_->Add(request_->url().GetOrigin(), auth_data_->credentials); |
| 324 auth_data_->credentials); | |
| 325 } | 320 } |
| 326 | 321 |
| 327 RestartTransactionWithAuth(); | 322 RestartTransactionWithAuth(); |
| 328 } | 323 } |
| 329 | 324 |
| 330 void URLRequestFtpJob::CancelAuth() { | 325 void URLRequestFtpJob::CancelAuth() { |
| 331 DCHECK(ftp_transaction_ || http_transaction_); | 326 DCHECK(ftp_transaction_ || http_transaction_); |
| 332 DCHECK(NeedsAuth()); | 327 DCHECK(NeedsAuth()); |
| 333 | 328 |
| 334 auth_data_->state = AUTH_STATE_CANCELED; | 329 auth_data_->state = AUTH_STATE_CANCELED; |
| 335 | 330 |
| 336 // Once the auth is cancelled, we proceed with the request as though | 331 // Once the auth is cancelled, we proceed with the request as though |
| 337 // there were no auth. Schedule this for later so that we don't cause | 332 // there were no auth. Schedule this for later so that we don't cause |
| 338 // any recursing into the caller as a result of this call. | 333 // any recursing into the caller as a result of this call. |
| 339 OnStartCompletedAsync(OK); | 334 OnStartCompletedAsync(OK); |
| 340 } | 335 } |
| 341 | 336 |
| 342 UploadProgress URLRequestFtpJob::GetUploadProgress() const { | 337 UploadProgress URLRequestFtpJob::GetUploadProgress() const { |
| 343 return UploadProgress(); | 338 return UploadProgress(); |
| 344 } | 339 } |
| 345 | 340 |
| 346 bool URLRequestFtpJob::ReadRawData(IOBuffer* buf, | 341 bool URLRequestFtpJob::ReadRawData(IOBuffer* buf, |
| 347 int buf_size, | 342 int buf_size, |
| 348 int *bytes_read) { | 343 int* bytes_read) { |
| 349 DCHECK_NE(buf_size, 0); | 344 DCHECK_NE(buf_size, 0); |
| 350 DCHECK(bytes_read); | 345 DCHECK(bytes_read); |
| 351 DCHECK(!read_in_progress_); | 346 DCHECK(!read_in_progress_); |
| 352 | 347 |
| 353 int rv; | 348 int rv; |
| 354 if (proxy_info_.is_direct()) { | 349 if (proxy_info_.is_direct()) { |
| 355 rv = ftp_transaction_->Read(buf, buf_size, | 350 rv = ftp_transaction_->Read( |
| 356 base::Bind(&URLRequestFtpJob::OnReadCompleted, | 351 buf, |
| 357 base::Unretained(this))); | 352 buf_size, |
| 353 base::Bind(&URLRequestFtpJob::OnReadCompleted, base::Unretained(this))); |
| 358 } else { | 354 } else { |
| 359 rv = http_transaction_->Read(buf, buf_size, | 355 rv = http_transaction_->Read( |
| 360 base::Bind(&URLRequestFtpJob::OnReadCompleted, | 356 buf, |
| 361 base::Unretained(this))); | 357 buf_size, |
| 358 base::Bind(&URLRequestFtpJob::OnReadCompleted, base::Unretained(this))); |
| 362 } | 359 } |
| 363 | 360 |
| 364 if (rv >= 0) { | 361 if (rv >= 0) { |
| 365 *bytes_read = rv; | 362 *bytes_read = rv; |
| 366 return true; | 363 return true; |
| 367 } | 364 } |
| 368 | 365 |
| 369 if (rv == ERR_IO_PENDING) { | 366 if (rv == ERR_IO_PENDING) { |
| 370 read_in_progress_ = true; | 367 read_in_progress_ = true; |
| 371 SetStatus(URLRequestStatus(URLRequestStatus::IO_PENDING, 0)); | 368 SetStatus(URLRequestStatus(URLRequestStatus::IO_PENDING, 0)); |
| (...skipping 25 matching lines...) Expand all Loading... |
| 397 if (cached_auth) { | 394 if (cached_auth) { |
| 398 // Retry using cached auth data. | 395 // Retry using cached auth data. |
| 399 SetAuth(cached_auth->credentials); | 396 SetAuth(cached_auth->credentials); |
| 400 } else { | 397 } else { |
| 401 // Prompt for a username/password. | 398 // Prompt for a username/password. |
| 402 NotifyHeadersComplete(); | 399 NotifyHeadersComplete(); |
| 403 } | 400 } |
| 404 } | 401 } |
| 405 | 402 |
| 406 } // namespace net | 403 } // namespace net |
| OLD | NEW |