Revert "update rx to the latest rx-oss-v1.1 build."
[mono-project.git] / mono / io-layer / locking.c
blobeec2549513dba01f0eb3a00093c7bf45afdad883
1 /*
2 * io.c: File, console and find handles
4 * Author:
5 * Dick Porter (dick@ximian.com)
7 * (C) 2002 Ximian, Inc.
8 * Copyright (c) 2002-2009 Novell, Inc.
9 */
10 #include <config.h>
11 #include <stdio.h>
12 #include <glib.h>
13 #include <fcntl.h>
14 #include <errno.h>
15 #include <mono/io-layer/wapi.h>
16 #include <mono/io-layer/wapi-private.h>
17 #include <mono/io-layer/handles-private.h>
18 #include <mono/io-layer/io-private.h>
20 #if 0
21 // #define DEBUG(...) g_message(__VA_ARGS__)
22 #else
23 #define DEBUG(...)
24 #endif
26 gboolean
27 _wapi_lock_file_region (int fd, off_t offset, off_t length)
29 #if defined(__native_client__)
30 printf("WARNING: locking.c: _wapi_lock_file_region(): fcntl() not available on Native Client!\n");
31 // behave as below -- locks are not available
32 return(TRUE);
33 #else
34 struct flock lock_data;
35 int ret;
37 if (offset < 0 || length < 0) {
38 SetLastError (ERROR_INVALID_PARAMETER);
39 return(FALSE);
42 lock_data.l_type = F_WRLCK;
43 lock_data.l_whence = SEEK_SET;
44 lock_data.l_start = offset;
45 lock_data.l_len = length;
47 do {
48 ret = fcntl (fd, F_SETLK, &lock_data);
49 } while(ret == -1 && errno == EINTR);
51 DEBUG ("%s: fcntl returns %d", __func__, ret);
53 if (ret == -1) {
55 * if locks are not available (NFS for example),
56 * ignore the error
58 if (errno == ENOLCK
59 #ifdef EOPNOTSUPP
60 || errno == EOPNOTSUPP
61 #endif
62 #ifdef ENOTSUP
63 || errno == ENOTSUP
64 #endif
65 ) {
66 return (TRUE);
69 SetLastError (ERROR_LOCK_VIOLATION);
70 return(FALSE);
73 return(TRUE);
74 #endif /* __native_client__ */
77 gboolean
78 _wapi_unlock_file_region (int fd, off_t offset, off_t length)
80 #if defined(__native_client__)
81 printf("WARNING: locking.c: _wapi_unlock_file_region(): fcntl() not available on Native Client!\n");
82 return (TRUE);
83 #else
84 struct flock lock_data;
85 int ret;
87 lock_data.l_type = F_UNLCK;
88 lock_data.l_whence = SEEK_SET;
89 lock_data.l_start = offset;
90 lock_data.l_len = length;
92 do {
93 ret = fcntl (fd, F_SETLK, &lock_data);
94 } while(ret == -1 && errno == EINTR);
96 DEBUG ("%s: fcntl returns %d", __func__, ret);
98 if (ret == -1) {
100 * if locks are not available (NFS for example),
101 * ignore the error
103 if (errno == ENOLCK
104 #ifdef EOPNOTSUPP
105 || errno == EOPNOTSUPP
106 #endif
107 #ifdef ENOTSUP
108 || errno == ENOTSUP
109 #endif
111 return (TRUE);
114 SetLastError (ERROR_LOCK_VIOLATION);
115 return(FALSE);
118 return(TRUE);
119 #endif /* __native_client__ */
122 gboolean
123 LockFile (gpointer handle, guint32 offset_low, guint32 offset_high,
124 guint32 length_low, guint32 length_high)
126 struct _WapiHandle_file *file_handle;
127 gboolean ok;
128 off_t offset, length;
129 int fd = GPOINTER_TO_UINT(handle);
131 ok = _wapi_lookup_handle (handle, WAPI_HANDLE_FILE,
132 (gpointer *)&file_handle);
133 if (ok == FALSE) {
134 g_warning ("%s: error looking up file handle %p", __func__,
135 handle);
136 SetLastError (ERROR_INVALID_HANDLE);
137 return(FALSE);
140 if (!(file_handle->fileaccess & GENERIC_READ) &&
141 !(file_handle->fileaccess & GENERIC_WRITE) &&
142 !(file_handle->fileaccess & GENERIC_ALL)) {
143 DEBUG ("%s: handle %p doesn't have GENERIC_READ or GENERIC_WRITE access: %u", __func__, handle, file_handle->fileaccess);
144 SetLastError (ERROR_ACCESS_DENIED);
145 return(FALSE);
148 #ifdef HAVE_LARGE_FILE_SUPPORT
149 offset = ((gint64)offset_high << 32) | offset_low;
150 length = ((gint64)length_high << 32) | length_low;
152 DEBUG ("%s: Locking handle %p, offset %lld, length %lld", __func__, handle, offset, length);
153 #else
154 if (offset_high > 0 || length_high > 0) {
155 SetLastError (ERROR_INVALID_PARAMETER);
156 return (FALSE);
158 offset = offset_low;
159 length = length_low;
161 DEBUG ("%s: Locking handle %p, offset %ld, length %ld", __func__,
162 handle, offset, length);
163 #endif
165 return(_wapi_lock_file_region (fd, offset, length));
168 gboolean
169 UnlockFile (gpointer handle, guint32 offset_low,
170 guint32 offset_high, guint32 length_low,
171 guint32 length_high)
173 struct _WapiHandle_file *file_handle;
174 gboolean ok;
175 off_t offset, length;
176 int fd = GPOINTER_TO_UINT(handle);
178 ok = _wapi_lookup_handle (handle, WAPI_HANDLE_FILE,
179 (gpointer *)&file_handle);
180 if (ok == FALSE) {
181 g_warning ("%s: error looking up file handle %p", __func__,
182 handle);
183 SetLastError (ERROR_INVALID_HANDLE);
184 return(FALSE);
187 if (!(file_handle->fileaccess & GENERIC_READ) &&
188 !(file_handle->fileaccess & GENERIC_WRITE) &&
189 !(file_handle->fileaccess & GENERIC_ALL)) {
190 DEBUG ("%s: handle %p doesn't have GENERIC_READ or GENERIC_WRITE access: %u", __func__, handle, file_handle->fileaccess);
191 SetLastError (ERROR_ACCESS_DENIED);
192 return(FALSE);
195 #ifdef HAVE_LARGE_FILE_SUPPORT
196 offset = ((gint64)offset_high << 32) | offset_low;
197 length = ((gint64)length_high << 32) | length_low;
199 DEBUG ("%s: Unlocking handle %p, offset %lld, length %lld", __func__, handle, offset, length);
200 #else
201 offset = offset_low;
202 length = length_low;
204 DEBUG ("%s: Unlocking handle %p, offset %ld, length %ld", __func__, handle, offset, length);
205 #endif
207 return(_wapi_unlock_file_region (fd, offset, length));