Flutter Engine
The Flutter Engine
Loading...
Searching...
No Matches
file.h
Go to the documentation of this file.
1// Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file
2// for details. All rights reserved. Use of this source code is governed by a
3// BSD-style license that can be found in the LICENSE file.
4
5#ifndef RUNTIME_BIN_FILE_H_
6#define RUNTIME_BIN_FILE_H_
7
8#include <stdio.h>
9#include <stdlib.h>
10#include <string.h>
11#include <sys/types.h>
12
13#include "bin/builtin.h"
14#include "bin/dartutils.h"
15#include "bin/namespace.h"
17#include "platform/syslog.h"
18#include "platform/utils.h"
19
20namespace dart {
21namespace bin {
22
23// Forward declaration.
24class FileHandle;
25
27 public:
28 MappedMemory(void* address, intptr_t size, bool should_unmap = true)
29 : should_unmap_(should_unmap), address_(address), size_(size) {}
31 if (should_unmap_) Unmap();
32 }
33
34 void* address() const { return address_; }
35 intptr_t size() const { return size_; }
36 uword start() const { return reinterpret_cast<uword>(address()); }
37
38 void Leak() { should_unmap_ = false; }
39
40 private:
41 void Unmap();
42
43 // False for mappings which reside inside another, and will be removed when
44 // the outer mapping is removed.
45 bool should_unmap_;
46
47 void* address_;
48 intptr_t size_;
49
51};
52
53class File : public ReferenceCounted<File> {
54 public:
63
64 // These values have to be kept in sync with the mode values of
65 // FileMode.READ, FileMode.WRITE, FileMode.APPEND,
66 // FileMode.WRITE_ONLY and FileMode.WRITE_ONLY_APPEND in file.dart.
74
75 enum Type {
79 kIsSock = 3, // Unix Domain Socket.
80 kIsPipe = 4, // FIFO/Pipe.
82 };
83
84 enum Identical { kIdentical = 0, kDifferent = 1, kError = 2 };
85
87 // These match the constants in stdio.dart.
89 kPipe = 1,
90 kFile = 2,
92 kOther = 4,
93 kTypeError = 5
94 };
95
96 enum FileStat {
97 // These match the constants in FileStat in file_system_entity.dart.
98 kType = 0,
102 kMode = 4,
103 kSize = 5,
104 kStatSize = 6
105 };
106
107 enum LockType {
108 // These match the constants in FileStat in file_impl.dart.
115 kLockMax = 4
116 };
117
118 intptr_t GetFD();
119
125
126 /// Maps or copies the file into memory.
127 ///
128 /// 'position' and 'length' should be page-aligned.
129 ///
130 /// If 'start' is zero, allocates virtual memory for the mapping. When the
131 /// returned 'MappedMemory' is destroyed, the mapping is removed.
132 ///
133 /// If 'start' is non-zero, it must point within a suitably sized existing
134 /// mapping. The returned 'MappedMemory' will not remove the mapping when it
135 /// is destroyed; rather, the mapping will be removed when the enclosing
136 /// mapping is removed. This mode is not supported on Fuchsia.
137 ///
138 /// If 'type' is 'kReadWrite', writes to the mapping are *not* copied back to
139 /// the file.
140 ///
141 /// 'position' + 'length' may be larger than the file size. In this case, the
142 /// extra memory is zero-filled.
144 int64_t position,
145 int64_t length,
146 void* start = nullptr);
147
148 // Read at most 'num_bytes' from the file. It may read less than 'num_bytes'
149 // even when EOF is not encountered. If no data is available then `Read`
150 // will block waiting for input (e.g. if the file represents a pipe that
151 // contains no unread data). A positive return value indicates the number of
152 // bytes read. Zero indicates an attempt to read past the end-of-file. -1
153 // indicates an error.
154 int64_t Read(void* buffer, int64_t num_bytes);
155 // Attempt to write 'num_bytes' bytes from 'buffer'. It returns the number
156 // of bytes written.
157 int64_t Write(const void* buffer, int64_t num_bytes);
158
159 // ReadFully and WriteFully do attempt to transfer num_bytes to/from
160 // the buffer. In the event of short accesses they will loop internally until
161 // the whole buffer has been transferred or an error occurs. If an error
162 // occurred the result will be set to false.
163 bool ReadFully(void* buffer, int64_t num_bytes);
164 bool WriteFully(const void* buffer, int64_t num_bytes);
165 bool WriteByte(uint8_t byte) { return WriteFully(&byte, 1); }
166
167 bool Print(const char* format, ...) PRINTF_ATTRIBUTE(2, 3) {
168 va_list args;
172 return result;
173 }
174 bool VPrint(const char* format, va_list args);
175
176 // Get the length of the file. Returns a negative value if the length cannot
177 // be determined (e.g. not seekable device).
178 int64_t Length();
179
180 // Get the current position in the file.
181 // Returns a negative value if position cannot be determined.
182 int64_t Position();
183
184 // Set the byte position in the file.
185 bool SetPosition(int64_t position);
186
187 // Truncate (or extend) the file to the given length in bytes.
188 bool Truncate(int64_t length);
189
190 // Flush contents of file.
191 bool Flush();
192
193 // Lock range of a file.
194 bool Lock(LockType lock, int64_t start, int64_t end);
195
196 // Returns whether the file has been closed.
197 bool IsClosed();
198
199 // Calls the platform-specific functions to close the file.
200 void Close();
201
202 // Returns the finalizable handle for the File's Dart wrapper.
204 return finalizable_handle_;
205 }
206
207 // Set the finalizable handle for the File's Dart wrapper.
209 ASSERT(finalizable_handle_ == nullptr);
210 finalizable_handle_ = handle;
211 }
212
213 // Deletes the finalizable handle for the File's Dart wrapper. Call
214 // when the file is explicitly closed and the finalizer is no longer
215 // needed.
217 Dart_DeleteFinalizableHandle(finalizable_handle_, strong_ref);
218 finalizable_handle_ = nullptr;
219 }
220
221 // Open the file with the given path. The file is always opened for
222 // reading. If mode contains kWrite the file is opened for both
223 // reading and writing. If mode contains kWrite and the file does
224 // not exist the file is created. The file is truncated to length 0 if
225 // mode contains kTruncate.
226 static File* Open(Namespace* namespc, const char* path, FileOpenMode mode);
227
228 // Same as [File::Open], but attempts to convert uri to path before opening
229 // the file. If conversion fails, uri is treated as a path.
230 static File* OpenUri(Namespace* namespc, const char* uri, FileOpenMode mode);
231
232 // Attempts to convert the given [uri] to a file path.
233 static Utils::CStringUniquePtr UriToPath(const char* uri);
234
235 // Create a file object for the specified stdio file descriptor
236 // (stdin, stout or stderr).
237 static File* OpenStdio(int fd);
238
239 static File* OpenFD(int fd);
240
241 static bool Exists(Namespace* namespc, const char* path);
242 static bool ExistsUri(Namespace* namespc, const char* uri);
243 static bool Create(Namespace* namespc, const char* path, bool exclusive);
244 static bool CreateLink(Namespace* namespc,
245 const char* path,
246 const char* target);
247 static bool CreatePipe(Namespace* namespc, File** readPipe, File** writePipe);
248 static bool Delete(Namespace* namespc, const char* path);
249 static bool DeleteLink(Namespace* namespc, const char* path);
250 static bool Rename(Namespace* namespc,
251 const char* old_path,
252 const char* new_path);
253 static bool RenameLink(Namespace* namespc,
254 const char* old_path,
255 const char* new_path);
256 static bool Copy(Namespace* namespc,
257 const char* old_path,
258 const char* new_path);
259 static int64_t LengthFromPath(Namespace* namespc, const char* path);
260 static void Stat(Namespace* namespc, const char* path, int64_t* data);
261 static time_t LastModified(Namespace* namespc, const char* path);
262 static bool SetLastModified(Namespace* namespc,
263 const char* path,
264 int64_t millis);
265 static time_t LastAccessed(Namespace* namespc, const char* path);
266 static bool SetLastAccessed(Namespace* namespc,
267 const char* path,
268 int64_t millis);
269 static bool IsAbsolutePath(const char* path);
270 static const char* PathSeparator();
271 static const char* StringEscapedPathSeparator();
272#if defined(DART_HOST_OS_WINDOWS)
273 static Type GetType(const wchar_t* path, bool follow_links);
274#endif
275 static Type GetType(Namespace* namespc, const char* path, bool follow_links);
277 const char* file_1,
278 Namespace* namespc_2,
279 const char* file_2);
281
282 // LinkTarget, GetCanonicalPath, and ReadLink may call Dart_ScopeAllocate.
283 // If dest and its size are provided, Dart String will not be created.
284 // The result will be populated into dest.
285 static const char* LinkTarget(Namespace* namespc,
286 const char* pathname,
287 char* dest = nullptr,
288 int dest_size = 0);
289 static const char* GetCanonicalPath(Namespace* namespc,
290 const char* path,
291 char* dest = nullptr,
292 int dest_size = 0);
293 // Link LinkTarget, but pathname must be absolute.
294 static const char* ReadLink(const char* pathname);
295 static intptr_t ReadLinkInto(const char* pathname,
296 char* result,
297 size_t result_size);
298
299 // Cleans an input path, transforming it to out, according to the rules
300 // defined by "Lexical File Names in Plan 9 or Getting Dot-Dot Right",
301 // accessible at: https://9p.io/sys/doc/lexnames.html.
302 // Returns -1 if out isn't big enough, and the length of out otherwise.
303 static intptr_t CleanUnixPath(const char* in, char* out, intptr_t outlen);
304
306
307 static CObject* ExistsRequest(const CObjectArray& request);
308 static CObject* CreateRequest(const CObjectArray& request);
309 static CObject* CreatePipeRequest(const CObjectArray& request);
310 static CObject* DeleteRequest(const CObjectArray& request);
311 static CObject* RenameRequest(const CObjectArray& request);
312 static CObject* CopyRequest(const CObjectArray& request);
313 static CObject* OpenRequest(const CObjectArray& request);
314 static CObject* ResolveSymbolicLinksRequest(const CObjectArray& request);
315 static CObject* CloseRequest(const CObjectArray& request);
316 static CObject* PositionRequest(const CObjectArray& request);
317 static CObject* SetPositionRequest(const CObjectArray& request);
318 static CObject* TruncateRequest(const CObjectArray& request);
319 static CObject* LengthRequest(const CObjectArray& request);
320 static CObject* LengthFromPathRequest(const CObjectArray& request);
321 static CObject* LastModifiedRequest(const CObjectArray& request);
322 static CObject* SetLastModifiedRequest(const CObjectArray& request);
323 static CObject* LastAccessedRequest(const CObjectArray& request);
324 static CObject* SetLastAccessedRequest(const CObjectArray& request);
325 static CObject* FlushRequest(const CObjectArray& request);
326 static CObject* ReadByteRequest(const CObjectArray& request);
327 static CObject* WriteByteRequest(const CObjectArray& request);
328 static CObject* ReadRequest(const CObjectArray& request);
329 static CObject* ReadIntoRequest(const CObjectArray& request);
330 static CObject* WriteFromRequest(const CObjectArray& request);
331 static CObject* CreateLinkRequest(const CObjectArray& request);
332 static CObject* DeleteLinkRequest(const CObjectArray& request);
333 static CObject* RenameLinkRequest(const CObjectArray& request);
334 static CObject* LinkTargetRequest(const CObjectArray& request);
335 static CObject* TypeRequest(const CObjectArray& request);
336 static CObject* IdenticalRequest(const CObjectArray& request);
337 static CObject* StatRequest(const CObjectArray& request);
338 static CObject* LockRequest(const CObjectArray& request);
339
340 private:
341 explicit File(FileHandle* handle)
342 : ReferenceCounted(), handle_(handle), finalizable_handle_(nullptr) {}
343
344 ~File();
345
346 static File* FileOpenW(const wchar_t* system_name, FileOpenMode mode);
347
348 static constexpr int kClosedFd = -1;
349
350 // FileHandle is an OS specific class which stores data about the file.
351 FileHandle* handle_; // OS specific handle for the file.
352
353 // We retain the finalizable handle because we can do cleanup eagerly when
354 // Dart code calls closeSync(). In that case, we delete the finalizable
355 // handle so that the finalizer doesn't run.
356 Dart_FinalizableHandle finalizable_handle_;
357
358 friend class ReferenceCounted<File>;
360};
361
363 public:
364 explicit UriDecoder(const char* uri);
365 ~UriDecoder();
366
367 const char* decoded() const { return decoded_; }
368
369 private:
370 bool HexCharPairToByte(const char* pch, char* dest);
371
372 char* decoded_;
373 const char* uri_;
374
376};
377
378} // namespace bin
379} // namespace dart
380
381#endif // RUNTIME_BIN_FILE_H_
std::unique_ptr< char, decltype(std::free) * > CStringUniquePtr
Definition utils.h:644
static bool CreatePipe(Namespace *namespc, File **readPipe, File **writePipe)
static CObject * PositionRequest(const CObjectArray &request)
Definition file.cc:918
static CObject * OpenRequest(const CObjectArray &request)
Definition file.cc:808
static CObject * TypeRequest(const CObjectArray &request)
Definition file.cc:1340
static CObject * LengthFromPathRequest(const CObjectArray &request)
Definition file.cc:985
static bool DeleteLink(Namespace *namespc, const char *path)
static CObject * FlushRequest(const CObjectArray &request)
Definition file.cc:1077
static bool IsAbsolutePath(const char *path)
static CObject * TruncateRequest(const CObjectArray &request)
Definition file.cc:950
static CObject * DeleteRequest(const CObjectArray &request)
Definition file.cc:832
static CObject * ReadIntoRequest(const CObjectArray &request)
Definition file.cc:1163
MappedMemory * Map(MapType type, int64_t position, int64_t length, void *start=nullptr)
static const char * GetCanonicalPath(Namespace *namespc, const char *path, char *dest=nullptr, int dest_size=0)
int64_t Position()
static CObject * ReadByteRequest(const CObjectArray &request)
Definition file.cc:1089
static CObject * RenameRequest(const CObjectArray &request)
Definition file.cc:847
static CObject * ExistsRequest(const CObjectArray &request)
Definition file.cc:751
static CObject * SetLastModifiedRequest(const CObjectArray &request)
Definition file.cc:1059
int64_t Read(void *buffer, int64_t num_bytes)
static bool SetLastAccessed(Namespace *namespc, const char *path, int64_t millis)
static Utils::CStringUniquePtr UriToPath(const char *uri)
static File * OpenUri(Namespace *namespc, const char *uri, FileOpenMode mode)
static CObject * StatRequest(const CObjectArray &request)
Definition file.cc:1376
@ kDoesNotExist
Definition file.h:81
static CObject * CopyRequest(const CObjectArray &request)
Definition file.cc:865
static bool SetLastModified(Namespace *namespc, const char *path, int64_t millis)
static CObject * SetPositionRequest(const CObjectArray &request)
Definition file.cc:934
static time_t LastModified(Namespace *namespc, const char *path)
static void Stat(Namespace *namespc, const char *path, int64_t *data)
static const char * PathSeparator()
static bool Create(Namespace *namespc, const char *path, bool exclusive)
bool VPrint(const char *format, va_list args)
static CObject * LinkTargetRequest(const CObjectArray &request)
Definition file.cc:1322
static bool Rename(Namespace *namespc, const char *old_path, const char *new_path)
static CObject * WriteFromRequest(const CObjectArray &request)
Definition file.cc:1227
static bool Delete(Namespace *namespc, const char *path)
static const char * StringEscapedPathSeparator()
bool WriteFully(const void *buffer, int64_t num_bytes)
static CObject * DeleteLinkRequest(const CObjectArray &request)
Definition file.cc:1288
static CObject * ReadRequest(const CObjectArray &request)
Definition file.cc:1128
@ kDartWriteOnlyAppend
Definition file.h:72
@ kDartWriteOnly
Definition file.h:71
static CObject * RenameLinkRequest(const CObjectArray &request)
Definition file.cc:1304
static int64_t LengthFromPath(Namespace *namespc, const char *path)
bool ReadFully(void *buffer, int64_t num_bytes)
static CObject * CreateLinkRequest(const CObjectArray &request)
Definition file.cc:1270
static bool Copy(Namespace *namespc, const char *old_path, const char *new_path)
static time_t LastAccessed(Namespace *namespc, const char *path)
intptr_t GetFD()
bool WriteByte(uint8_t byte)
Definition file.h:165
static intptr_t CleanUnixPath(const char *in, char *out, intptr_t outlen)
Definition file.cc:655
static CObject * IdenticalRequest(const CObjectArray &request)
Definition file.cc:1357
bool result
Definition file.h:170
int64_t Write(const void *buffer, int64_t num_bytes)
static CObject * LengthRequest(const CObjectArray &request)
Definition file.cc:969
return result
Definition file.h:172
static CObject * WriteByteRequest(const CObjectArray &request)
Definition file.cc:1109
static bool Exists(Namespace *namespc, const char *path)
static File * Open(Namespace *namespc, const char *path, FileOpenMode mode)
bool Lock(LockType lock, int64_t start, int64_t end)
static FileOpenMode DartModeToFileMode(DartFileOpenMode mode)
static CObject * CreateRequest(const CObjectArray &request)
Definition file.cc:765
void SetFinalizableHandle(Dart_FinalizableHandle handle)
Definition file.h:208
static CObject * LastAccessedRequest(const CObjectArray &request)
Definition file.cc:1003
static CObject * ResolveSymbolicLinksRequest(const CObjectArray &request)
Definition file.cc:883
static const char * ReadLink(const char *pathname)
bool SetPosition(int64_t position)
static Identical AreIdentical(Namespace *namespc_1, const char *file_1, Namespace *namespc_2, const char *file_2)
Dart_FinalizableHandle FinalizableHandle() const
Definition file.h:203
int64_t Length()
void DeleteFinalizableHandle(Dart_Isolate isolate, Dart_Handle strong_ref)
Definition file.h:216
static File * OpenFD(int fd)
static const char * LinkTarget(Namespace *namespc, const char *pathname, char *dest=nullptr, int dest_size=0)
@ kLockBlockingShared
Definition file.h:113
@ kLockBlockingExclusive
Definition file.h:114
static bool CreateLink(Namespace *namespc, const char *path, const char *target)
static CObject * CreatePipeRequest(const CObjectArray &request)
Definition file.cc:783
static bool ExistsUri(Namespace *namespc, const char *uri)
@ kWriteTruncate
Definition file.h:60
@ kWriteOnlyTruncate
Definition file.h:61
static File * OpenStdio(int fd)
static StdioHandleType GetStdioHandleType(int fd)
static CObject * SetLastAccessedRequest(const CObjectArray &request)
Definition file.cc:1022
static Type GetType(Namespace *namespc, const char *path, bool follow_links)
bool Truncate(int64_t length)
static CObject * CloseRequest(const CObjectArray &request)
Definition file.cc:901
static CObject * LockRequest(const CObjectArray &request)
Definition file.cc:1401
bool va_start(args, format)
bool Print(const char *format,...) PRINTF_ATTRIBUTE(2
static intptr_t ReadLinkInto(const char *pathname, char *result, size_t result_size)
static CObject * LastModifiedRequest(const CObjectArray &request)
Definition file.cc:1040
static bool RenameLink(Namespace *namespc, const char *old_path, const char *new_path)
void * address() const
Definition file.h:34
uword start() const
Definition file.h:36
intptr_t size() const
Definition file.h:35
MappedMemory(void *address, intptr_t size, bool should_unmap=true)
Definition file.h:28
const char * decoded() const
Definition file.h:367
struct _Dart_Handle * Dart_Handle
Definition dart_api.h:258
struct _Dart_Isolate * Dart_Isolate
Definition dart_api.h:88
struct _Dart_FinalizableHandle * Dart_FinalizableHandle
Definition dart_api.h:261
#define ASSERT(E)
glong glong end
G_BEGIN_DECLS G_MODULE_EXPORT FlValue * args
static const uint8_t buffer[]
uint32_t uint32_t * format
uint32_t * target
size_t length
uintptr_t uword
Definition globals.h:501
DART_EXPORT void Dart_DeleteFinalizableHandle(Dart_FinalizableHandle object, Dart_Handle strong_ref_to_object)
static int8_t data[kExtLength]
#define PRINTF_ATTRIBUTE(string_index, first_to_check)
Definition globals.h:697
#define DISALLOW_COPY_AND_ASSIGN(TypeName)
Definition globals.h:581