1 // Copyright 2015 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "components/filesystem/util.h"
14 #include "base/logging.h"
15 #include "base/strings/string_util.h"
16 #include "mojo/public/cpp/bindings/string.h"
18 namespace filesystem
{
20 Error
IsPathValid(const mojo::String
& path
) {
21 DCHECK(!path
.is_null());
22 if (!base::IsStringUTF8(path
.get()))
23 return ERROR_INVALID_ARGUMENT
;
24 if (path
.size() > 0 && path
[0] == '/')
25 return ERROR_PERMISSION_DENIED
;
29 Error
IsWhenceValid(Whence whence
) {
30 return (whence
== WHENCE_FROM_CURRENT
|| whence
== WHENCE_FROM_START
||
31 whence
== WHENCE_FROM_END
)
33 : ERROR_UNIMPLEMENTED
;
36 Error
IsOffsetValid(int64_t offset
) {
37 return (offset
>= std::numeric_limits
<off_t
>::min() &&
38 offset
<= std::numeric_limits
<off_t
>::max())
43 Error
ErrnoToError(int errno_value
) {
48 int WhenceToStandardWhence(Whence whence
) {
49 DCHECK_EQ(IsWhenceValid(whence
), ERROR_OK
);
51 case WHENCE_FROM_CURRENT
:
53 case WHENCE_FROM_START
:
62 Error
TimespecToStandardTimespec(const Timespec
* in
, struct timespec
* out
) {
65 out
->tv_nsec
= UTIME_OMIT
;
69 static_assert(sizeof(int64_t) >= sizeof(time_t), "whoa, time_t is huge");
70 if (in
->seconds
< std::numeric_limits
<time_t>::min() ||
71 in
->seconds
> std::numeric_limits
<time_t>::max())
72 return ERROR_OUT_OF_RANGE
;
74 if (in
->nanoseconds
< 0 || in
->nanoseconds
>= 1000000000)
75 return ERROR_INVALID_ARGUMENT
;
77 out
->tv_sec
= static_cast<time_t>(in
->seconds
);
78 out
->tv_nsec
= static_cast<long>(in
->nanoseconds
);
82 Error
TimespecOrNowToStandardTimespec(const TimespecOrNow
* in
,
83 struct timespec
* out
) {
86 out
->tv_nsec
= UTIME_OMIT
;
91 if (!in
->timespec
.is_null())
92 return ERROR_INVALID_ARGUMENT
;
94 out
->tv_nsec
= UTIME_NOW
;
98 return TimespecToStandardTimespec(in
->timespec
.get(), out
);
101 Error
ValidateOpenFlags(uint32_t open_flags
, bool is_directory
) {
102 // Treat unknown flags as "unimplemented".
104 ~(kOpenFlagRead
| kOpenFlagWrite
| kOpenFlagCreate
| kOpenFlagExclusive
|
105 kOpenFlagAppend
| kOpenFlagTruncate
)))
106 return ERROR_UNIMPLEMENTED
;
108 // At least one of |kOpenFlagRead| or |kOpenFlagWrite| must be set.
109 if (!(open_flags
& (kOpenFlagRead
| kOpenFlagWrite
)))
110 return ERROR_INVALID_ARGUMENT
;
112 // |kOpenFlagCreate| requires |kOpenFlagWrite|.
113 if ((open_flags
& kOpenFlagCreate
) && !(open_flags
& kOpenFlagWrite
))
114 return ERROR_INVALID_ARGUMENT
;
116 // |kOpenFlagExclusive| requires |kOpenFlagCreate|.
117 if ((open_flags
& kOpenFlagExclusive
) && !(open_flags
& kOpenFlagCreate
))
118 return ERROR_INVALID_ARGUMENT
;
121 // Check that file-only flags aren't set.
122 if ((open_flags
& (kOpenFlagAppend
| kOpenFlagTruncate
)))
123 return ERROR_INVALID_ARGUMENT
;
129 // |kOpenFlagAppend| requires |kOpenFlagWrite|.
130 if ((open_flags
& kOpenFlagAppend
) && !(open_flags
& kOpenFlagWrite
))
131 return ERROR_INVALID_ARGUMENT
;
133 // |kOpenFlagTruncate| requires |kOpenFlagWrite|.
134 if ((open_flags
& kOpenFlagTruncate
) && !(open_flags
& kOpenFlagWrite
))
135 return ERROR_INVALID_ARGUMENT
;
140 Error
ValidateDeleteFlags(uint32_t delete_flags
) {
141 // Treat unknown flags as "unimplemented".
143 ~(kDeleteFlagFileOnly
| kDeleteFlagDirectoryOnly
|
144 kDeleteFlagRecursive
)))
145 return ERROR_UNIMPLEMENTED
;
147 // Only one of the three currently-defined flags may be set.
148 if ((delete_flags
& kDeleteFlagFileOnly
) &&
149 (delete_flags
& (kDeleteFlagDirectoryOnly
| kDeleteFlagRecursive
)))
150 return ERROR_INVALID_ARGUMENT
;
151 if ((delete_flags
& kDeleteFlagDirectoryOnly
) &&
152 (delete_flags
& (kDeleteFlagFileOnly
| kDeleteFlagRecursive
)))
153 return ERROR_INVALID_ARGUMENT
;
154 if ((delete_flags
& kDeleteFlagRecursive
) &&
155 (delete_flags
& (kDeleteFlagFileOnly
| kDeleteFlagDirectoryOnly
)))
156 return ERROR_INVALID_ARGUMENT
;
161 } // namespace filesystem