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 "base/platform_file.h" | 5 #include "base/files/base_file.h" |
6 | 6 |
| 7 #include <errno.h> |
7 #include <fcntl.h> | 8 #include <fcntl.h> |
8 #include <errno.h> | |
9 #include <sys/stat.h> | 9 #include <sys/stat.h> |
10 #include <unistd.h> | 10 #include <unistd.h> |
11 | 11 |
12 #include "base/files/file_path.h" | 12 #include "base/files/file_path.h" |
13 #include "base/logging.h" | 13 #include "base/logging.h" |
14 #include "base/metrics/sparse_histogram.h" | 14 #include "base/metrics/sparse_histogram.h" |
| 15 // TODO(rvargas): remove this (needed for kInvalidPlatformFileValue). |
| 16 #include "base/platform_file.h" |
15 #include "base/posix/eintr_wrapper.h" | 17 #include "base/posix/eintr_wrapper.h" |
16 #include "base/strings/utf_string_conversions.h" | 18 #include "base/strings/utf_string_conversions.h" |
17 #include "base/threading/thread_restrictions.h" | 19 #include "base/threading/thread_restrictions.h" |
18 | 20 |
19 #if defined(OS_ANDROID) | 21 #if defined(OS_ANDROID) |
20 #include "base/os_compat_android.h" | 22 #include "base/os_compat_android.h" |
21 #endif | 23 #endif |
22 | 24 |
23 namespace base { | 25 namespace base { |
24 | 26 |
25 // Make sure our Whence mappings match the system headers. | 27 // Make sure our Whence mappings match the system headers. |
26 COMPILE_ASSERT(PLATFORM_FILE_FROM_BEGIN == SEEK_SET && | 28 COMPILE_ASSERT(BASE_FILE_FROM_BEGIN == SEEK_SET && |
27 PLATFORM_FILE_FROM_CURRENT == SEEK_CUR && | 29 BASE_FILE_FROM_CURRENT == SEEK_CUR && |
28 PLATFORM_FILE_FROM_END == SEEK_END, whence_matches_system); | 30 BASE_FILE_FROM_END == SEEK_END, whence_matches_system); |
29 | 31 |
30 namespace { | 32 namespace { |
31 | 33 |
32 #if defined(OS_BSD) || defined(OS_MACOSX) || defined(OS_NACL) | 34 #if defined(OS_BSD) || defined(OS_MACOSX) || defined(OS_NACL) |
33 typedef struct stat stat_wrapper_t; | 35 typedef struct stat stat_wrapper_t; |
34 static int CallFstat(int fd, stat_wrapper_t *sb) { | 36 static int CallFstat(int fd, stat_wrapper_t *sb) { |
35 base::ThreadRestrictions::AssertIOAllowed(); | 37 base::ThreadRestrictions::AssertIOAllowed(); |
36 return fstat(fd, sb); | 38 return fstat(fd, sb); |
37 } | 39 } |
38 #else | 40 #else |
(...skipping 29 matching lines...) Expand all Loading... |
68 ts_times[0].tv_nsec = times[0].tv_usec * 1000; | 70 ts_times[0].tv_nsec = times[0].tv_usec * 1000; |
69 ts_times[1].tv_sec = times[1].tv_sec; | 71 ts_times[1].tv_sec = times[1].tv_sec; |
70 ts_times[1].tv_nsec = times[1].tv_usec * 1000; | 72 ts_times[1].tv_nsec = times[1].tv_usec * 1000; |
71 | 73 |
72 return futimens(file, ts_times); | 74 return futimens(file, ts_times); |
73 #else | 75 #else |
74 return futimes(file, times); | 76 return futimes(file, times); |
75 #endif | 77 #endif |
76 } | 78 } |
77 | 79 |
78 static PlatformFileError CallFctnlFlock(PlatformFile file, bool do_lock) { | 80 static BaseFileError CallFctnlFlock(PlatformFile file, bool do_lock) { |
79 struct flock lock; | 81 struct flock lock; |
80 lock.l_type = F_WRLCK; | 82 lock.l_type = F_WRLCK; |
81 lock.l_whence = SEEK_SET; | 83 lock.l_whence = SEEK_SET; |
82 lock.l_start = 0; | 84 lock.l_start = 0; |
83 lock.l_len = 0; // Lock entire file. | 85 lock.l_len = 0; // Lock entire file. |
84 if (HANDLE_EINTR(fcntl(file, do_lock ? F_SETLK : F_UNLCK, &lock)) == -1) | 86 if (HANDLE_EINTR(fcntl(file, do_lock ? F_SETLK : F_UNLCK, &lock)) == -1) |
85 return ErrnoToPlatformFileError(errno); | 87 return ErrorToBaseFileError(errno); |
86 return PLATFORM_FILE_OK; | 88 return BASE_FILE_OK; |
87 } | 89 } |
88 #else // defined(OS_NACL) | 90 #else // defined(OS_NACL) |
89 | 91 |
90 static bool IsOpenAppend(PlatformFile file) { | 92 static bool IsOpenAppend(PlatformFile file) { |
91 // NaCl doesn't implement fcntl. Since NaCl's write conforms to the POSIX | 93 // NaCl doesn't implement fcntl. Since NaCl's write conforms to the POSIX |
92 // standard and always appends if the file is opened with O_APPEND, just | 94 // standard and always appends if the file is opened with O_APPEND, just |
93 // return false here. | 95 // return false here. |
94 return false; | 96 return false; |
95 } | 97 } |
96 | 98 |
97 static int CallFtruncate(PlatformFile file, int64 length) { | 99 static int CallFtruncate(PlatformFile file, int64 length) { |
98 NOTIMPLEMENTED(); // NaCl doesn't implement ftruncate. | 100 NOTIMPLEMENTED(); // NaCl doesn't implement ftruncate. |
99 return 0; | 101 return 0; |
100 } | 102 } |
101 | 103 |
102 static int CallFsync(PlatformFile file) { | 104 static int CallFsync(PlatformFile file) { |
103 NOTIMPLEMENTED(); // NaCl doesn't implement fsync. | 105 NOTIMPLEMENTED(); // NaCl doesn't implement fsync. |
104 return 0; | 106 return 0; |
105 } | 107 } |
106 | 108 |
107 static int CallFutimes(PlatformFile file, const struct timeval times[2]) { | 109 static int CallFutimes(PlatformFile file, const struct timeval times[2]) { |
108 NOTIMPLEMENTED(); // NaCl doesn't implement futimes. | 110 NOTIMPLEMENTED(); // NaCl doesn't implement futimes. |
109 return 0; | 111 return 0; |
110 } | 112 } |
111 | 113 |
112 static PlatformFileError CallFctnlFlock(PlatformFile file, bool do_lock) { | 114 static BaseFileError CallFctnlFlock(PlatformFile file, bool do_lock) { |
113 NOTIMPLEMENTED(); // NaCl doesn't implement flock struct. | 115 NOTIMPLEMENTED(); // NaCl doesn't implement flock struct. |
114 return PLATFORM_FILE_ERROR_INVALID_OPERATION; | 116 return BASE_FILE_ERROR_INVALID_OPERATION; |
115 } | 117 } |
116 #endif // defined(OS_NACL) | 118 #endif // defined(OS_NACL) |
117 | 119 |
118 } // namespace | 120 } // namespace |
119 | 121 |
| 122 BaseFileError ErrorToBaseFileError(int saved_errno) { |
| 123 switch (saved_errno) { |
| 124 case EACCES: |
| 125 case EISDIR: |
| 126 case EROFS: |
| 127 case EPERM: |
| 128 return BASE_FILE_ERROR_ACCESS_DENIED; |
| 129 #if !defined(OS_NACL) // ETXTBSY not defined by NaCl. |
| 130 case ETXTBSY: |
| 131 return BASE_FILE_ERROR_IN_USE; |
| 132 #endif |
| 133 case EEXIST: |
| 134 return BASE_FILE_ERROR_EXISTS; |
| 135 case ENOENT: |
| 136 return BASE_FILE_ERROR_NOT_FOUND; |
| 137 case EMFILE: |
| 138 return BASE_FILE_ERROR_TOO_MANY_OPENED; |
| 139 case ENOMEM: |
| 140 return BASE_FILE_ERROR_NO_MEMORY; |
| 141 case ENOSPC: |
| 142 return BASE_FILE_ERROR_NO_SPACE; |
| 143 case ENOTDIR: |
| 144 return BASE_FILE_ERROR_NOT_A_DIRECTORY; |
| 145 default: |
| 146 #if !defined(OS_NACL) // NaCl build has no metrics code. |
| 147 UMA_HISTOGRAM_SPARSE_SLOWLY("PlatformFile.UnknownErrors.Posix", |
| 148 saved_errno); |
| 149 #endif |
| 150 return BASE_FILE_ERROR_FAILED; |
| 151 } |
| 152 } |
| 153 |
120 // NaCl doesn't implement system calls to open files directly. | 154 // NaCl doesn't implement system calls to open files directly. |
121 #if !defined(OS_NACL) | 155 #if !defined(OS_NACL) |
122 // TODO(erikkay): does it make sense to support PLATFORM_FILE_EXCLUSIVE_* here? | 156 // TODO(erikkay): does it make sense to support BASE_FILE_EXCLUSIVE_* here? |
123 PlatformFile CreatePlatformFileUnsafe(const FilePath& name, | 157 void BaseFile::CreateBaseFileUnsafe(const FilePath& name, int flags) { |
124 int flags, | |
125 bool* created, | |
126 PlatformFileError* error) { | |
127 base::ThreadRestrictions::AssertIOAllowed(); | 158 base::ThreadRestrictions::AssertIOAllowed(); |
| 159 DCHECK(!IsValid()); |
| 160 DCHECK(!(flags & BASE_FILE_ASYNC)); |
128 | 161 |
129 int open_flags = 0; | 162 int open_flags = 0; |
130 if (flags & PLATFORM_FILE_CREATE) | 163 if (flags & BASE_FILE_CREATE) |
131 open_flags = O_CREAT | O_EXCL; | 164 open_flags = O_CREAT | O_EXCL; |
132 | 165 |
133 if (created) | 166 created_ = false; |
134 *created = false; | |
135 | 167 |
136 if (flags & PLATFORM_FILE_CREATE_ALWAYS) { | 168 if (flags & BASE_FILE_CREATE_ALWAYS) { |
137 DCHECK(!open_flags); | 169 DCHECK(!open_flags); |
138 open_flags = O_CREAT | O_TRUNC; | 170 open_flags = O_CREAT | O_TRUNC; |
139 } | 171 } |
140 | 172 |
141 if (flags & PLATFORM_FILE_OPEN_TRUNCATED) { | 173 if (flags & BASE_FILE_OPEN_TRUNCATED) { |
142 DCHECK(!open_flags); | 174 DCHECK(!open_flags); |
143 DCHECK(flags & PLATFORM_FILE_WRITE); | 175 DCHECK(flags & BASE_FILE_WRITE); |
144 open_flags = O_TRUNC; | 176 open_flags = O_TRUNC; |
145 } | 177 } |
146 | 178 |
147 if (!open_flags && !(flags & PLATFORM_FILE_OPEN) && | 179 if (!open_flags && !(flags & BASE_FILE_OPEN) && |
148 !(flags & PLATFORM_FILE_OPEN_ALWAYS)) { | 180 !(flags & BASE_FILE_OPEN_ALWAYS)) { |
149 NOTREACHED(); | 181 NOTREACHED(); |
150 errno = EOPNOTSUPP; | 182 errno = EOPNOTSUPP; |
151 if (error) | 183 error_ = BASE_FILE_ERROR_FAILED; |
152 *error = PLATFORM_FILE_ERROR_FAILED; | 184 return; |
153 return kInvalidPlatformFileValue; | |
154 } | 185 } |
155 | 186 |
156 if (flags & PLATFORM_FILE_WRITE && flags & PLATFORM_FILE_READ) { | 187 if (flags & BASE_FILE_WRITE && flags & BASE_FILE_READ) { |
157 open_flags |= O_RDWR; | 188 open_flags |= O_RDWR; |
158 } else if (flags & PLATFORM_FILE_WRITE) { | 189 } else if (flags & BASE_FILE_WRITE) { |
159 open_flags |= O_WRONLY; | 190 open_flags |= O_WRONLY; |
160 } else if (!(flags & PLATFORM_FILE_READ) && | 191 } else if (!(flags & BASE_FILE_READ) && |
161 !(flags & PLATFORM_FILE_WRITE_ATTRIBUTES) && | 192 !(flags & BASE_FILE_WRITE_ATTRIBUTES) && |
162 !(flags & PLATFORM_FILE_APPEND) && | 193 !(flags & BASE_FILE_APPEND) && |
163 !(flags & PLATFORM_FILE_OPEN_ALWAYS)) { | 194 !(flags & BASE_FILE_OPEN_ALWAYS)) { |
164 NOTREACHED(); | 195 NOTREACHED(); |
165 } | 196 } |
166 | 197 |
167 if (flags & PLATFORM_FILE_TERMINAL_DEVICE) | 198 if (flags & BASE_FILE_TERMINAL_DEVICE) |
168 open_flags |= O_NOCTTY | O_NDELAY; | 199 open_flags |= O_NOCTTY | O_NDELAY; |
169 | 200 |
170 if (flags & PLATFORM_FILE_APPEND && flags & PLATFORM_FILE_READ) | 201 if (flags & BASE_FILE_APPEND && flags & BASE_FILE_READ) |
171 open_flags |= O_APPEND | O_RDWR; | 202 open_flags |= O_APPEND | O_RDWR; |
172 else if (flags & PLATFORM_FILE_APPEND) | 203 else if (flags & BASE_FILE_APPEND) |
173 open_flags |= O_APPEND | O_WRONLY; | 204 open_flags |= O_APPEND | O_WRONLY; |
174 | 205 |
175 COMPILE_ASSERT(O_RDONLY == 0, O_RDONLY_must_equal_zero); | 206 COMPILE_ASSERT(O_RDONLY == 0, O_RDONLY_must_equal_zero); |
176 | 207 |
177 int mode = S_IRUSR | S_IWUSR; | 208 int mode = S_IRUSR | S_IWUSR; |
178 #if defined(OS_CHROMEOS) | 209 #if defined(OS_CHROMEOS) |
179 mode |= S_IRGRP | S_IROTH; | 210 mode |= S_IRGRP | S_IROTH; |
180 #endif | 211 #endif |
181 | 212 |
182 int descriptor = | 213 int descriptor = |
183 HANDLE_EINTR(open(name.value().c_str(), open_flags, mode)); | 214 HANDLE_EINTR(open(name.value().c_str(), open_flags, mode)); |
184 | 215 |
185 if (flags & PLATFORM_FILE_OPEN_ALWAYS) { | 216 if (flags & BASE_FILE_OPEN_ALWAYS) { |
186 if (descriptor < 0) { | 217 if (descriptor < 0) { |
187 open_flags |= O_CREAT; | 218 open_flags |= O_CREAT; |
188 if (flags & PLATFORM_FILE_EXCLUSIVE_READ || | 219 if (flags & BASE_FILE_EXCLUSIVE_READ || |
189 flags & PLATFORM_FILE_EXCLUSIVE_WRITE) { | 220 flags & BASE_FILE_EXCLUSIVE_WRITE) { |
190 open_flags |= O_EXCL; // together with O_CREAT implies O_NOFOLLOW | 221 open_flags |= O_EXCL; // together with O_CREAT implies O_NOFOLLOW |
191 } | 222 } |
192 descriptor = HANDLE_EINTR( | 223 descriptor = HANDLE_EINTR( |
193 open(name.value().c_str(), open_flags, mode)); | 224 open(name.value().c_str(), open_flags, mode)); |
194 if (created && descriptor >= 0) | 225 if (descriptor >= 0) |
195 *created = true; | 226 created_ = true; |
196 } | 227 } |
197 } | 228 } |
198 | 229 |
199 if (created && (descriptor >= 0) && | 230 if (descriptor >= 0 && |
200 (flags & (PLATFORM_FILE_CREATE_ALWAYS | PLATFORM_FILE_CREATE))) | 231 (flags & (BASE_FILE_CREATE_ALWAYS | BASE_FILE_CREATE))) { |
201 *created = true; | 232 created_ = true; |
| 233 } |
202 | 234 |
203 if ((descriptor >= 0) && (flags & PLATFORM_FILE_DELETE_ON_CLOSE)) { | 235 if ((descriptor >= 0) && (flags & BASE_FILE_DELETE_ON_CLOSE)) { |
204 unlink(name.value().c_str()); | 236 unlink(name.value().c_str()); |
205 } | 237 } |
206 | 238 |
207 if (error) { | 239 if (descriptor >= 0) |
208 if (descriptor >= 0) | 240 error_ = BASE_FILE_OK; |
209 *error = PLATFORM_FILE_OK; | 241 else |
210 else | 242 error_ = ErrorToBaseFileError(errno); |
211 *error = ErrnoToPlatformFileError(errno); | |
212 } | |
213 | 243 |
214 return descriptor; | 244 file_ = descriptor; |
215 } | |
216 | |
217 FILE* FdopenPlatformFile(PlatformFile file, const char* mode) { | |
218 return fdopen(file, mode); | |
219 } | 245 } |
220 #endif // !defined(OS_NACL) | 246 #endif // !defined(OS_NACL) |
221 | 247 |
222 bool ClosePlatformFile(PlatformFile file) { | 248 bool BaseFile::IsValid() const { |
223 base::ThreadRestrictions::AssertIOAllowed(); | 249 return file_ >= 0; |
224 return !HANDLE_EINTR(close(file)); | |
225 } | 250 } |
226 | 251 |
227 int64 SeekPlatformFile(PlatformFile file, | 252 PlatformFile BaseFile::TakePlatformFile() { |
228 PlatformFileWhence whence, | 253 PlatformFile file = file_; |
229 int64 offset) { | 254 file_ = kInvalidPlatformFileValue; |
| 255 return file; |
| 256 } |
| 257 |
| 258 void BaseFile::Close() { |
230 base::ThreadRestrictions::AssertIOAllowed(); | 259 base::ThreadRestrictions::AssertIOAllowed(); |
231 if (file < 0 || offset < 0) | 260 if (!IsValid()) |
| 261 return; |
| 262 |
| 263 if (!HANDLE_EINTR(close(file_))) |
| 264 file_ = kInvalidPlatformFileValue; |
| 265 } |
| 266 |
| 267 int64 BaseFile::Seek(BaseFileWhence whence, int64 offset) { |
| 268 base::ThreadRestrictions::AssertIOAllowed(); |
| 269 DCHECK(IsValid()); |
| 270 if (file_ < 0 || offset < 0) |
232 return -1; | 271 return -1; |
233 | 272 |
234 return lseek(file, static_cast<off_t>(offset), static_cast<int>(whence)); | 273 return lseek(file_, static_cast<off_t>(offset), static_cast<int>(whence)); |
235 } | 274 } |
236 | 275 |
237 int ReadPlatformFile(PlatformFile file, int64 offset, char* data, int size) { | 276 int BaseFile::Read(int64 offset, char* data, int size) { |
238 base::ThreadRestrictions::AssertIOAllowed(); | 277 base::ThreadRestrictions::AssertIOAllowed(); |
239 if (file < 0 || size < 0) | 278 DCHECK(IsValid()); |
| 279 if (size < 0) |
240 return -1; | 280 return -1; |
241 | 281 |
242 int bytes_read = 0; | 282 int bytes_read = 0; |
243 int rv; | 283 int rv; |
244 do { | 284 do { |
245 rv = HANDLE_EINTR(pread(file, data + bytes_read, | 285 rv = HANDLE_EINTR(pread(file_, data + bytes_read, |
246 size - bytes_read, offset + bytes_read)); | 286 size - bytes_read, offset + bytes_read)); |
247 if (rv <= 0) | 287 if (rv <= 0) |
248 break; | 288 break; |
249 | 289 |
250 bytes_read += rv; | 290 bytes_read += rv; |
251 } while (bytes_read < size); | 291 } while (bytes_read < size); |
252 | 292 |
253 return bytes_read ? bytes_read : rv; | 293 return bytes_read ? bytes_read : rv; |
254 } | 294 } |
255 | 295 |
256 int ReadPlatformFileAtCurrentPos(PlatformFile file, char* data, int size) { | 296 int BaseFile::ReadAtCurrentPos(char* data, int size) { |
257 base::ThreadRestrictions::AssertIOAllowed(); | 297 base::ThreadRestrictions::AssertIOAllowed(); |
258 if (file < 0 || size < 0) | 298 DCHECK(IsValid()); |
| 299 if (size < 0) |
259 return -1; | 300 return -1; |
260 | 301 |
261 int bytes_read = 0; | 302 int bytes_read = 0; |
262 int rv; | 303 int rv; |
263 do { | 304 do { |
264 rv = HANDLE_EINTR(read(file, data, size)); | 305 rv = HANDLE_EINTR(read(file_, data, size)); |
265 if (rv <= 0) | 306 if (rv <= 0) |
266 break; | 307 break; |
267 | 308 |
268 bytes_read += rv; | 309 bytes_read += rv; |
269 } while (bytes_read < size); | 310 } while (bytes_read < size); |
270 | 311 |
271 return bytes_read ? bytes_read : rv; | 312 return bytes_read ? bytes_read : rv; |
272 } | 313 } |
273 | 314 |
274 int ReadPlatformFileNoBestEffort(PlatformFile file, int64 offset, | 315 int BaseFile::ReadNoBestEffort(int64 offset, char* data, int size) { |
275 char* data, int size) { | |
276 base::ThreadRestrictions::AssertIOAllowed(); | 316 base::ThreadRestrictions::AssertIOAllowed(); |
277 if (file < 0) | 317 DCHECK(IsValid()); |
| 318 |
| 319 return HANDLE_EINTR(pread(file_, data, size, offset)); |
| 320 } |
| 321 |
| 322 int BaseFile::ReadAtCurrentPosNoBestEffort(char* data, int size) { |
| 323 base::ThreadRestrictions::AssertIOAllowed(); |
| 324 DCHECK(IsValid()); |
| 325 if (size < 0) |
278 return -1; | 326 return -1; |
279 | 327 |
280 return HANDLE_EINTR(pread(file, data, size, offset)); | 328 return HANDLE_EINTR(read(file_, data, size)); |
281 } | 329 } |
282 | 330 |
283 int ReadPlatformFileCurPosNoBestEffort(PlatformFile file, | 331 int BaseFile::Write(int64 offset, const char* data, int size) { |
284 char* data, int size) { | |
285 base::ThreadRestrictions::AssertIOAllowed(); | |
286 if (file < 0 || size < 0) | |
287 return -1; | |
288 | |
289 return HANDLE_EINTR(read(file, data, size)); | |
290 } | |
291 | |
292 int WritePlatformFile(PlatformFile file, int64 offset, | |
293 const char* data, int size) { | |
294 base::ThreadRestrictions::AssertIOAllowed(); | 332 base::ThreadRestrictions::AssertIOAllowed(); |
295 | 333 |
296 if (IsOpenAppend(file)) | 334 if (IsOpenAppend(file_)) |
297 return WritePlatformFileAtCurrentPos(file, data, size); | 335 return WriteAtCurrentPos(data, size); |
298 | 336 |
299 if (file < 0 || size < 0) | 337 DCHECK(IsValid()); |
| 338 if (size < 0) |
300 return -1; | 339 return -1; |
301 | 340 |
302 int bytes_written = 0; | 341 int bytes_written = 0; |
303 int rv; | 342 int rv; |
304 do { | 343 do { |
305 rv = HANDLE_EINTR(pwrite(file, data + bytes_written, | 344 rv = HANDLE_EINTR(pwrite(file_, data + bytes_written, |
306 size - bytes_written, offset + bytes_written)); | 345 size - bytes_written, offset + bytes_written)); |
307 if (rv <= 0) | 346 if (rv <= 0) |
308 break; | 347 break; |
309 | 348 |
310 bytes_written += rv; | 349 bytes_written += rv; |
311 } while (bytes_written < size); | 350 } while (bytes_written < size); |
312 | 351 |
313 return bytes_written ? bytes_written : rv; | 352 return bytes_written ? bytes_written : rv; |
314 } | 353 } |
315 | 354 |
316 int WritePlatformFileAtCurrentPos(PlatformFile file, | 355 int BaseFile::WriteAtCurrentPos(const char* data, int size) { |
317 const char* data, int size) { | |
318 base::ThreadRestrictions::AssertIOAllowed(); | 356 base::ThreadRestrictions::AssertIOAllowed(); |
319 if (file < 0 || size < 0) | 357 DCHECK(IsValid()); |
| 358 if (size < 0) |
320 return -1; | 359 return -1; |
321 | 360 |
322 int bytes_written = 0; | 361 int bytes_written = 0; |
323 int rv; | 362 int rv; |
324 do { | 363 do { |
325 rv = HANDLE_EINTR(write(file, data, size)); | 364 rv = HANDLE_EINTR(write(file_, data, size)); |
326 if (rv <= 0) | 365 if (rv <= 0) |
327 break; | 366 break; |
328 | 367 |
329 bytes_written += rv; | 368 bytes_written += rv; |
330 } while (bytes_written < size); | 369 } while (bytes_written < size); |
331 | 370 |
332 return bytes_written ? bytes_written : rv; | 371 return bytes_written ? bytes_written : rv; |
333 } | 372 } |
334 | 373 |
335 int WritePlatformFileCurPosNoBestEffort(PlatformFile file, | 374 int BaseFile::WriteAtCurrentPosNoBestEffort(const char* data, int size) { |
336 const char* data, int size) { | |
337 base::ThreadRestrictions::AssertIOAllowed(); | 375 base::ThreadRestrictions::AssertIOAllowed(); |
338 if (file < 0 || size < 0) | 376 DCHECK(IsValid()); |
| 377 if (size < 0) |
339 return -1; | 378 return -1; |
340 | 379 |
341 return HANDLE_EINTR(write(file, data, size)); | 380 return HANDLE_EINTR(write(file_, data, size)); |
342 } | 381 } |
343 | 382 |
344 bool TruncatePlatformFile(PlatformFile file, int64 length) { | 383 bool BaseFile::Truncate(int64 length) { |
345 base::ThreadRestrictions::AssertIOAllowed(); | 384 base::ThreadRestrictions::AssertIOAllowed(); |
346 return ((file >= 0) && !CallFtruncate(file, length)); | 385 DCHECK(IsValid()); |
| 386 return !CallFtruncate(file_, length); |
347 } | 387 } |
348 | 388 |
349 bool FlushPlatformFile(PlatformFile file) { | 389 bool BaseFile::Flush() { |
350 base::ThreadRestrictions::AssertIOAllowed(); | 390 base::ThreadRestrictions::AssertIOAllowed(); |
351 return !CallFsync(file); | 391 DCHECK(IsValid()); |
| 392 return !CallFsync(file_); |
352 } | 393 } |
353 | 394 |
354 bool TouchPlatformFile(PlatformFile file, const base::Time& last_access_time, | 395 bool BaseFile::SetTime(Time last_access_time, Time last_modified_time) { |
355 const base::Time& last_modified_time) { | |
356 base::ThreadRestrictions::AssertIOAllowed(); | 396 base::ThreadRestrictions::AssertIOAllowed(); |
357 if (file < 0) | 397 DCHECK(IsValid()); |
358 return false; | |
359 | 398 |
360 timeval times[2]; | 399 timeval times[2]; |
361 times[0] = last_access_time.ToTimeVal(); | 400 times[0] = last_access_time.ToTimeVal(); |
362 times[1] = last_modified_time.ToTimeVal(); | 401 times[1] = last_modified_time.ToTimeVal(); |
363 | 402 |
364 return !CallFutimes(file, times); | 403 return !CallFutimes(file_, times); |
365 } | 404 } |
366 | 405 |
367 bool GetPlatformFileInfo(PlatformFile file, PlatformFileInfo* info) { | 406 bool BaseFile::GetInfo(BaseFileInfo* info) { |
368 if (!info) | 407 DCHECK(IsValid()); |
369 return false; | |
370 | 408 |
371 stat_wrapper_t file_info; | 409 stat_wrapper_t file_info; |
372 if (CallFstat(file, &file_info)) | 410 if (CallFstat(file_, &file_info)) |
373 return false; | 411 return false; |
374 | 412 |
375 info->is_directory = S_ISDIR(file_info.st_mode); | 413 info->is_directory = S_ISDIR(file_info.st_mode); |
376 info->is_symbolic_link = S_ISLNK(file_info.st_mode); | 414 info->is_symbolic_link = S_ISLNK(file_info.st_mode); |
377 info->size = file_info.st_size; | 415 info->size = file_info.st_size; |
378 | 416 |
379 #if defined(OS_LINUX) | 417 #if defined(OS_LINUX) |
380 const time_t last_modified_sec = file_info.st_mtim.tv_sec; | 418 const time_t last_modified_sec = file_info.st_mtim.tv_sec; |
381 const int64 last_modified_nsec = file_info.st_mtim.tv_nsec; | 419 const int64 last_modified_nsec = file_info.st_mtim.tv_nsec; |
382 const time_t last_accessed_sec = file_info.st_atim.tv_sec; | 420 const time_t last_accessed_sec = file_info.st_atim.tv_sec; |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
415 base::Time::FromTimeT(last_accessed_sec) + | 453 base::Time::FromTimeT(last_accessed_sec) + |
416 base::TimeDelta::FromMicroseconds(last_accessed_nsec / | 454 base::TimeDelta::FromMicroseconds(last_accessed_nsec / |
417 base::Time::kNanosecondsPerMicrosecond); | 455 base::Time::kNanosecondsPerMicrosecond); |
418 info->creation_time = | 456 info->creation_time = |
419 base::Time::FromTimeT(creation_time_sec) + | 457 base::Time::FromTimeT(creation_time_sec) + |
420 base::TimeDelta::FromMicroseconds(creation_time_nsec / | 458 base::TimeDelta::FromMicroseconds(creation_time_nsec / |
421 base::Time::kNanosecondsPerMicrosecond); | 459 base::Time::kNanosecondsPerMicrosecond); |
422 return true; | 460 return true; |
423 } | 461 } |
424 | 462 |
425 PlatformFileError LockPlatformFile(PlatformFile file) { | 463 BaseFileError BaseFile::Lock() { |
426 return CallFctnlFlock(file, true); | 464 return CallFctnlFlock(file_, true); |
427 } | 465 } |
428 | 466 |
429 PlatformFileError UnlockPlatformFile(PlatformFile file) { | 467 BaseFileError BaseFile::Unlock() { |
430 return CallFctnlFlock(file, false); | 468 return CallFctnlFlock(file_, false); |
431 } | 469 } |
432 | 470 |
433 PlatformFileError ErrnoToPlatformFileError(int saved_errno) { | 471 void BaseFile::SetPlatformFile(PlatformFile file) { |
434 switch (saved_errno) { | 472 DCHECK_EQ(file_, kInvalidPlatformFileValue); |
435 case EACCES: | 473 file_ = file; |
436 case EISDIR: | |
437 case EROFS: | |
438 case EPERM: | |
439 return PLATFORM_FILE_ERROR_ACCESS_DENIED; | |
440 #if !defined(OS_NACL) // ETXTBSY not defined by NaCl. | |
441 case ETXTBSY: | |
442 return PLATFORM_FILE_ERROR_IN_USE; | |
443 #endif | |
444 case EEXIST: | |
445 return PLATFORM_FILE_ERROR_EXISTS; | |
446 case ENOENT: | |
447 return PLATFORM_FILE_ERROR_NOT_FOUND; | |
448 case EMFILE: | |
449 return PLATFORM_FILE_ERROR_TOO_MANY_OPENED; | |
450 case ENOMEM: | |
451 return PLATFORM_FILE_ERROR_NO_MEMORY; | |
452 case ENOSPC: | |
453 return PLATFORM_FILE_ERROR_NO_SPACE; | |
454 case ENOTDIR: | |
455 return PLATFORM_FILE_ERROR_NOT_A_DIRECTORY; | |
456 default: | |
457 #if !defined(OS_NACL) // NaCl build has no metrics code. | |
458 UMA_HISTOGRAM_SPARSE_SLOWLY("PlatformFile.UnknownErrors.Posix", | |
459 saved_errno); | |
460 #endif | |
461 return PLATFORM_FILE_ERROR_FAILED; | |
462 } | |
463 } | 474 } |
464 | 475 |
465 } // namespace base | 476 } // namespace base |
OLD | NEW |