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

Side by Side Diff: net/base/file_stream_posix.cc

Issue 9288084: Added Net logging to FileStream. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Fixed copyright issue. Created 8 years, 10 months 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
« no previous file with comments | « net/base/file_stream_net_log_parameters.cc ('k') | net/base/file_stream_unittest.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2011 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 // For 64-bit file access (off_t = off64_t, lseek64, etc). 5 // For 64-bit file access (off_t = off64_t, lseek64, etc).
6 #define _FILE_OFFSET_BITS 64 6 #define _FILE_OFFSET_BITS 64
7 7
8 #include "net/base/file_stream.h" 8 #include "net/base/file_stream.h"
9 9
10 #include <sys/types.h> 10 #include <sys/types.h>
11 #include <sys/stat.h> 11 #include <sys/stat.h>
12 #include <fcntl.h> 12 #include <fcntl.h>
13 #include <unistd.h> 13 #include <unistd.h>
14 #include <errno.h> 14 #include <errno.h>
15 15
16 #include "base/basictypes.h" 16 #include "base/basictypes.h"
17 #include "base/bind.h" 17 #include "base/bind.h"
18 #include "base/bind_helpers.h" 18 #include "base/bind_helpers.h"
19 #include "base/callback.h" 19 #include "base/callback.h"
20 #include "base/eintr_wrapper.h" 20 #include "base/eintr_wrapper.h"
21 #include "base/file_path.h" 21 #include "base/file_path.h"
22 #include "base/logging.h" 22 #include "base/logging.h"
23 #include "base/message_loop.h" 23 #include "base/message_loop.h"
24 #include "base/metrics/histogram.h" 24 #include "base/metrics/histogram.h"
25 #include "base/string_util.h" 25 #include "base/string_util.h"
26 #include "base/threading/thread_restrictions.h" 26 #include "base/threading/thread_restrictions.h"
27 #include "base/threading/worker_pool.h" 27 #include "base/threading/worker_pool.h"
28 #include "base/synchronization/waitable_event.h" 28 #include "base/synchronization/waitable_event.h"
29 #include "net/base/file_stream_metrics.h" 29 #include "net/base/file_stream_metrics.h"
30 #include "net/base/file_stream_net_log_parameters.h"
30 #include "net/base/net_errors.h" 31 #include "net/base/net_errors.h"
31 32
32 #if defined(OS_ANDROID) 33 #if defined(OS_ANDROID)
33 // Android's bionic libc only supports the LFS transitional API. 34 // Android's bionic libc only supports the LFS transitional API.
34 #define off_t off64_t 35 #define off_t off64_t
35 #define lseek lseek64 36 #define lseek lseek64
36 #define stat stat64 37 #define stat stat64
37 #define fstat fstat64 38 #define fstat fstat64
38 #endif 39 #endif
39 40
40 namespace net { 41 namespace net {
41 42
42 // We cast back and forth, so make sure it's the size we're expecting. 43 // We cast back and forth, so make sure it's the size we're expecting.
43 COMPILE_ASSERT(sizeof(int64) == sizeof(off_t), off_t_64_bit); 44 COMPILE_ASSERT(sizeof(int64) == sizeof(off_t), off_t_64_bit);
44 45
45 // Make sure our Whence mappings match the system headers. 46 // Make sure our Whence mappings match the system headers.
46 COMPILE_ASSERT(FROM_BEGIN == SEEK_SET && 47 COMPILE_ASSERT(FROM_BEGIN == SEEK_SET &&
47 FROM_CURRENT == SEEK_CUR && 48 FROM_CURRENT == SEEK_CUR &&
48 FROM_END == SEEK_END, whence_matches_system); 49 FROM_END == SEEK_END, whence_matches_system);
49 50
50 namespace { 51 namespace {
51 52
52 int RecordAndMapError(int error, FileErrorSource source, bool record_uma) { 53 int RecordAndMapError(int error,
54 FileErrorSource source,
55 bool record_uma,
56 const net::BoundNetLog& bound_net_log) {
57 net::Error net_error = MapSystemError(error);
58
59 bound_net_log.AddEvent(
60 net::NetLog::TYPE_FILE_STREAM_ERROR,
61 make_scoped_refptr(
62 new FileStreamErrorParameters(GetFileErrorSourceName(source),
63 error,
64 net_error)));
65
53 RecordFileError(error, source, record_uma); 66 RecordFileError(error, source, record_uma);
54 return MapSystemError(error); 67
68 return net_error;
55 } 69 }
56 70
57 // ReadFile() is a simple wrapper around read() that handles EINTR signals and 71 // ReadFile() is a simple wrapper around read() that handles EINTR signals and
58 // calls MapSystemError() to map errno to net error codes. 72 // calls MapSystemError() to map errno to net error codes.
59 int ReadFile(base::PlatformFile file, char* buf, int buf_len, bool record_uma) { 73 int ReadFile(base::PlatformFile file,
74 char* buf,
75 int buf_len,
76 bool record_uma,
77 const net::BoundNetLog& bound_net_log) {
60 base::ThreadRestrictions::AssertIOAllowed(); 78 base::ThreadRestrictions::AssertIOAllowed();
61 // read(..., 0) returns 0 to indicate end-of-file. 79 // read(..., 0) returns 0 to indicate end-of-file.
62 80
63 // Loop in the case of getting interrupted by a signal. 81 // Loop in the case of getting interrupted by a signal.
64 ssize_t res = HANDLE_EINTR(read(file, buf, static_cast<size_t>(buf_len))); 82 ssize_t res = HANDLE_EINTR(read(file, buf, static_cast<size_t>(buf_len)));
65 if (res == static_cast<ssize_t>(-1)) 83 if (res == static_cast<ssize_t>(-1))
66 RecordAndMapError(errno, FILE_ERROR_SOURCE_READ, record_uma); 84 RecordAndMapError(errno, FILE_ERROR_SOURCE_READ, record_uma, bound_net_log);
67 return static_cast<int>(res); 85 return static_cast<int>(res);
68 } 86 }
69 87
70 void ReadFileTask(base::PlatformFile file, 88 void ReadFileTask(base::PlatformFile file,
71 char* buf, 89 char* buf,
72 int buf_len, 90 int buf_len,
73 bool record_uma, 91 bool record_uma,
92 const net::BoundNetLog& bound_net_log,
74 const CompletionCallback& callback) { 93 const CompletionCallback& callback) {
75 callback.Run(ReadFile(file, buf, buf_len, record_uma)); 94 callback.Run(ReadFile(file, buf, buf_len, record_uma, bound_net_log));
76 } 95 }
77 96
78 // WriteFile() is a simple wrapper around write() that handles EINTR signals and 97 // WriteFile() is a simple wrapper around write() that handles EINTR signals and
79 // calls MapSystemError() to map errno to net error codes. It tries to write to 98 // calls MapSystemError() to map errno to net error codes. It tries to write to
80 // completion. 99 // completion.
81 int WriteFile(base::PlatformFile file, const char* buf, int buf_len, 100 int WriteFile(base::PlatformFile file,
82 bool record_uma) { 101 const char* buf,
102 int buf_len,
103 bool record_uma,
104 const net::BoundNetLog& bound_net_log) {
83 base::ThreadRestrictions::AssertIOAllowed(); 105 base::ThreadRestrictions::AssertIOAllowed();
84 ssize_t res = HANDLE_EINTR(write(file, buf, buf_len)); 106 ssize_t res = HANDLE_EINTR(write(file, buf, buf_len));
85 if (res == -1) 107 if (res == -1) {
86 RecordAndMapError(errno, FILE_ERROR_SOURCE_WRITE, record_uma); 108 RecordAndMapError(errno, FILE_ERROR_SOURCE_WRITE, record_uma,
109 bound_net_log);
110 }
87 return res; 111 return res;
88 } 112 }
89 113
90 void WriteFileTask(base::PlatformFile file, 114 void WriteFileTask(base::PlatformFile file,
91 const char* buf, 115 const char* buf,
92 int buf_len, bool record_uma, 116 int buf_len,
117 bool record_uma,
118 const net::BoundNetLog& bound_net_log,
93 const CompletionCallback& callback) { 119 const CompletionCallback& callback) {
94 callback.Run(WriteFile(file, buf, buf_len, record_uma)); 120 callback.Run(WriteFile(file, buf, buf_len, record_uma, bound_net_log));
95 } 121 }
96 122
97 // FlushFile() is a simple wrapper around fsync() that handles EINTR signals and 123 // FlushFile() is a simple wrapper around fsync() that handles EINTR signals and
98 // calls MapSystemError() to map errno to net error codes. It tries to flush to 124 // calls MapSystemError() to map errno to net error codes. It tries to flush to
99 // completion. 125 // completion.
100 int FlushFile(base::PlatformFile file, bool record_uma) { 126 int FlushFile(base::PlatformFile file,
127 bool record_uma,
128 const net::BoundNetLog& bound_net_log) {
101 base::ThreadRestrictions::AssertIOAllowed(); 129 base::ThreadRestrictions::AssertIOAllowed();
102 ssize_t res = HANDLE_EINTR(fsync(file)); 130 ssize_t res = HANDLE_EINTR(fsync(file));
103 if (res == -1) 131 if (res == -1) {
104 RecordAndMapError(errno, FILE_ERROR_SOURCE_FLUSH, record_uma); 132 RecordAndMapError(errno, FILE_ERROR_SOURCE_FLUSH, record_uma,
133 bound_net_log);
134 }
105 return res; 135 return res;
106 } 136 }
107 137
108 } // namespace 138 } // namespace
109 139
110 // Cancelable wrapper around a Closure. 140 // Cancelable wrapper around a Closure.
111 class CancelableCallback { 141 class CancelableCallback {
112 public: 142 public:
113 explicit CancelableCallback(const base::Closure& callback) 143 explicit CancelableCallback(const base::Closure& callback)
114 : canceled_(false), 144 : canceled_(false),
(...skipping 16 matching lines...) Expand all
131 // FileStream::AsyncContext ---------------------------------------------- 161 // FileStream::AsyncContext ----------------------------------------------
132 162
133 class FileStream::AsyncContext { 163 class FileStream::AsyncContext {
134 public: 164 public:
135 AsyncContext(); 165 AsyncContext();
136 ~AsyncContext(); 166 ~AsyncContext();
137 167
138 // These methods post synchronous read() and write() calls to a WorkerThread. 168 // These methods post synchronous read() and write() calls to a WorkerThread.
139 void InitiateAsyncRead( 169 void InitiateAsyncRead(
140 base::PlatformFile file, char* buf, int buf_len, 170 base::PlatformFile file, char* buf, int buf_len,
171 const net::BoundNetLog& bound_net_log,
141 const CompletionCallback& callback); 172 const CompletionCallback& callback);
142 void InitiateAsyncWrite( 173 void InitiateAsyncWrite(
143 base::PlatformFile file, const char* buf, int buf_len, 174 base::PlatformFile file, const char* buf, int buf_len,
175 const net::BoundNetLog& bound_net_log,
144 const CompletionCallback& callback); 176 const CompletionCallback& callback);
145 177
146 const CompletionCallback& callback() const { return callback_; } 178 const CompletionCallback& callback() const { return callback_; }
147 179
148 // Called by the WorkerPool thread executing the IO after the IO completes. 180 // Called by the WorkerPool thread executing the IO after the IO completes.
149 // This method queues RunAsynchronousCallback() on the MessageLoop and signals 181 // This method queues RunAsynchronousCallback() on the MessageLoop and signals
150 // |background_io_completed_callback_|, in case the destructor is waiting. In 182 // |background_io_completed_callback_|, in case the destructor is waiting. In
151 // that case, the destructor will call RunAsynchronousCallback() instead, and 183 // that case, the destructor will call RunAsynchronousCallback() instead, and
152 // cancel |message_loop_task_|. 184 // cancel |message_loop_task_|.
153 // |result| is the result of the Read/Write task. 185 // |result| is the result of the Read/Write task.
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after
200 if (need_to_wait) { 232 if (need_to_wait) {
201 // We want to see if we block the message loop for too long. 233 // We want to see if we block the message loop for too long.
202 UMA_HISTOGRAM_TIMES("AsyncIO.FileStreamClose", 234 UMA_HISTOGRAM_TIMES("AsyncIO.FileStreamClose",
203 base::TimeTicks::Now() - start); 235 base::TimeTicks::Now() - start);
204 } 236 }
205 } 237 }
206 } 238 }
207 239
208 void FileStream::AsyncContext::InitiateAsyncRead( 240 void FileStream::AsyncContext::InitiateAsyncRead(
209 base::PlatformFile file, char* buf, int buf_len, 241 base::PlatformFile file, char* buf, int buf_len,
242 const net::BoundNetLog& bound_net_log,
210 const CompletionCallback& callback) { 243 const CompletionCallback& callback) {
211 DCHECK(callback_.is_null()); 244 DCHECK(callback_.is_null());
212 callback_ = callback; 245 callback_ = callback;
213 246
214 base::WorkerPool::PostTask( 247 base::WorkerPool::PostTask(
215 FROM_HERE, 248 FROM_HERE,
216 base::Bind(&ReadFileTask, file, buf, buf_len, 249 base::Bind(&ReadFileTask,
250 file,
251 buf,
252 buf_len,
217 record_uma_, 253 record_uma_,
254 bound_net_log,
218 base::Bind(&AsyncContext::OnBackgroundIOCompleted, 255 base::Bind(&AsyncContext::OnBackgroundIOCompleted,
219 base::Unretained(this))), 256 base::Unretained(this))),
220 true /* task_is_slow */); 257 true /* task_is_slow */);
221 } 258 }
222 259
223 void FileStream::AsyncContext::InitiateAsyncWrite( 260 void FileStream::AsyncContext::InitiateAsyncWrite(
224 base::PlatformFile file, const char* buf, int buf_len, 261 base::PlatformFile file, const char* buf, int buf_len,
262 const net::BoundNetLog& bound_net_log,
225 const CompletionCallback& callback) { 263 const CompletionCallback& callback) {
226 DCHECK(callback_.is_null()); 264 DCHECK(callback_.is_null());
227 callback_ = callback; 265 callback_ = callback;
228 266
229 base::WorkerPool::PostTask( 267 base::WorkerPool::PostTask(
230 FROM_HERE, 268 FROM_HERE,
231 base::Bind( 269 base::Bind(&WriteFileTask,
232 &WriteFileTask, 270 file,
233 file, buf, buf_len, 271 buf,
234 record_uma_, 272 buf_len,
235 base::Bind(&AsyncContext::OnBackgroundIOCompleted, 273 record_uma_,
236 base::Unretained(this))), 274 bound_net_log,
275 base::Bind(&AsyncContext::OnBackgroundIOCompleted,
276 base::Unretained(this))),
237 true /* task_is_slow */); 277 true /* task_is_slow */);
238 } 278 }
239 279
240 void FileStream::AsyncContext::OnBackgroundIOCompleted(int result) { 280 void FileStream::AsyncContext::OnBackgroundIOCompleted(int result) {
241 result_ = result; 281 result_ = result;
242 message_loop_task_ = new CancelableCallback( 282 message_loop_task_ = new CancelableCallback(
243 base::Bind(&AsyncContext::RunAsynchronousCallback, 283 base::Bind(&AsyncContext::RunAsynchronousCallback,
244 base::Unretained(this))); 284 base::Unretained(this)));
245 message_loop_->PostTask(FROM_HERE, 285 message_loop_->PostTask(FROM_HERE,
246 base::Bind(&CancelableCallback::Run, 286 base::Bind(&CancelableCallback::Run,
(...skipping 19 matching lines...) Expand all
266 306
267 DCHECK(!callback_.is_null()); 307 DCHECK(!callback_.is_null());
268 CompletionCallback temp; 308 CompletionCallback temp;
269 std::swap(temp, callback_); 309 std::swap(temp, callback_);
270 background_io_completed_.Reset(); 310 background_io_completed_.Reset();
271 temp.Run(result_); 311 temp.Run(result_);
272 } 312 }
273 313
274 // FileStream ------------------------------------------------------------ 314 // FileStream ------------------------------------------------------------
275 315
276 FileStream::FileStream() 316 FileStream::FileStream(net::NetLog* net_log)
277 : file_(base::kInvalidPlatformFileValue), 317 : file_(base::kInvalidPlatformFileValue),
278 open_flags_(0), 318 open_flags_(0),
279 auto_closed_(true), 319 auto_closed_(true),
280 record_uma_(false) { 320 record_uma_(false),
281 DCHECK(!IsOpen()); 321 bound_net_log_(net::BoundNetLog::Make(net_log,
322 net::NetLog::SOURCE_FILESTREAM)) {
323 bound_net_log_.BeginEvent(net::NetLog::TYPE_FILE_STREAM_ALIVE, NULL);
282 } 324 }
283 325
284 FileStream::FileStream(base::PlatformFile file, int flags) 326 FileStream::FileStream(base::PlatformFile file, int flags, net::NetLog* net_log)
285 : file_(file), 327 : file_(file),
286 open_flags_(flags), 328 open_flags_(flags),
287 auto_closed_(false), 329 auto_closed_(false),
288 record_uma_(false) { 330 record_uma_(false),
331 bound_net_log_(net::BoundNetLog::Make(net_log,
332 net::NetLog::SOURCE_FILESTREAM)) {
333 bound_net_log_.BeginEvent(net::NetLog::TYPE_FILE_STREAM_ALIVE, NULL);
334
289 // If the file handle is opened with base::PLATFORM_FILE_ASYNC, we need to 335 // If the file handle is opened with base::PLATFORM_FILE_ASYNC, we need to
290 // make sure we will perform asynchronous File IO to it. 336 // make sure we will perform asynchronous File IO to it.
291 if (flags & base::PLATFORM_FILE_ASYNC) { 337 if (flags & base::PLATFORM_FILE_ASYNC) {
292 async_context_.reset(new AsyncContext()); 338 async_context_.reset(new AsyncContext());
293 } 339 }
294 } 340 }
295 341
296 FileStream::~FileStream() { 342 FileStream::~FileStream() {
297 if (auto_closed_) 343 if (auto_closed_)
298 Close(); 344 Close();
345
346 bound_net_log_.EndEvent(net::NetLog::TYPE_FILE_STREAM_ALIVE, NULL);
299 } 347 }
300 348
301 void FileStream::Close() { 349 void FileStream::Close() {
350 bound_net_log_.AddEvent(net::NetLog::TYPE_FILE_STREAM_CLOSE, NULL);
351
302 // Abort any existing asynchronous operations. 352 // Abort any existing asynchronous operations.
303 async_context_.reset(); 353 async_context_.reset();
304 354
305 if (file_ != base::kInvalidPlatformFileValue) { 355 if (file_ != base::kInvalidPlatformFileValue) {
306 if (close(file_) != 0) { 356 if (close(file_) != 0) {
307 NOTREACHED(); 357 NOTREACHED();
308 } 358 }
309 file_ = base::kInvalidPlatformFileValue; 359 file_ = base::kInvalidPlatformFileValue;
360
361 bound_net_log_.EndEvent(net::NetLog::TYPE_FILE_STREAM_OPEN, NULL);
310 } 362 }
311 } 363 }
312 364
313 int FileStream::Open(const FilePath& path, int open_flags) { 365 int FileStream::Open(const FilePath& path, int open_flags) {
314 if (IsOpen()) { 366 if (IsOpen()) {
315 DLOG(FATAL) << "File is already open!"; 367 DLOG(FATAL) << "File is already open!";
316 return ERR_UNEXPECTED; 368 return ERR_UNEXPECTED;
317 } 369 }
318 370
371 bound_net_log_.BeginEvent(
372 net::NetLog::TYPE_FILE_STREAM_OPEN,
373 make_scoped_refptr(
374 new net::NetLogStringParameter("file_name",
375 path.AsUTF8Unsafe())));
376
319 open_flags_ = open_flags; 377 open_flags_ = open_flags;
320 file_ = base::CreatePlatformFile(path, open_flags_, NULL, NULL); 378 file_ = base::CreatePlatformFile(path, open_flags_, NULL, NULL);
321 if (file_ == base::kInvalidPlatformFileValue) 379 if (file_ == base::kInvalidPlatformFileValue) {
322 return RecordAndMapError(errno, FILE_ERROR_SOURCE_OPEN, record_uma_); 380 int net_error = RecordAndMapError(errno,
381 FILE_ERROR_SOURCE_OPEN,
382 record_uma_,
383 bound_net_log_);
384 bound_net_log_.EndEvent(net::NetLog::TYPE_FILE_STREAM_OPEN, NULL);
385 return net_error;
386 }
323 387
324 if (open_flags_ & base::PLATFORM_FILE_ASYNC) 388 if (open_flags_ & base::PLATFORM_FILE_ASYNC)
325 async_context_.reset(new AsyncContext()); 389 async_context_.reset(new AsyncContext());
326 390
327 return OK; 391 return OK;
328 } 392 }
329 393
330 bool FileStream::IsOpen() const { 394 bool FileStream::IsOpen() const {
331 return file_ != base::kInvalidPlatformFileValue; 395 return file_ != base::kInvalidPlatformFileValue;
332 } 396 }
333 397
334 int64 FileStream::Seek(Whence whence, int64 offset) { 398 int64 FileStream::Seek(Whence whence, int64 offset) {
335 base::ThreadRestrictions::AssertIOAllowed(); 399 base::ThreadRestrictions::AssertIOAllowed();
336 400
337 if (!IsOpen()) 401 if (!IsOpen())
338 return ERR_UNEXPECTED; 402 return ERR_UNEXPECTED;
339 403
340 // If we're in async, make sure we don't have a request in flight. 404 // If we're in async, make sure we don't have a request in flight.
341 DCHECK(!async_context_.get() || async_context_->callback().is_null()); 405 DCHECK(!async_context_.get() || async_context_->callback().is_null());
342 406
343 off_t res = lseek(file_, static_cast<off_t>(offset), 407 off_t res = lseek(file_, static_cast<off_t>(offset),
344 static_cast<int>(whence)); 408 static_cast<int>(whence));
345 if (res == static_cast<off_t>(-1)) 409 if (res == static_cast<off_t>(-1)) {
346 return RecordAndMapError(errno, FILE_ERROR_SOURCE_SEEK, record_uma_); 410 return RecordAndMapError(errno,
411 FILE_ERROR_SOURCE_SEEK,
412 record_uma_,
413 bound_net_log_);
414 }
347 415
348 return res; 416 return res;
349 } 417 }
350 418
351 int64 FileStream::Available() { 419 int64 FileStream::Available() {
352 base::ThreadRestrictions::AssertIOAllowed(); 420 base::ThreadRestrictions::AssertIOAllowed();
353 421
354 if (!IsOpen()) 422 if (!IsOpen())
355 return ERR_UNEXPECTED; 423 return ERR_UNEXPECTED;
356 424
357 int64 cur_pos = Seek(FROM_CURRENT, 0); 425 int64 cur_pos = Seek(FROM_CURRENT, 0);
358 if (cur_pos < 0) 426 if (cur_pos < 0)
359 return cur_pos; 427 return cur_pos;
360 428
361 struct stat info; 429 struct stat info;
362 if (fstat(file_, &info) != 0) 430 if (fstat(file_, &info) != 0) {
363 return RecordAndMapError(errno, FILE_ERROR_SOURCE_GET_SIZE, record_uma_); 431 return RecordAndMapError(errno,
432 FILE_ERROR_SOURCE_GET_SIZE,
433 record_uma_,
434 bound_net_log_);
435 }
364 436
365 int64 size = static_cast<int64>(info.st_size); 437 int64 size = static_cast<int64>(info.st_size);
366 DCHECK_GT(size, cur_pos); 438 DCHECK_GT(size, cur_pos);
367 439
368 return size - cur_pos; 440 return size - cur_pos;
369 } 441 }
370 442
371 int FileStream::Read( 443 int FileStream::Read(
372 char* buf, int buf_len, const CompletionCallback& callback) { 444 char* buf, int buf_len, const CompletionCallback& callback) {
373 if (!IsOpen()) 445 if (!IsOpen())
374 return ERR_UNEXPECTED; 446 return ERR_UNEXPECTED;
375 447
376 // read(..., 0) will return 0, which indicates end-of-file. 448 // read(..., 0) will return 0, which indicates end-of-file.
377 DCHECK_GT(buf_len, 0); 449 DCHECK_GT(buf_len, 0);
378 DCHECK(open_flags_ & base::PLATFORM_FILE_READ); 450 DCHECK(open_flags_ & base::PLATFORM_FILE_READ);
379 451
380 if (async_context_.get()) { 452 if (async_context_.get()) {
381 DCHECK(open_flags_ & base::PLATFORM_FILE_ASYNC); 453 DCHECK(open_flags_ & base::PLATFORM_FILE_ASYNC);
382 // If we're in async, make sure we don't have a request in flight. 454 // If we're in async, make sure we don't have a request in flight.
383 DCHECK(async_context_->callback().is_null()); 455 DCHECK(async_context_->callback().is_null());
384 if (record_uma_) 456 if (record_uma_)
385 async_context_->EnableErrorStatistics(); 457 async_context_->EnableErrorStatistics();
386 async_context_->InitiateAsyncRead(file_, buf, buf_len, callback); 458 async_context_->InitiateAsyncRead(file_, buf, buf_len, bound_net_log_,
459 callback);
387 return ERR_IO_PENDING; 460 return ERR_IO_PENDING;
388 } else { 461 } else {
389 return ReadFile(file_, buf, buf_len, record_uma_); 462 return ReadFile(file_, buf, buf_len, record_uma_, bound_net_log_);
390 } 463 }
391 } 464 }
392 465
393 int FileStream::ReadUntilComplete(char *buf, int buf_len) { 466 int FileStream::ReadUntilComplete(char *buf, int buf_len) {
394 int to_read = buf_len; 467 int to_read = buf_len;
395 int bytes_total = 0; 468 int bytes_total = 0;
396 469
397 do { 470 do {
398 int bytes_read = Read(buf, to_read, CompletionCallback()); 471 int bytes_read = Read(buf, to_read, CompletionCallback());
399 if (bytes_read <= 0) { 472 if (bytes_read <= 0) {
(...skipping 18 matching lines...) Expand all
418 491
419 if (!IsOpen()) 492 if (!IsOpen())
420 return ERR_UNEXPECTED; 493 return ERR_UNEXPECTED;
421 494
422 if (async_context_.get()) { 495 if (async_context_.get()) {
423 DCHECK(open_flags_ & base::PLATFORM_FILE_ASYNC); 496 DCHECK(open_flags_ & base::PLATFORM_FILE_ASYNC);
424 // If we're in async, make sure we don't have a request in flight. 497 // If we're in async, make sure we don't have a request in flight.
425 DCHECK(async_context_->callback().is_null()); 498 DCHECK(async_context_->callback().is_null());
426 if (record_uma_) 499 if (record_uma_)
427 async_context_->EnableErrorStatistics(); 500 async_context_->EnableErrorStatistics();
428 async_context_->InitiateAsyncWrite(file_, buf, buf_len, callback); 501 async_context_->InitiateAsyncWrite(file_, buf, buf_len, bound_net_log_,
502 callback);
429 return ERR_IO_PENDING; 503 return ERR_IO_PENDING;
430 } else { 504 } else {
431 return WriteFile(file_, buf, buf_len, record_uma_); 505 return WriteFile(file_, buf, buf_len, record_uma_, bound_net_log_);
432 } 506 }
433 } 507 }
434 508
435 int64 FileStream::Truncate(int64 bytes) { 509 int64 FileStream::Truncate(int64 bytes) {
436 base::ThreadRestrictions::AssertIOAllowed(); 510 base::ThreadRestrictions::AssertIOAllowed();
437 511
438 if (!IsOpen()) 512 if (!IsOpen())
439 return ERR_UNEXPECTED; 513 return ERR_UNEXPECTED;
440 514
441 // We better be open for reading. 515 // We'd better be open for writing.
442 DCHECK(open_flags_ & base::PLATFORM_FILE_WRITE); 516 DCHECK(open_flags_ & base::PLATFORM_FILE_WRITE);
443 517
444 // Seek to the position to truncate from. 518 // Seek to the position to truncate from.
445 int64 seek_position = Seek(FROM_BEGIN, bytes); 519 int64 seek_position = Seek(FROM_BEGIN, bytes);
446 if (seek_position != bytes) 520 if (seek_position != bytes)
447 return ERR_UNEXPECTED; 521 return ERR_UNEXPECTED;
448 522
449 // And truncate the file. 523 // And truncate the file.
450 int result = ftruncate(file_, bytes); 524 int result = ftruncate(file_, bytes);
451 if (result == 0) 525 if (result == 0)
452 return seek_position; 526 return seek_position;
453 527
454 return RecordAndMapError(errno, FILE_ERROR_SOURCE_SET_EOF, record_uma_); 528 return RecordAndMapError(errno,
529 FILE_ERROR_SOURCE_SET_EOF,
530 record_uma_,
531 bound_net_log_);
455 } 532 }
456 533
457 int FileStream::Flush() { 534 int FileStream::Flush() {
458 if (!IsOpen()) 535 if (!IsOpen())
459 return ERR_UNEXPECTED; 536 return ERR_UNEXPECTED;
460 537
461 return FlushFile(file_, record_uma_); 538 return FlushFile(file_, record_uma_, bound_net_log_);
462 } 539 }
463 540
464 void FileStream::EnableErrorStatistics() { 541 void FileStream::EnableErrorStatistics() {
465 record_uma_ = true; 542 record_uma_ = true;
466 } 543 }
467 544
545 void FileStream::SetBoundNetLogSource(
546 const net::BoundNetLog& owner_bound_net_log) {
547 if ((owner_bound_net_log.source().id == net::NetLog::Source::kInvalidId) &&
548 (bound_net_log_.source().id == net::NetLog::Source::kInvalidId)) {
549 // Both |BoundNetLog|s are invalid.
550 return;
551 }
552
553 // Should never connect to itself.
554 DCHECK_NE(bound_net_log_.source().id, owner_bound_net_log.source().id);
555
556 bound_net_log_.AddEvent(
557 net::NetLog::TYPE_FILE_STREAM_BOUND_TO_OWNER,
558 make_scoped_refptr(
559 new net::NetLogSourceParameter("source_dependency",
560 owner_bound_net_log.source())));
561
562 owner_bound_net_log.AddEvent(
563 net::NetLog::TYPE_FILE_STREAM_SOURCE,
564 make_scoped_refptr(
565 new net::NetLogSourceParameter("source_dependency",
566 bound_net_log_.source())));
567 }
568
468 } // namespace net 569 } // namespace net
OLDNEW
« no previous file with comments | « net/base/file_stream_net_log_parameters.cc ('k') | net/base/file_stream_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698