|
|
1.1 root 1: // The following code tries to simulate the mode argument
2: // of the System V open().
3: // Supports only O_RDONLY O_WRONLY O_RDWR O_CREAT O_TRUNC O_EXCL
4:
5: #include <errno.h>
6: #include <osfcn.h>
7:
8: // The following defines are from System V release 2.
9:
10: #define O_RDONLY 0
11: #define O_WRONLY 1
12: #define O_RDWR 2
13: #define O_NDELAY 04 /* Non-blocking I/O */
14: #define O_APPEND 010 /* append (writes guaranteed at the end) */
15: #define O_SYNC 020 /* synchronous write option */
16:
17: /* Flag values accessible only to open(2) */
18: #define O_CREAT 00400 /* open with file create (uses third open arg)*/
19: #define O_TRUNC 01000 /* open with truncation */
20: #define O_EXCL 02000 /* exclusive open */
21:
22: int
23: open(const char* path, int kind, int mode)
24: {
25: // guard against arguments we cannot handle
26: if (kind & ~(O_RDONLY|O_WRONLY|O_RDWR|O_CREAT|O_TRUNC|O_EXCL)) {
27: errno = EINVAL;
28: return -1;
29: }
30:
31: // If O_CREAT and O_EXCL both set and the file exists, fail.
32: if ((kind & (O_CREAT|O_EXCL)) == (O_CREAT|O_EXCL)
33: && access(path, 0) >= 0) {
34: errno = EEXIST;
35: return -1;
36: }
37:
38: register int fd;
39: register int io = kind & (O_RDONLY|O_WRONLY|O_RDWR);
40:
41: switch (io) {
42: case O_RDONLY:
43: case O_RDWR:
44: fd = open(path, io);
45: if (fd >= 0) {
46: if (kind & O_TRUNC)
47: close(creat(path, 0));
48: } else if (kind & O_CREAT) {
49: int save = umask(0);
50: if ((fd = creat(path, 0600)) >= 0) {
51: close(fd);
52: if ((fd = open(path, io)) >= 0)
53: chmod(path, mode & ~save);
54: }
55: umask(save);
56: }
57: break;
58:
59: case O_WRONLY:
60: if (kind & O_TRUNC)
61: fd = creat(path, mode);
62: else {
63: fd = open(path, io);
64: if (fd < 0 && (kind & O_CREAT))
65: fd = creat(path, mode);
66: }
67: break;
68:
69: default:
70: errno = EINVAL;
71: fd = -1;
72: }
73: return fd;
74: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.