1 /*
2 +----------------------------------------------------------------------+
3 | PHP Version 5 |
4 +----------------------------------------------------------------------+
5 | Copyright (c) 1997-2015 The PHP Group |
6 +----------------------------------------------------------------------+
7 | This source file is subject to version 3.01 of the PHP license, |
8 | that is bundled with this package in the file LICENSE, and is |
9 | available through the world-wide-web at the following url: |
10 | http://www.php.net/license/3_01.txt |
11 | If you did not receive a copy of the PHP license and are unable to |
12 | obtain it through the world-wide-web, please send a note to |
13 | license@php.net so we can mail you a copy immediately. |
14 +----------------------------------------------------------------------+
15 | Author: Sascha Schumann <sascha@schumann.cx> |
16 +----------------------------------------------------------------------+
17 */
18
19 /* $Id$ */
20
21 #include "php.h"
22 #include <errno.h>
23 #include "ext/standard/flock_compat.h"
24
25 #if HAVE_STRUCT_FLOCK
26 #include <unistd.h>
27 #include <fcntl.h>
28 #include <sys/file.h>
29 #endif
30
31 #ifdef PHP_WIN32
32 #include <io.h>
33 #include "config.w32.h"
34 #endif
35
36 #ifdef NETWARE
37 #include <netinet/in.h>
38 #endif
39
40 #ifndef HAVE_FLOCK
flock(int fd,int operation)41 PHPAPI int flock(int fd, int operation)
42 {
43 return php_flock(fd, operation);
44 }
45 #endif /* !defined(HAVE_FLOCK) */
46
php_flock(int fd,int operation)47 PHPAPI int php_flock(int fd, int operation)
48 #if HAVE_STRUCT_FLOCK /* {{{ */
49 {
50 struct flock flck;
51 int ret;
52
53 flck.l_start = flck.l_len = 0;
54 flck.l_whence = SEEK_SET;
55
56 if (operation & LOCK_SH)
57 flck.l_type = F_RDLCK;
58 else if (operation & LOCK_EX)
59 flck.l_type = F_WRLCK;
60 else if (operation & LOCK_UN)
61 flck.l_type = F_UNLCK;
62 else {
63 errno = EINVAL;
64 return -1;
65 }
66
67 ret = fcntl(fd, operation & LOCK_NB ? F_SETLK : F_SETLKW, &flck);
68
69 if (operation & LOCK_NB && ret == -1 &&
70 (errno == EACCES || errno == EAGAIN))
71 errno = EWOULDBLOCK;
72
73 if (ret != -1) ret = 0;
74
75 return ret;
76 }
77 /* }}} */
78 #elif defined(PHP_WIN32) /* {{{ */
79 /*
80 * Program: Unix compatibility routines
81 *
82 * Author: Mark Crispin
83 * Networks and Distributed Computing
84 * Computing & Communications
85 * University of Washington
86 * Administration Building, AG-44
87 * Seattle, WA 98195
88 * Internet: MRC@CAC.Washington.EDU
89 *
90 * Date: 14 September 1996
91 * Last Edited: 14 August 1997
92 *
93 * Copyright 1997 by the University of Washington
94 *
95 * Permission to use, copy, modify, and distribute this software and its
96 * documentation for any purpose and without fee is hereby granted, provided
97 * that the above copyright notice appears in all copies and that both the
98 * above copyright notice and this permission notice appear in supporting
99 * documentation, and that the name of the University of Washington not be
100 * used in advertising or publicity pertaining to distribution of the software
101 * without specific, written prior permission. This software is made available
102 * "as is", and
103 * THE UNIVERSITY OF WASHINGTON DISCLAIMS ALL WARRANTIES, EXPRESS OR IMPLIED,
104 * WITH REGARD TO THIS SOFTWARE, INCLUDING WITHOUT LIMITATION ALL IMPLIED * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE, AND IN
105 * NO EVENT SHALL THE UNIVERSITY OF WASHINGTON BE LIABLE FOR ANY SPECIAL,
106 * INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
107 * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, TORT
108 * (INCLUDING NEGLIGENCE) OR STRICT LIABILITY, ARISING OUT OF OR IN CONNECTION
109 * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
110 *
111 */
112 /* DEDICATION
113
114 * This file is dedicated to my dog, Unix, also known as Yun-chan and
115 * Unix J. Terwilliker Jehosophat Aloysius Monstrosity Animal Beast. Unix
116 * passed away at the age of 11 1/2 on September 14, 1996, 12:18 PM PDT, after
117 * a two-month bout with cirrhosis of the liver.
118 *
119 * He was a dear friend, and I miss him terribly.
120 *
121 * Lift a leg, Yunie. Luv ya forever!!!!
122 */
123 {
124 HANDLE hdl = (HANDLE) _get_osfhandle(fd);
125 DWORD low = 1, high = 0;
126 OVERLAPPED offset =
127 {0, 0, 0, 0, NULL};
128 DWORD err;
129
130 if (hdl < 0) {
131 _set_errno(EBADF);
132 return -1; /* error in file descriptor */
133 }
134 /* bug for bug compatible with Unix */
135 UnlockFileEx(hdl, 0, low, high, &offset);
136 switch (operation & ~LOCK_NB) { /* translate to LockFileEx() op */
137 case LOCK_EX: /* exclusive */
138 if (LockFileEx(hdl, LOCKFILE_EXCLUSIVE_LOCK +
139 ((operation & LOCK_NB) ? LOCKFILE_FAIL_IMMEDIATELY : 0),
140 0, low, high, &offset))
141 return 0;
142 break;
143 case LOCK_SH: /* shared */
144 if (LockFileEx(hdl, ((operation & LOCK_NB) ? LOCKFILE_FAIL_IMMEDIATELY : 0),
145 0, low, high, &offset))
146 return 0;
147 break;
148 case LOCK_UN: /* unlock */
149 return 0; /* always succeeds */
150 default: /* default */
151 break;
152 }
153
154 err = GetLastError();
155 if (ERROR_LOCK_VIOLATION == err || ERROR_SHARING_VIOLATION == err) {
156 _set_errno(EWOULDBLOCK);
157 } else {
158 _set_errno(EINVAL); /* bad call */
159 }
160
161 return -1;
162 }
163 /* }}} */
164 #else
165 #warning no proper flock support for your site
166 {
167 errno = 0;
168 return 0;
169 }
170 #endif
171
172 #ifndef PHP_WIN32
173 #if !(HAVE_INET_ATON)
174 /* {{{ inet_aton
175 * Check whether "cp" is a valid ascii representation
176 * of an Internet address and convert to a binary address.
177 * Returns 1 if the address is valid, 0 if not.
178 * This replaces inet_addr, the return value from which
179 * cannot distinguish between failure and a local broadcast address.
180 */
inet_aton(const char * cp,struct in_addr * ap)181 int inet_aton(const char *cp, struct in_addr *ap)
182 {
183 int dots = 0;
184 register unsigned long acc = 0, addr = 0;
185
186 do {
187 register char cc = *cp;
188
189 switch (cc) {
190 case '0':
191 case '1':
192 case '2':
193 case '3':
194 case '4':
195 case '5':
196 case '6':
197 case '7':
198 case '8':
199 case '9':
200 acc = acc * 10 + (cc - '0');
201 break;
202
203 case '.':
204 if (++dots > 3) {
205 return 0;
206 }
207 /* Fall through */
208
209 case '\0':
210 if (acc > 255) {
211 return 0;
212 }
213 addr = addr << 8 | acc;
214 acc = 0;
215 break;
216
217 default:
218 return 0;
219 }
220 } while (*cp++) ;
221
222 /* Normalize the address */
223 if (dots < 3) {
224 addr <<= 8 * (3 - dots) ;
225 }
226
227 /* Store it if requested */
228 if (ap) {
229 ap->s_addr = htonl(addr);
230 }
231
232 return 1;
233 }
234 /* }}} */
235 #endif /* !HAVE_INET_ATON */
236 #endif
237
238 /*
239 * Local variables:
240 * tab-width: 4
241 * c-basic-offset: 4
242 * End:
243 * vim600: sw=4 ts=4 fdm=marker
244 * vim<600: sw=4 ts=4
245 */
246