1*7c478bd9Sstevel@tonic-gate /*-
2*7c478bd9Sstevel@tonic-gate * See the file LICENSE for redistribution information.
3*7c478bd9Sstevel@tonic-gate *
4*7c478bd9Sstevel@tonic-gate * Copyright (c) 1997, 1998
5*7c478bd9Sstevel@tonic-gate * Sleepycat Software. All rights reserved.
6*7c478bd9Sstevel@tonic-gate */
7*7c478bd9Sstevel@tonic-gate
8*7c478bd9Sstevel@tonic-gate #include "config.h"
9*7c478bd9Sstevel@tonic-gate
10*7c478bd9Sstevel@tonic-gate #ifndef lint
11*7c478bd9Sstevel@tonic-gate static const char sccsid[] = "@(#)os_open.c 10.33 (Sleepycat) 10/12/98";
12*7c478bd9Sstevel@tonic-gate #endif /* not lint */
13*7c478bd9Sstevel@tonic-gate
14*7c478bd9Sstevel@tonic-gate #ifndef NO_SYSTEM_INCLUDES
15*7c478bd9Sstevel@tonic-gate #include <sys/types.h>
16*7c478bd9Sstevel@tonic-gate
17*7c478bd9Sstevel@tonic-gate #include <errno.h>
18*7c478bd9Sstevel@tonic-gate #include <fcntl.h>
19*7c478bd9Sstevel@tonic-gate #include <signal.h>
20*7c478bd9Sstevel@tonic-gate #include <unistd.h>
21*7c478bd9Sstevel@tonic-gate #endif
22*7c478bd9Sstevel@tonic-gate
23*7c478bd9Sstevel@tonic-gate #include "db_int.h"
24*7c478bd9Sstevel@tonic-gate #include "os_jump.h"
25*7c478bd9Sstevel@tonic-gate
26*7c478bd9Sstevel@tonic-gate /*
27*7c478bd9Sstevel@tonic-gate * __db_open --
28*7c478bd9Sstevel@tonic-gate * Open a file descriptor.
29*7c478bd9Sstevel@tonic-gate *
30*7c478bd9Sstevel@tonic-gate * PUBLIC: int __db_open __P((const char *, u_int32_t, u_int32_t, int, int *));
31*7c478bd9Sstevel@tonic-gate */
32*7c478bd9Sstevel@tonic-gate int
__db_open(name,arg_flags,ok_flags,mode,fdp)33*7c478bd9Sstevel@tonic-gate __db_open(name, arg_flags, ok_flags, mode, fdp)
34*7c478bd9Sstevel@tonic-gate const char *name;
35*7c478bd9Sstevel@tonic-gate u_int32_t arg_flags, ok_flags;
36*7c478bd9Sstevel@tonic-gate int mode, *fdp;
37*7c478bd9Sstevel@tonic-gate {
38*7c478bd9Sstevel@tonic-gate #if !defined(_WIN32) && defined(HAVE_SIGFILLSET)
39*7c478bd9Sstevel@tonic-gate sigset_t set, oset;
40*7c478bd9Sstevel@tonic-gate #endif
41*7c478bd9Sstevel@tonic-gate int flags, ret;
42*7c478bd9Sstevel@tonic-gate
43*7c478bd9Sstevel@tonic-gate if (arg_flags & ~ok_flags)
44*7c478bd9Sstevel@tonic-gate return (EINVAL);
45*7c478bd9Sstevel@tonic-gate
46*7c478bd9Sstevel@tonic-gate flags = 0;
47*7c478bd9Sstevel@tonic-gate
48*7c478bd9Sstevel@tonic-gate /*
49*7c478bd9Sstevel@tonic-gate * DB requires the semantic that two files opened at the same time
50*7c478bd9Sstevel@tonic-gate * with O_CREAT and O_EXCL set will return failure in at least one.
51*7c478bd9Sstevel@tonic-gate */
52*7c478bd9Sstevel@tonic-gate if (arg_flags & DB_CREATE)
53*7c478bd9Sstevel@tonic-gate flags |= O_CREAT;
54*7c478bd9Sstevel@tonic-gate
55*7c478bd9Sstevel@tonic-gate if (arg_flags & DB_EXCL)
56*7c478bd9Sstevel@tonic-gate flags |= O_EXCL;
57*7c478bd9Sstevel@tonic-gate
58*7c478bd9Sstevel@tonic-gate if (arg_flags & DB_RDONLY)
59*7c478bd9Sstevel@tonic-gate flags |= O_RDONLY;
60*7c478bd9Sstevel@tonic-gate else
61*7c478bd9Sstevel@tonic-gate flags |= O_RDWR;
62*7c478bd9Sstevel@tonic-gate
63*7c478bd9Sstevel@tonic-gate #if defined(_WIN32) || defined(WIN16)
64*7c478bd9Sstevel@tonic-gate #ifdef _MSC_VER
65*7c478bd9Sstevel@tonic-gate if (arg_flags & DB_SEQUENTIAL)
66*7c478bd9Sstevel@tonic-gate flags |= _O_SEQUENTIAL;
67*7c478bd9Sstevel@tonic-gate else
68*7c478bd9Sstevel@tonic-gate flags |= _O_RANDOM;
69*7c478bd9Sstevel@tonic-gate
70*7c478bd9Sstevel@tonic-gate if (arg_flags & DB_TEMPORARY)
71*7c478bd9Sstevel@tonic-gate flags |= _O_TEMPORARY;
72*7c478bd9Sstevel@tonic-gate #endif
73*7c478bd9Sstevel@tonic-gate flags |= O_BINARY | O_NOINHERIT;
74*7c478bd9Sstevel@tonic-gate #endif
75*7c478bd9Sstevel@tonic-gate
76*7c478bd9Sstevel@tonic-gate if (arg_flags & DB_TRUNCATE)
77*7c478bd9Sstevel@tonic-gate flags |= O_TRUNC;
78*7c478bd9Sstevel@tonic-gate
79*7c478bd9Sstevel@tonic-gate #if !defined(_WIN32) && defined(HAVE_SIGFILLSET)
80*7c478bd9Sstevel@tonic-gate /*
81*7c478bd9Sstevel@tonic-gate * We block every signal we can get our hands on so that the temporary
82*7c478bd9Sstevel@tonic-gate * file isn't left around if we're interrupted at the wrong time. Of
83*7c478bd9Sstevel@tonic-gate * course, if we drop core in-between the calls we'll hang forever, but
84*7c478bd9Sstevel@tonic-gate * that's probably okay. ;-)
85*7c478bd9Sstevel@tonic-gate */
86*7c478bd9Sstevel@tonic-gate if (arg_flags & DB_TEMPORARY) {
87*7c478bd9Sstevel@tonic-gate (void)sigfillset(&set);
88*7c478bd9Sstevel@tonic-gate (void)sigprocmask(SIG_BLOCK, &set, &oset);
89*7c478bd9Sstevel@tonic-gate }
90*7c478bd9Sstevel@tonic-gate #endif
91*7c478bd9Sstevel@tonic-gate
92*7c478bd9Sstevel@tonic-gate /* Open the file. */
93*7c478bd9Sstevel@tonic-gate if ((ret = __os_open(name, flags, mode, fdp)) != 0)
94*7c478bd9Sstevel@tonic-gate return (ret);
95*7c478bd9Sstevel@tonic-gate
96*7c478bd9Sstevel@tonic-gate #if !defined(_WIN32)
97*7c478bd9Sstevel@tonic-gate /* Delete any temporary file; done for Win32 by _O_TEMPORARY. */
98*7c478bd9Sstevel@tonic-gate if (arg_flags & DB_TEMPORARY) {
99*7c478bd9Sstevel@tonic-gate (void)__os_unlink(name);
100*7c478bd9Sstevel@tonic-gate #if defined(HAVE_SIGFILLSET)
101*7c478bd9Sstevel@tonic-gate (void)sigprocmask(SIG_SETMASK, &oset, NULL);
102*7c478bd9Sstevel@tonic-gate #endif
103*7c478bd9Sstevel@tonic-gate }
104*7c478bd9Sstevel@tonic-gate #endif
105*7c478bd9Sstevel@tonic-gate
106*7c478bd9Sstevel@tonic-gate #if !defined(_WIN32) && !defined(WIN16) && !defined(VMS)
107*7c478bd9Sstevel@tonic-gate /*
108*7c478bd9Sstevel@tonic-gate * Deny access to any child process.
109*7c478bd9Sstevel@tonic-gate * VMS: does not have fd inheritance.
110*7c478bd9Sstevel@tonic-gate * Win32: done by O_NOINHERIT.
111*7c478bd9Sstevel@tonic-gate */
112*7c478bd9Sstevel@tonic-gate if (fcntl(*fdp, F_SETFD, 1) == -1) {
113*7c478bd9Sstevel@tonic-gate ret = errno;
114*7c478bd9Sstevel@tonic-gate
115*7c478bd9Sstevel@tonic-gate (void)__os_close(*fdp);
116*7c478bd9Sstevel@tonic-gate return (ret);
117*7c478bd9Sstevel@tonic-gate }
118*7c478bd9Sstevel@tonic-gate #endif
119*7c478bd9Sstevel@tonic-gate return (0);
120*7c478bd9Sstevel@tonic-gate }
121*7c478bd9Sstevel@tonic-gate
122*7c478bd9Sstevel@tonic-gate /*
123*7c478bd9Sstevel@tonic-gate * __os_open --
124*7c478bd9Sstevel@tonic-gate * Open a file.
125*7c478bd9Sstevel@tonic-gate *
126*7c478bd9Sstevel@tonic-gate * PUBLIC: int __os_open __P((const char *, int, int, int *));
127*7c478bd9Sstevel@tonic-gate */
128*7c478bd9Sstevel@tonic-gate int
__os_open(name,flags,mode,fdp)129*7c478bd9Sstevel@tonic-gate __os_open(name, flags, mode, fdp)
130*7c478bd9Sstevel@tonic-gate const char *name;
131*7c478bd9Sstevel@tonic-gate int flags, mode, *fdp;
132*7c478bd9Sstevel@tonic-gate {
133*7c478bd9Sstevel@tonic-gate *fdp = __db_jump.j_open != NULL ?
134*7c478bd9Sstevel@tonic-gate __db_jump.j_open(name, flags, mode) : open(name, flags, mode);
135*7c478bd9Sstevel@tonic-gate return (*fdp == -1 ? errno : 0);
136*7c478bd9Sstevel@tonic-gate }
137*7c478bd9Sstevel@tonic-gate
138*7c478bd9Sstevel@tonic-gate /*
139*7c478bd9Sstevel@tonic-gate * __os_close --
140*7c478bd9Sstevel@tonic-gate * Close a file descriptor.
141*7c478bd9Sstevel@tonic-gate *
142*7c478bd9Sstevel@tonic-gate * PUBLIC: int __os_close __P((int));
143*7c478bd9Sstevel@tonic-gate */
144*7c478bd9Sstevel@tonic-gate int
__os_close(fd)145*7c478bd9Sstevel@tonic-gate __os_close(fd)
146*7c478bd9Sstevel@tonic-gate int fd;
147*7c478bd9Sstevel@tonic-gate {
148*7c478bd9Sstevel@tonic-gate int ret;
149*7c478bd9Sstevel@tonic-gate
150*7c478bd9Sstevel@tonic-gate ret = __db_jump.j_close != NULL ? __db_jump.j_close(fd) : close(fd);
151*7c478bd9Sstevel@tonic-gate return (ret == 0 ? 0 : errno);
152*7c478bd9Sstevel@tonic-gate }
153