2 * innotek Portable Runtime - File I/O.
6 * Copyright (C) 2006-2007 innotek GmbH
8 * This file is part of VirtualBox Open Source Edition (OSE), as
9 * available from http://www.virtualbox.org. This file is free software;
10 * you can redistribute it and/or modify it under the terms of the GNU
11 * General Public License as published by the Free Software Foundation,
12 * in version 2 as it comes in the "COPYING" file of the VirtualBox OSE
13 * distribution. VirtualBox OSE is distributed in the hope that it will
14 * be useful, but WITHOUT ANY WARRANTY of any kind.
17 #ifndef ___iprt_file_h
18 #define ___iprt_file_h
22 #include "const_defines.h"
26 /** @todo rename this file to iprt/file.h */
30 /** @defgroup grp_rt_fileio RTFile - File I/O
35 /** Platform specific text line break.
36 * @deprecated Use text I/O streams and '\\n'. See iprt/stream.h. */
37 #if defined(RT_OS_OS2) || defined(RT_OS_WINDOWS)
38 # define RTFILE_LINEFEED "\r\n"
40 # define RTFILE_LINEFEED "\n"
46 /** Open the file with read access. */
47 #define RTFILE_O_READ 0x00000001
48 /** Open the file with write access. */
49 #define RTFILE_O_WRITE 0x00000002
50 /** Open the file with read & write access. */
51 #define RTFILE_O_READWRITE 0x00000003
52 /** The file access mask.
53 * @remark The value 0 is invalid. */
54 #define RTFILE_O_ACCESS_MASK 0x00000003
56 /** Sharing mode: deny none (the default mode). */
57 #define RTFILE_O_DENY_NONE 0x00000000
58 /** Sharing mode: deny read. */
59 #define RTFILE_O_DENY_READ 0x00000010
60 /** Sharing mode: deny write. */
61 #define RTFILE_O_DENY_WRITE 0x00000020
62 /** Sharing mode: deny read and write. */
63 #define RTFILE_O_DENY_READWRITE 0x00000030
64 /** Sharing mode: deny all. */
65 #define RTFILE_O_DENY_ALL RTFILE_O_DENY_READWRITE
66 /** Sharing mode: do NOT deny delete (NT).
67 * @remark This might not be implemented on all platforms,
68 * and will be defaulted & ignored on those.
70 #define RTFILE_O_DENY_NOT_DELETE 0x00000040
71 /** Sharing mode mask. */
72 #define RTFILE_O_DENY_MASK 0x00000070
74 /** Action: Open an existing file (the default action). */
75 #define RTFILE_O_OPEN 0x00000000
76 /** Action: Create a new file or open an existing one. */
77 #define RTFILE_O_OPEN_CREATE 0x00000100
78 /** Action: Create a new a file. */
79 #define RTFILE_O_CREATE 0x00000200
80 /** Action: Create a new file or replace an existing one. */
81 #define RTFILE_O_CREATE_REPLACE 0x00000300
83 #define RTFILE_O_ACTION_MASK 0x00000300
85 /** Turns off indexing of files on Windows hosts, *CREATE* only.
86 * @remark This might not be implemented on all platforms,
87 * and will be ignored on those.
89 #define RTFILE_O_NOT_CONTENT_INDEXED 0x00000800
90 /** Truncate the file.
91 * @remark This will not truncate files opened for read-only.
92 * @remark The trunction doesn't have to be atomically, so anyone
93 * else opening the file may be racing us. The caller is
94 * responsible for not causing this race. */
95 #define RTFILE_O_TRUNCATE 0x00001000
96 /** Make the handle inheritable on RTProcessCreate(/exec). */
97 #define RTFILE_O_INHERIT 0x00002000
98 /** Open file in non-blocking mode - non-portable.
99 * @remark This flag may not be supported on all platforms, in which
100 * case it's considered an invalid parameter.
102 #define RTFILE_O_NON_BLOCK 0x00004000
103 /** Write through directly to disk. Workaround to avoid iSCSI
104 * initiator deadlocks on Windows hosts.
105 * @remark This might not be implemented on all platforms,
106 * and will be ignored on those.
108 #define RTFILE_O_WRITE_THROUGH 0x00008000
110 /** Mask of all valid flags.
111 * @remark This doesn't validate the access mode properly.
113 #define RTFILE_O_VALID_MASK 0x0000FB73
119 * Force the use of open flags for all files opened after the setting is
120 * changed. The caller is responsible for not causing races with RTFileOpen().
122 * @returns iprt status code.
123 * @param fOpenForAccess Access mode to which the set/mask settings apply.
124 * @param fSet Open flags to be forced set.
125 * @param fMask Open flags to be masked out.
127 int RTFileSetForceFlags(unsigned fOpenForAccess
, unsigned fSet
, unsigned fMask
);
132 * @returns iprt status code.
133 * @param pFile Where to store the handle to the opened file.
134 * @param pszFilename Path to the file which is to be opened. (UTF-8)
135 * @param fOpen Open flags, i.e a combination of the RTFILE_O_* defines.
137 int RTFileOpen(PRTFILE pFile
, const char *pszFilename
, unsigned fOpen
);
140 * Close a file opened by RTFileOpen().
142 * @returns iprt status code.
143 * @param File The file handle to close.
145 int RTFileClose(RTFILE File
);
150 * @returns iprt status code.
151 * @param pszFilename Path to the file which is to be deleted. (UTF-8)
152 * @todo This is a RTPath api!
154 int RTFileDelete(const char *pszFilename
);
156 /** @name Seek flags.
158 /** Seek from the start of the file. */
159 #define RTFILE_SEEK_BEGIN 0x00
160 /** Seek from the current file position. */
161 #define RTFILE_SEEK_CURRENT 0x01
162 /** Seek from the end of the file. */
163 #define RTFILE_SEEK_END 0x02
165 #define RTFILE_SEEK_FIRST RTFILE_SEEK_BEGIN
167 #define RTFILE_SEEK_LAST RTFILE_SEEK_END
172 * Changes the read & write position in a file.
174 * @returns iprt status code.
175 * @param File Handle to the file.
176 * @param offSeek Offset to seek.
177 * @param uMethod Seek method, i.e. one of the RTFILE_SEEK_* defines.
178 * @param poffActual Where to store the new file position.
181 int RTFileSeek(RTFILE File
, int64_t offSeek
, unsigned uMethod
, uint64_t *poffActual
);
184 * Read bytes from a file.
186 * @returns iprt status code.
187 * @param File Handle to the file.
188 * @param pvBuf Where to put the bytes we read.
189 * @param cbToRead How much to read.
190 * @param *pcbRead How much we actually read .
191 * If NULL an error will be returned for a partial read.
193 int RTFileRead(RTFILE File
, void *pvBuf
, size_t cbToRead
, size_t *pcbRead
);
196 * Read bytes from a file at a given offset.
197 * This function may modify the file position.
199 * @returns iprt status code.
200 * @param File Handle to the file.
201 * @param off Where to read.
202 * @param pvBuf Where to put the bytes we read.
203 * @param cbToRead How much to read.
204 * @param *pcbRead How much we actually read .
205 * If NULL an error will be returned for a partial read.
207 int RTFileReadAt(RTFILE File
, RTFOFF off
, void *pvBuf
, size_t cbToRead
, size_t *pcbRead
);
210 * Write bytes to a file.
212 * @returns iprt status code.
213 * @param File Handle to the file.
214 * @param pvBuf What to write.
215 * @param cbToWrite How much to write.
216 * @param *pcbWritten How much we actually wrote.
217 * If NULL an error will be returned for a partial write.
219 int RTFileWrite(RTFILE File
, const void *pvBuf
, size_t cbToWrite
, size_t *pcbWritten
);
222 * Write bytes to a file at a given offset.
223 * This function may modify the file position.
225 * @returns iprt status code.
226 * @param File Handle to the file.
227 * @param off Where to write.
228 * @param pvBuf What to write.
229 * @param cbToWrite How much to write.
230 * @param *pcbWritten How much we actually wrote.
231 * If NULL an error will be returned for a partial write.
233 int RTFileWriteAt(RTFILE File
, RTFOFF off
, const void *pvBuf
, size_t cbToWrite
, size_t *pcbWritten
);
236 * Flushes the buffers for the specified file.
238 * @returns iprt status code.
239 * @param File Handle to the file.
241 int RTFileFlush(RTFILE File
);
244 * Set the size of the file.
246 * @returns iprt status code.
247 * @param File Handle to the file.
248 * @param cbSize The new file size.
250 int RTFileSetSize(RTFILE File
, uint64_t cbSize
);
253 * Query the size of the file.
255 * @returns iprt status code.
256 * @param File Handle to the file.
257 * @param pcbSize Where to store the filesize.
259 int RTFileGetSize(RTFILE File
, uint64_t *pcbSize
);
262 * Gets the current file position.
264 * @returns File offset.
265 * @returns ~0UUL on failure.
266 * @param File Handle to the file.
268 uint64_t RTFileTell(RTFILE File
);
271 * Checks if the supplied handle is valid.
273 * @returns true if valid.
274 * @returns false if invalid.
275 * @param File The file handle
277 bool RTFileIsValid(RTFILE File
);
282 * @returns VERR_ALREADY_EXISTS if the destination file exists.
283 * @returns VBox Status code.
285 * @param pszSrc The path to the source file.
286 * @param pszDst The path to the destination file.
287 * This file will be created.
289 int RTFileCopy(const char *pszSrc
, const char *pszDst
);
292 * Copies a file given the handles to both files.
294 * @returns VBox Status code.
296 * @param FileSrc The source file. The file position is unaltered.
297 * @param FileDst The destination file.
298 * On successful returns the file position is at the end of the file.
299 * On failures the file position and size is undefined.
301 int RTFileCopyByHandles(RTFILE FileSrc
, RTFILE FileDst
);
306 * @returns VERR_ALREADY_EXISTS if the destination file exists.
307 * @returns VBox Status code.
309 * @param pszSrc The path to the source file.
310 * @param pszDst The path to the destination file.
311 * This file will be created.
312 * @param pfnProgress Pointer to callback function for reporting progress.
313 * @param pvUser User argument to pass to pfnProgress along with the completion precentage.
315 int RTFileCopyEx(const char *pszSrc
, const char *pszDst
, PFNRTPROGRESS pfnProgress
, void *pvUser
);
318 * Copies a file given the handles to both files and
319 * provide progress callbacks.
321 * @returns IPRT status code.
323 * @param FileSrc The source file. The file position is unaltered.
324 * @param FileDst The destination file.
325 * On successful returns the file position is at the end of the file.
326 * On failures the file position and size is undefined.
327 * @param pfnProgress Pointer to callback function for reporting progress.
328 * @param pvUser User argument to pass to pfnProgress along with the completion precentage.
330 int RTFileCopyByHandlesEx(RTFILE FileSrc
, RTFILE FileDst
, PFNRTPROGRESS pfnProgress
, void *pvUser
);
335 * Identical to RTPathRename except that it will ensure that the source is not a directory.
337 * @returns IPRT status code.
338 * @returns VERR_ALREADY_EXISTS if the destination file exists.
340 * @param pszSrc The path to the source file.
341 * @param pszDst The path to the destination file.
342 * This file will be created.
343 * @param fRename See RTPathRename.
345 int RTFileRename(const char *pszSrc
, const char *pszDst
, unsigned fRename
);
348 /** @name RTFileMove flags (bit masks).
350 /** Replace destination file if present. */
351 #define RTFILEMOVE_FLAGS_REPLACE 0x1
357 * RTFileMove differs from RTFileRename in that it works across volumes.
359 * @returns IPRT status code.
360 * @returns VERR_ALREADY_EXISTS if the destination file exists.
362 * @param pszSrc The path to the source file.
363 * @param pszDst The path to the destination file.
364 * This file will be created.
365 * @param fMove A combination of the RTFILEMOVE_* flags.
367 int RTFileMove(const char *pszSrc
, const char *pszDst
, unsigned fMove
);
370 /** @page pg_rt_filelock RT File locking API description
372 * File locking general rules:
374 * Region to lock or unlock can be located beyond the end of file, this can be used for
376 * Read (or Shared) locks can be acquired held by an unlimited number of processes at the
377 * same time, but a Write (or Exclusive) lock can only be acquired by one process, and
378 * cannot coexist with a Shared lock. To acquire a Read lock, a process must wait until
379 * there are no processes holding any Write locks. To acquire a Write lock, a process must
380 * wait until there are no processes holding either kind of lock.
381 * By default, RTFileLock and RTFileChangeLock calls returns error immediately if the lock
382 * can't be acquired due to conflict with other locks, however they can be called in wait mode.
384 * Differences in implementation:
386 * Win32, OS/2: Locking is mandatory, since locks are enforced by the operating system.
387 * I.e. when file region is locked in Read mode, any write in it will fail; in case of Write
388 * lock - region can be readed and writed only by lock's owner.
390 * Win32: File size change (RTFileSetSize) is not controlled by locking at all (!) in the
391 * operation system. Also see comments to RTFileChangeLock API call.
393 * Linux/Posix: By default locks in Unixes are advisory. This means that cooperating processes
394 * may use locks to coordonate access to a file between themselves, but programs are also free
395 * to ignore locks and access the file in any way they choose to.
397 * Additional reading:
398 * http://en.wikipedia.org/wiki/File_locking
399 * http://unixhelp.ed.ac.uk/CGI/man-cgi?fcntl+2
400 * http://msdn.microsoft.com/library/default.asp?url=/library/en-us/fileio/fs/lockfileex.asp
403 /** @name Lock flags (bit masks).
405 /** Read access, can be shared with others. */
406 #define RTFILE_LOCK_READ 0x00
407 /** Write access, one at a time. */
408 #define RTFILE_LOCK_WRITE 0x01
409 /** Don't wait for other locks to be released. */
410 #define RTFILE_LOCK_IMMEDIATELY 0x00
411 /** Wait till conflicting locks have been released. */
412 #define RTFILE_LOCK_WAIT 0x02
413 /** Valid flags mask */
414 #define RTFILE_LOCK_MASK 0x03
419 * Locks a region of file for read (shared) or write (exclusive) access.
421 * @returns iprt status code.
422 * @returns VERR_FILE_LOCK_VIOLATION if lock can't be acquired.
423 * @param File Handle to the file.
424 * @param fLock Lock method and flags, see RTFILE_LOCK_* defines.
425 * @param offLock Offset of lock start.
426 * @param cbLock Length of region to lock, may overlap the end of file.
428 int RTFileLock(RTFILE File
, unsigned fLock
, int64_t offLock
, uint64_t cbLock
);
431 * Changes a lock type from read to write or from write to read.
432 * The region to type change must correspond exactly to an existing locked region.
433 * If change can't be done due to locking conflict and non-blocking mode is used, error is
434 * returned and lock keeps its state (see next warning).
436 * WARNING: win32 implementation of this call is not atomic, it transforms to a pair of
437 * calls RTFileUnlock and RTFileLock. Potentially the previously acquired lock can be
438 * lost, i.e. function is called in non-blocking mode, previous lock is freed, new lock can't
439 * be acquired, and old lock (previous state) can't be acquired back too. This situation
440 * may occurs _only_ if the other process is acquiring a _write_ lock in blocking mode or
441 * in race condition with the current call.
442 * In this very bad case special error code VERR_FILE_LOCK_LOST will be returned.
444 * @returns iprt status code.
445 * @returns VERR_FILE_NOT_LOCKED if region was not locked.
446 * @returns VERR_FILE_LOCK_VIOLATION if lock type can't be changed, lock remains its type.
447 * @returns VERR_FILE_LOCK_LOST if lock was lost, we haven't this lock anymore :(
448 * @param File Handle to the file.
449 * @param fLock Lock method and flags, see RTFILE_LOCK_* defines.
450 * @param offLock Offset of lock start.
451 * @param cbLock Length of region to lock, may overlap the end of file.
453 int RTFileChangeLock(RTFILE File
, unsigned fLock
, int64_t offLock
, uint64_t cbLock
);
456 * Unlocks previously locked region of file.
457 * The region to unlock must correspond exactly to an existing locked region.
459 * @returns iprt status code.
460 * @returns VERR_FILE_NOT_LOCKED if region was not locked.
461 * @param File Handle to the file.
462 * @param offLock Offset of lock start.
463 * @param cbLock Length of region to unlock, may overlap the end of file.
465 int RTFileUnlock(RTFILE File
, int64_t offLock
, uint64_t cbLock
);
469 * Query information about an open file.
471 * @returns iprt status code.
473 * @param File Handle to the file.
474 * @param pObjInfo Object information structure to be filled on successful return.
475 * @param enmAdditionalAttribs Which set of additional attributes to request.
476 * Use RTFSOBJATTRADD_NOTHING if this doesn't matter.
478 int RTFileQueryInfo(RTFILE File
, PRTFSOBJINFO pObjInfo
, RTFSOBJATTRADD enmAdditionalAttribs
);
481 * Changes one or more of the timestamps associated of file system object.
483 * @returns iprt status code.
484 * @returns VERR_NOT_SUPPORTED is returned if the operation isn't supported by the OS.
486 * @param File Handle to the file.
487 * @param pAccessTime Pointer to the new access time. NULL if not to be changed.
488 * @param pModificationTime Pointer to the new modifcation time. NULL if not to be changed.
489 * @param pChangeTime Pointer to the new change time. NULL if not to be changed.
490 * @param pBirthTime Pointer to the new time of birth. NULL if not to be changed.
492 * @remark The file system might not implement all these time attributes,
493 * the API will ignore the ones which aren't supported.
495 * @remark The file system might not implement the time resolution
496 * employed by this interface, the time will be chopped to fit.
498 * @remark The file system may update the change time even if it's
501 * @remark POSIX can only set Access & Modification and will always set both.
503 int RTFileSetTimes(RTFILE File
, PCRTTIMESPEC pAccessTime
, PCRTTIMESPEC pModificationTime
,
504 PCRTTIMESPEC pChangeTime
, PCRTTIMESPEC pBirthTime
);
507 * Gets one or more of the timestamps associated of file system object.
509 * @returns iprt status code.
510 * @param File Handle to the file.
511 * @param pAccessTime Where to store the access time. NULL is ok.
512 * @param pModificationTime Where to store the modifcation time. NULL is ok.
513 * @param pChangeTime Where to store the change time. NULL is ok.
514 * @param pBirthTime Where to store the time of birth. NULL is ok.
516 * @remark This is wrapper around RTFileQueryInfo() and exists to complement RTFileSetTimes().
518 int RTFileGetTimes(RTFILE File
, PRTTIMESPEC pAccessTime
, PRTTIMESPEC pModificationTime
,
519 PRTTIMESPEC pChangeTime
, PRTTIMESPEC pBirthTime
);
522 * Changes the mode flags of an open file.
524 * The API requires at least one of the mode flag sets (Unix/Dos) to
525 * be set. The type is ignored.
527 * @returns iprt status code.
528 * @param File Handle to the file.
529 * @param fMode The new file mode, see @ref grp_rt_fs for details.
531 int RTFileSetMode(RTFILE File
, RTFMODE fMode
);
534 * Gets the mode flags of an open file.
536 * @returns iprt status code.
537 * @param File Handle to the file.
538 * @param pfMode Where to store the file mode, see @ref grp_rt_fs for details.
540 * @remark This is wrapper around RTFileQueryInfo()
541 * and exists to complement RTFileSetMode().
543 int RTFileGetMode(RTFILE File
, uint32_t *pfMode
);
546 * Changes the owner and/or group of an open file.
548 * @returns iprt status code.
549 * @param File Handle to the file.
550 * @param uid The new file owner user id. Use -1 (or ~0) to leave this unchanged.
551 * @param gid The new group id. Use -1 (or ~0) to leave this unchanged.
553 int RTFileSetOwner(RTFILE File
, uint32_t uid
, uint32_t gid
);
556 * Gets the owner and/or group of an open file.
558 * @returns iprt status code.
559 * @param File Handle to the file.
560 * @param pUid Where to store the owner user id. NULL is ok.
561 * @param pGid Where to store the group id. NULL is ok.
563 * @remark This is wrapper around RTFileQueryInfo() and exists to complement RTFileGetOwner().
565 int RTFileGetOwner(RTFILE File
, uint32_t *pUid
, uint32_t *pGid
);
568 * Executes an IOCTL on a file descriptor.
570 * This function is currently only available in L4 and posix environments.
571 * Attemps at calling it from code shared with any other platforms will break things!
573 * The rational for defining this API is to simplify L4 porting of audio drivers,
574 * and to remove some of the assumptions on RTFILE being a file descriptor on
575 * platforms using the posix file implementation.
577 * @returns iprt status code.
578 * @param File Handle to the file.
579 * @param iRequest IOCTL request to carry out.
580 * @param pvData IOCTL data.
581 * @param cbData Size of the IOCTL data.
582 * @param piRet Return value of the IOCTL request.
584 int RTFileIoCtl(RTFILE File
, int iRequest
, void *pvData
, unsigned cbData
, int *piRet
);