Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(358)

Side by Side Diff: chrome/browser/chromeos/drive/drive_file_stream_reader.cc

Issue 93883006: Fix failure of reading zero-byte files on Drive via StreamReader. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 7 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright 2013 The Chromium Authors. All rights reserved. 1 // Copyright 2013 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 "chrome/browser/chromeos/drive/drive_file_stream_reader.h" 5 #include "chrome/browser/chromeos/drive/drive_file_stream_reader.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <cstring> 8 #include <cstring>
9 9
10 #include "base/callback_helpers.h" 10 #include "base/callback_helpers.h"
(...skipping 321 matching lines...) Expand 10 before | Expand all | Expand 10 after
332 int DriveFileStreamReader::Read(net::IOBuffer* buffer, int buffer_length, 332 int DriveFileStreamReader::Read(net::IOBuffer* buffer, int buffer_length,
333 const net::CompletionCallback& callback) { 333 const net::CompletionCallback& callback) {
334 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); 334 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
335 DCHECK(reader_proxy_); 335 DCHECK(reader_proxy_);
336 DCHECK(buffer); 336 DCHECK(buffer);
337 DCHECK(!callback.is_null()); 337 DCHECK(!callback.is_null());
338 return reader_proxy_->Read(buffer, buffer_length, callback); 338 return reader_proxy_->Read(buffer, buffer_length, callback);
339 } 339 }
340 340
341 void DriveFileStreamReader::InitializeAfterGetFileContentInitialized( 341 void DriveFileStreamReader::InitializeAfterGetFileContentInitialized(
342 const net::HttpByteRange& in_byte_range, 342 const net::HttpByteRange& byte_range,
343 const InitializeCompletionCallback& callback, 343 const InitializeCompletionCallback& callback,
344 FileError error, 344 FileError error,
345 scoped_ptr<ResourceEntry> entry, 345 scoped_ptr<ResourceEntry> entry,
346 const base::FilePath& local_cache_file_path, 346 const base::FilePath& local_cache_file_path,
347 const base::Closure& ui_cancel_download_closure) { 347 const base::Closure& ui_cancel_download_closure) {
348 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); 348 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
349 349
350 if (error != FILE_ERROR_OK) { 350 if (error != FILE_ERROR_OK) {
351 callback.Run(FileErrorToNetError(error), scoped_ptr<ResourceEntry>()); 351 callback.Run(FileErrorToNetError(error), scoped_ptr<ResourceEntry>());
352 return; 352 return;
353 } 353 }
354 DCHECK(entry); 354 DCHECK(entry);
355 355
356 net::HttpByteRange byte_range = in_byte_range; 356 // Note: both boundary of |byte_range| are inclusive.
357 if (!byte_range.ComputeBounds(entry->file_info().size())) { 357 // Convert it to half-exclusive range with missing bounds filled.
hashimoto 2013/12/19 08:53:40 Is it OK to ignore suffix byte range?
kinaba 2013/12/20 03:57:55 Good catch. Recovered the support for suffix range
358 const int64 range_start = byte_range.HasFirstBytePosition() ?
359 byte_range.first_byte_position() : 0;
360 const int64 range_end = byte_range.HasLastBytePosition() ?
361 byte_range.last_byte_position() + 1 : entry->file_info().size();
362
363 if (range_start > range_end || entry->file_info().size() < range_end) {
358 // If |byte_range| is invalid (e.g. out of bounds), return with an error. 364 // If |byte_range| is invalid (e.g. out of bounds), return with an error.
359 // At the same time, we cancel the in-flight downloading operation if 365 // At the same time, we cancel the in-flight downloading operation if
360 // needed and and invalidate weak pointers so that we won't 366 // needed and and invalidate weak pointers so that we won't
361 // receive unwanted callbacks. 367 // receive unwanted callbacks.
362 if (!ui_cancel_download_closure.is_null()) 368 if (!ui_cancel_download_closure.is_null())
363 RunTaskOnUIThread(ui_cancel_download_closure); 369 RunTaskOnUIThread(ui_cancel_download_closure);
364 weak_ptr_factory_.InvalidateWeakPtrs(); 370 weak_ptr_factory_.InvalidateWeakPtrs();
365 callback.Run( 371 callback.Run(
366 net::ERR_REQUEST_RANGE_NOT_SATISFIABLE, scoped_ptr<ResourceEntry>()); 372 net::ERR_REQUEST_RANGE_NOT_SATISFIABLE, scoped_ptr<ResourceEntry>());
367 return; 373 return;
368 } 374 }
369 375
370 // Note: both boundary of |byte_range| are inclusive.
371 int64 range_length =
372 byte_range.last_byte_position() - byte_range.first_byte_position() + 1;
373 DCHECK_GE(range_length, 0);
374
375 if (local_cache_file_path.empty()) { 376 if (local_cache_file_path.empty()) {
376 // The file is not cached, and being downloaded. 377 // The file is not cached, and being downloaded.
377 DCHECK(!ui_cancel_download_closure.is_null()); 378 DCHECK(!ui_cancel_download_closure.is_null());
378 reader_proxy_.reset( 379 reader_proxy_.reset(
379 new internal::NetworkReaderProxy( 380 new internal::NetworkReaderProxy(
380 byte_range.first_byte_position(), range_length, 381 range_start, range_end - range_start,
381 base::Bind(&RunTaskOnUIThread, ui_cancel_download_closure))); 382 base::Bind(&RunTaskOnUIThread, ui_cancel_download_closure)));
382 callback.Run(net::OK, entry.Pass()); 383 callback.Run(net::OK, entry.Pass());
383 return; 384 return;
384 } 385 }
385 386
386 // Otherwise, open the stream for file. 387 // Otherwise, open the stream for file.
387 scoped_ptr<util::LocalFileReader> file_reader( 388 scoped_ptr<util::LocalFileReader> file_reader(
388 new util::LocalFileReader(file_task_runner_.get())); 389 new util::LocalFileReader(file_task_runner_.get()));
389 util::LocalFileReader* file_reader_ptr = file_reader.get(); 390 util::LocalFileReader* file_reader_ptr = file_reader.get();
390 file_reader_ptr->Open( 391 file_reader_ptr->Open(
391 local_cache_file_path, 392 local_cache_file_path,
392 byte_range.first_byte_position(), 393 range_start,
393 base::Bind( 394 base::Bind(
394 &DriveFileStreamReader::InitializeAfterLocalFileOpen, 395 &DriveFileStreamReader::InitializeAfterLocalFileOpen,
395 weak_ptr_factory_.GetWeakPtr(), 396 weak_ptr_factory_.GetWeakPtr(),
396 range_length, 397 range_end - range_start,
397 callback, 398 callback,
398 base::Passed(&entry), 399 base::Passed(&entry),
399 base::Passed(&file_reader))); 400 base::Passed(&file_reader)));
400 } 401 }
401 402
402 void DriveFileStreamReader::InitializeAfterLocalFileOpen( 403 void DriveFileStreamReader::InitializeAfterLocalFileOpen(
403 int64 length, 404 int64 length,
404 const InitializeCompletionCallback& callback, 405 const InitializeCompletionCallback& callback,
405 scoped_ptr<ResourceEntry> entry, 406 scoped_ptr<ResourceEntry> entry,
406 scoped_ptr<util::LocalFileReader> file_reader, 407 scoped_ptr<util::LocalFileReader> file_reader,
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
442 // Note: due to the same reason, LocalReaderProxy::OnCompleted may 443 // Note: due to the same reason, LocalReaderProxy::OnCompleted may
443 // or may not be called. This is timing issue, and it is difficult to avoid 444 // or may not be called. This is timing issue, and it is difficult to avoid
444 // unfortunately. 445 // unfortunately.
445 if (error != FILE_ERROR_OK) { 446 if (error != FILE_ERROR_OK) {
446 callback.Run(FileErrorToNetError(error), scoped_ptr<ResourceEntry>()); 447 callback.Run(FileErrorToNetError(error), scoped_ptr<ResourceEntry>());
447 } 448 }
448 } 449 }
449 } 450 }
450 451
451 } // namespace drive 452 } // namespace drive
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698