~ubuntu-branches/ubuntu/utopic/squid3/utopic-proposed

« back to all changes in this revision

Viewing changes to lib/win32lib.c

  • Committer: Package Import Robot
  • Author(s): Yolanda Robla
  • Date: 2013-07-10 17:12:42 UTC
  • mfrom: (21.2.18 sid)
  • Revision ID: package-import@ubuntu.com-20130710171242-2i9v941ikbpnjyqk
Tags: 3.3.4-1ubuntu1
* Merge from Debian unstable (LP: #1199883).  Remaining changes:
  + debian/control:
    - Update maintainer.
    - Suggests apparmor (>= 2.3)
    - Depends on ssl-cert ((>= 1.0-11ubuntu1), autopkgtests
  + debian/squid3.upstart
    - Move ulimit command to script section so that it applies
      to the started squid daemon. Thanks to Timur Irmatov (LP: 986159)
    - Work around squid not handling SIGHUP by adding respawn to
      upstart job. (LP: 978356)
  + debian/NEWS.Debian: Rename NEWS.debian, add note regarding squid3
    transition in 12.04 (LP: 924739)
  + debian/rules
    - Re-enable all hardening options lost in the squid->squid3
      transition (LP: 986314)
  + squid3.resolvconf, debian/squid3.postinst, debian/squid3.postrm,
    debian/squid3.preinst, debian/squid3.prerm:
    - Convert init script to upstart
  + debian/patches/99-ubuntu-ssl-cert-snakeoil:
    - Use snakeoil certificates.
  + debian/logrotate
    - Use sar-reports rather than sarg-maint. (LP: 26616)
  + debian/patches/90-cf.data.ubuntu.dpatch:
    - Add an example refresh pattern for debs.
      (foundations-lucid-local-report spec)
  + Add disabled by default AppArmor profile (LP: 497790)
    - debian/squid3.upstart: load profile in pre-start stanza
    - add debian/usr.sbin.squid3 profile
    - debian/rules:
      + install debian/usr.sbin.squid3, etc/apparmor.d/force-complain and
        etc/apparmor.d/disable into $(INSTALLDIR)
      + use dh_apparmor
    - debian/squid3.install: install etc/apparmor.d/disable, force-complain
      and usr.sbin.squid3
    - debian/squid3.preinst: disable profile on clean install or upgrades
      from earlier than when we shipped the profile
  + debian/tests:
    - Add autopkgtests.

* Dropped:
  - debian/patches: dropped patches, superseded by new release:
    + 98-CVE-2012-5643.patch
    + 99-lp1117517_r12473.patch
  - debian/rules: fix FTBFS, removed --with-cppunit-basedir flag,
    included in Debian.
  - debian/control: Dropped transitional packages from squid, no
    longer required.

* Refreshed patches:
  - 01-cf.data.debian.patch
  - 02-makefile-defaults.patch
  - 15-cachemgr-default-config.patch

* debian/tests/test-squid.py: fixed case problem with ftp test

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
 
2
 
/*
3
 
 * $Id$
4
 
 *
5
 
 * Windows support
6
 
 * AUTHOR: Guido Serassio <serassio@squid-cache.org>
7
 
 * inspired by previous work by Romeo Anghelache & Eric Stern.
8
 
 *
9
 
 * SQUID Web Proxy Cache          http://www.squid-cache.org/
10
 
 * ----------------------------------------------------------
11
 
 *
12
 
 *  Squid is the result of efforts by numerous individuals from
13
 
 *  the Internet community; see the CONTRIBUTORS file for full
14
 
 *  details.   Many organizations have provided support for Squid's
15
 
 *  development; see the SPONSORS file for full details.  Squid is
16
 
 *  Copyrighted (C) 2001 by the Regents of the University of
17
 
 *  California; see the COPYRIGHT file for full details.  Squid
18
 
 *  incorporates software developed and/or copyrighted by other
19
 
 *  sources; see the CREDITS file for full details.
20
 
 *
21
 
 *  This program is free software; you can redistribute it and/or modify
22
 
 *  it under the terms of the GNU General Public License as published by
23
 
 *  the Free Software Foundation; either version 2 of the License, or
24
 
 *  (at your option) any later version.
25
 
 *
26
 
 *  This program is distributed in the hope that it will be useful,
27
 
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
28
 
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
29
 
 *  GNU General Public License for more details.
30
 
 *
31
 
 *  You should have received a copy of the GNU General Public License
32
 
 *  along with this program; if not, write to the Free Software
33
 
 *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA.
34
 
 *
35
 
 */
36
 
 
37
 
#include "util.h"
38
 
 
39
 
/* The following code section is part of an EXPERIMENTAL native */
40
 
/* Windows NT/2000 Squid port - Compiles only on MS Visual C++  */
41
 
#if defined(_SQUID_MSWIN_)
42
 
 
43
 
#undef strerror
44
 
#define sys_nerr _sys_nerr
45
 
 
46
 
#undef assert
47
 
#include <assert.h>
48
 
#include <stdio.h>
49
 
#include <fcntl.h>
50
 
#include "squid_windows.h"
51
 
#include <string.h>
52
 
#include <sys/timeb.h>
53
 
#if HAVE_WIN32_PSAPI
54
 
#include <psapi.h>
55
 
#endif
56
 
 
57
 
THREADLOCAL int ws32_result;
58
 
LPCRITICAL_SECTION dbg_mutex = NULL;
59
 
 
60
 
void GetProcessName(pid_t, char *);
61
 
 
62
 
#if defined(_MSC_VER)           /* Microsoft C Compiler ONLY */
63
 
size_t
64
 
getpagesize()
65
 
{
66
 
    static DWORD system_pagesize = 0;
67
 
    if (!system_pagesize) {
68
 
        SYSTEM_INFO system_info;
69
 
        GetSystemInfo(&system_info);
70
 
        system_pagesize = system_info.dwPageSize;
71
 
    }
72
 
    return system_pagesize;
73
 
}
74
 
#endif
75
 
 
76
 
uid_t
77
 
geteuid(void)
78
 
{
79
 
    return 100;
80
 
}
81
 
 
82
 
uid_t
83
 
getuid(void)
84
 
{
85
 
    return 100;
86
 
}
87
 
 
88
 
int
89
 
setuid(uid_t uid)
90
 
{
91
 
    return 0;
92
 
}
93
 
 
94
 
int
95
 
seteuid(uid_t euid)
96
 
{
97
 
    return 0;
98
 
}
99
 
 
100
 
gid_t
101
 
getegid(void)
102
 
{
103
 
    return 100;
104
 
}
105
 
 
106
 
gid_t
107
 
getgid(void)
108
 
{
109
 
    return 100;
110
 
}
111
 
 
112
 
int
113
 
setgid(gid_t gid)
114
 
{
115
 
    return 0;
116
 
}
117
 
 
118
 
int
119
 
setegid(gid_t egid)
120
 
{
121
 
    return 0;
122
 
}
123
 
 
124
 
int
125
 
chroot(const char *dirname)
126
 
{
127
 
    if (SetCurrentDirectory(dirname))
128
 
        return 0;
129
 
    else
130
 
        return GetLastError();
131
 
}
132
 
 
133
 
void
134
 
GetProcessName(pid_t pid, char *ProcessName)
135
 
{
136
 
    HANDLE hProcess;
137
 
 
138
 
    strcpy(ProcessName, "unknown");
139
 
#if HAVE_WIN32_PSAPI
140
 
    /* Get a handle to the process. */
141
 
    hProcess = OpenProcess(PROCESS_QUERY_INFORMATION |
142
 
                           PROCESS_VM_READ,
143
 
                           FALSE, pid);
144
 
    /* Get the process name. */
145
 
    if (NULL != hProcess) {
146
 
        HMODULE hMod;
147
 
        DWORD cbNeeded;
148
 
 
149
 
        if (EnumProcessModules(hProcess, &hMod, sizeof(hMod), &cbNeeded))
150
 
            GetModuleBaseName(hProcess, hMod, ProcessName, sizeof(ProcessName));
151
 
        else {
152
 
            CloseHandle(hProcess);
153
 
            return;
154
 
        }
155
 
    } else
156
 
        return;
157
 
    CloseHandle(hProcess);
158
 
#endif
159
 
}
160
 
 
161
 
int
162
 
kill(pid_t pid, int sig)
163
 
{
164
 
    HANDLE hProcess;
165
 
    char MyProcessName[MAX_PATH];
166
 
    char ProcessNameToCheck[MAX_PATH];
167
 
 
168
 
    if (sig == 0) {
169
 
        if ((hProcess = OpenProcess(PROCESS_QUERY_INFORMATION |
170
 
                                    PROCESS_VM_READ,
171
 
                                    FALSE, pid)) == NULL)
172
 
            return -1;
173
 
        else {
174
 
            CloseHandle(hProcess);
175
 
            GetProcessName(getpid(), MyProcessName);
176
 
            GetProcessName(pid, ProcessNameToCheck);
177
 
            if (strcmp(MyProcessName, ProcessNameToCheck) == 0)
178
 
                return 0;
179
 
            return -1;
180
 
        }
181
 
    } else
182
 
        return 0;
183
 
}
184
 
 
185
 
#ifndef HAVE_GETTIMEOFDAY
186
 
int
187
 
gettimeofday(struct timeval *pcur_time, void *tzp)
188
 
{
189
 
    struct _timeb current;
190
 
    struct timezone *tz = (struct timezone *) tzp;
191
 
 
192
 
    _ftime(&current);
193
 
 
194
 
    pcur_time->tv_sec = current.time;
195
 
    pcur_time->tv_usec = current.millitm * 1000L;
196
 
    if (tz) {
197
 
        tz->tz_minuteswest = current.timezone;  /* minutes west of Greenwich  */
198
 
        tz->tz_dsttime = current.dstflag;       /* type of dst correction  */
199
 
    }
200
 
    return 0;
201
 
}
202
 
#endif
203
 
 
204
 
int
205
 
statfs(const char *path, struct statfs *sfs)
206
 
{
207
 
    char drive[4];
208
 
    DWORD spc, bps, freec, totalc;
209
 
    DWORD vsn, maxlen, flags;
210
 
 
211
 
    if (!sfs) {
212
 
        errno = EINVAL;
213
 
        return -1;
214
 
    }
215
 
    strncpy(drive, path, 2);
216
 
    drive[2] = '\0';
217
 
    strcat(drive, "\\");
218
 
 
219
 
    if (!GetDiskFreeSpace(drive, &spc, &bps, &freec, &totalc)) {
220
 
        errno = ENOENT;
221
 
        return -1;
222
 
    }
223
 
    if (!GetVolumeInformation(drive, NULL, 0, &vsn, &maxlen, &flags, NULL, 0)) {
224
 
        errno = ENOENT;
225
 
        return -1;
226
 
    }
227
 
    sfs->f_type = flags;
228
 
    sfs->f_bsize = spc * bps;
229
 
    sfs->f_blocks = totalc;
230
 
    sfs->f_bfree = sfs->f_bavail = freec;
231
 
    sfs->f_files = -1;
232
 
    sfs->f_ffree = -1;
233
 
    sfs->f_fsid = vsn;
234
 
    sfs->f_namelen = maxlen;
235
 
    return 0;
236
 
}
237
 
 
238
 
int
239
 
WIN32_ftruncate(int fd, off_t size)
240
 
{
241
 
    HANDLE hfile;
242
 
    unsigned int curpos;
243
 
 
244
 
    if (fd < 0)
245
 
        return -1;
246
 
 
247
 
    hfile = (HANDLE) _get_osfhandle(fd);
248
 
    curpos = SetFilePointer(hfile, 0, NULL, FILE_CURRENT);
249
 
    if (curpos == 0xFFFFFFFF
250
 
            || SetFilePointer(hfile, size, NULL, FILE_BEGIN) == 0xFFFFFFFF
251
 
            || !SetEndOfFile(hfile)) {
252
 
        int error = GetLastError();
253
 
 
254
 
        switch (error) {
255
 
        case ERROR_INVALID_HANDLE:
256
 
            errno = EBADF;
257
 
            break;
258
 
        default:
259
 
            errno = EIO;
260
 
            break;
261
 
        }
262
 
 
263
 
        return -1;
264
 
    }
265
 
    return 0;
266
 
}
267
 
 
268
 
int
269
 
WIN32_truncate(const char *pathname, off_t length)
270
 
{
271
 
    int fd;
272
 
    int res = -1;
273
 
 
274
 
    fd = open(pathname, O_RDWR);
275
 
 
276
 
    if (fd == -1)
277
 
        errno = EBADF;
278
 
    else {
279
 
        res = WIN32_ftruncate(fd, length);
280
 
        _close(fd);
281
 
    }
282
 
 
283
 
    return res;
284
 
}
285
 
 
286
 
static struct _wsaerrtext {
287
 
    int err;
288
 
    const char *errconst;
289
 
    const char *errdesc;
290
 
} _wsaerrtext[] = {
291
 
 
292
 
    {
293
 
        WSA_E_CANCELLED, "WSA_E_CANCELLED", "Lookup cancelled."
294
 
    },
295
 
    {
296
 
        WSA_E_NO_MORE, "WSA_E_NO_MORE", "No more data available."
297
 
    },
298
 
    {
299
 
        WSAEACCES, "WSAEACCES", "Permission denied."
300
 
    },
301
 
    {
302
 
        WSAEADDRINUSE, "WSAEADDRINUSE", "Address already in use."
303
 
    },
304
 
    {
305
 
        WSAEADDRNOTAVAIL, "WSAEADDRNOTAVAIL", "Cannot assign requested address."
306
 
    },
307
 
    {
308
 
        WSAEAFNOSUPPORT, "WSAEAFNOSUPPORT", "Address family not supported by protocol family."
309
 
    },
310
 
    {
311
 
        WSAEALREADY, "WSAEALREADY", "Operation already in progress."
312
 
    },
313
 
    {
314
 
        WSAEBADF, "WSAEBADF", "Bad file number."
315
 
    },
316
 
    {
317
 
        WSAECANCELLED, "WSAECANCELLED", "Operation cancelled."
318
 
    },
319
 
    {
320
 
        WSAECONNABORTED, "WSAECONNABORTED", "Software caused connection abort."
321
 
    },
322
 
    {
323
 
        WSAECONNREFUSED, "WSAECONNREFUSED", "Connection refused."
324
 
    },
325
 
    {
326
 
        WSAECONNRESET, "WSAECONNRESET", "Connection reset by peer."
327
 
    },
328
 
    {
329
 
        WSAEDESTADDRREQ, "WSAEDESTADDRREQ", "Destination address required."
330
 
    },
331
 
    {
332
 
        WSAEDQUOT, "WSAEDQUOT", "Disk quota exceeded."
333
 
    },
334
 
    {
335
 
        WSAEFAULT, "WSAEFAULT", "Bad address."
336
 
    },
337
 
    {
338
 
        WSAEHOSTDOWN, "WSAEHOSTDOWN", "Host is down."
339
 
    },
340
 
    {
341
 
        WSAEHOSTUNREACH, "WSAEHOSTUNREACH", "No route to host."
342
 
    },
343
 
    {
344
 
        WSAEINPROGRESS, "WSAEINPROGRESS", "Operation now in progress."
345
 
    },
346
 
    {
347
 
        WSAEINTR, "WSAEINTR", "Interrupted function call."
348
 
    },
349
 
    {
350
 
        WSAEINVAL, "WSAEINVAL", "Invalid argument."
351
 
    },
352
 
    {
353
 
        WSAEINVALIDPROCTABLE, "WSAEINVALIDPROCTABLE", "Invalid procedure table from service provider."
354
 
    },
355
 
    {
356
 
        WSAEINVALIDPROVIDER, "WSAEINVALIDPROVIDER", "Invalid service provider version number."
357
 
    },
358
 
    {
359
 
        WSAEISCONN, "WSAEISCONN", "Socket is already connected."
360
 
    },
361
 
    {
362
 
        WSAELOOP, "WSAELOOP", "Too many levels of symbolic links."
363
 
    },
364
 
    {
365
 
        WSAEMFILE, "WSAEMFILE", "Too many open files."
366
 
    },
367
 
    {
368
 
        WSAEMSGSIZE, "WSAEMSGSIZE", "Message too long."
369
 
    },
370
 
    {
371
 
        WSAENAMETOOLONG, "WSAENAMETOOLONG", "File name is too long."
372
 
    },
373
 
    {
374
 
        WSAENETDOWN, "WSAENETDOWN", "Network is down."
375
 
    },
376
 
    {
377
 
        WSAENETRESET, "WSAENETRESET", "Network dropped connection on reset."
378
 
    },
379
 
    {
380
 
        WSAENETUNREACH, "WSAENETUNREACH", "Network is unreachable."
381
 
    },
382
 
    {
383
 
        WSAENOBUFS, "WSAENOBUFS", "No buffer space available."
384
 
    },
385
 
    {
386
 
        WSAENOMORE, "WSAENOMORE", "No more data available."
387
 
    },
388
 
    {
389
 
        WSAENOPROTOOPT, "WSAENOPROTOOPT", "Bad protocol option."
390
 
    },
391
 
    {
392
 
        WSAENOTCONN, "WSAENOTCONN", "Socket is not connected."
393
 
    },
394
 
    {
395
 
        WSAENOTEMPTY, "WSAENOTEMPTY", "Directory is not empty."
396
 
    },
397
 
    {
398
 
        WSAENOTSOCK, "WSAENOTSOCK", "Socket operation on nonsocket."
399
 
    },
400
 
    {
401
 
        WSAEOPNOTSUPP, "WSAEOPNOTSUPP", "Operation not supported."
402
 
    },
403
 
    {
404
 
        WSAEPFNOSUPPORT, "WSAEPFNOSUPPORT", "Protocol family not supported."
405
 
    },
406
 
    {
407
 
        WSAEPROCLIM, "WSAEPROCLIM", "Too many processes."
408
 
    },
409
 
    {
410
 
        WSAEPROTONOSUPPORT, "WSAEPROTONOSUPPORT", "Protocol not supported."
411
 
    },
412
 
    {
413
 
        WSAEPROTOTYPE, "WSAEPROTOTYPE", "Protocol wrong type for socket."
414
 
    },
415
 
    {
416
 
        WSAEPROVIDERFAILEDINIT, "WSAEPROVIDERFAILEDINIT", "Unable to initialise a service provider."
417
 
    },
418
 
    {
419
 
        WSAEREFUSED, "WSAEREFUSED", "Refused."
420
 
    },
421
 
    {
422
 
        WSAEREMOTE, "WSAEREMOTE", "Too many levels of remote in path."
423
 
    },
424
 
    {
425
 
        WSAESHUTDOWN, "WSAESHUTDOWN", "Cannot send after socket shutdown."
426
 
    },
427
 
    {
428
 
        WSAESOCKTNOSUPPORT, "WSAESOCKTNOSUPPORT", "Socket type not supported."
429
 
    },
430
 
    {
431
 
        WSAESTALE, "WSAESTALE", "Stale NFS file handle."
432
 
    },
433
 
    {
434
 
        WSAETIMEDOUT, "WSAETIMEDOUT", "Connection timed out."
435
 
    },
436
 
    {
437
 
        WSAETOOMANYREFS, "WSAETOOMANYREFS", "Too many references."
438
 
    },
439
 
    {
440
 
        WSAEUSERS, "WSAEUSERS", "Too many users."
441
 
    },
442
 
    {
443
 
        WSAEWOULDBLOCK, "WSAEWOULDBLOCK", "Resource temporarily unavailable."
444
 
    },
445
 
    {
446
 
        WSANOTINITIALISED, "WSANOTINITIALISED", "Successful WSAStartup not yet performed."
447
 
    },
448
 
    {
449
 
        WSASERVICE_NOT_FOUND, "WSASERVICE_NOT_FOUND", "Service not found."
450
 
    },
451
 
    {
452
 
        WSASYSCALLFAILURE, "WSASYSCALLFAILURE", "System call failure."
453
 
    },
454
 
    {
455
 
        WSASYSNOTREADY, "WSASYSNOTREADY", "Network subsystem is unavailable."
456
 
    },
457
 
    {
458
 
        WSATYPE_NOT_FOUND, "WSATYPE_NOT_FOUND", "Class type not found."
459
 
    },
460
 
    {
461
 
        WSAVERNOTSUPPORTED, "WSAVERNOTSUPPORTED", "Winsock.dll version out of range."
462
 
    },
463
 
    {
464
 
        WSAEDISCON, "WSAEDISCON", "Graceful shutdown in progress."
465
 
    }
466
 
};
467
 
 
468
 
/*
469
 
 * wsastrerror() - description of WSAGetLastError()
470
 
 */
471
 
const char *
472
 
wsastrerror(int err)
473
 
{
474
 
    static char xwsaerror_buf[BUFSIZ];
475
 
    int i, errind = -1;
476
 
 
477
 
    if (err == 0)
478
 
        return "(0) No error.";
479
 
    for (i = 0; i < sizeof(_wsaerrtext) / sizeof(struct _wsaerrtext); i++) {
480
 
        if (_wsaerrtext[i].err != err)
481
 
            continue;
482
 
        errind = i;
483
 
        break;
484
 
    }
485
 
    if (errind == -1)
486
 
        snprintf(xwsaerror_buf, BUFSIZ, "Unknown");
487
 
    else
488
 
        snprintf(xwsaerror_buf, BUFSIZ, "%s, %s", _wsaerrtext[errind].errconst, _wsaerrtext[errind].errdesc);
489
 
    return xwsaerror_buf;
490
 
}
491
 
 
492
 
struct passwd *
493
 
getpwnam(char *unused) {
494
 
    static struct passwd pwd = {NULL, NULL, 100, 100, NULL, NULL, NULL};
495
 
    return &pwd;
496
 
}
497
 
 
498
 
struct group *
499
 
getgrnam(char *unused) {
500
 
    static struct group grp = {NULL, NULL, 100, NULL};
501
 
    return &grp;
502
 
}
503
 
 
504
 
/*
505
 
 * WIN32_strerror with argument for late notification */
506
 
 
507
 
const char *
508
 
WIN32_strerror(int err)
509
 
{
510
 
    static char xbstrerror_buf[BUFSIZ];
511
 
 
512
 
    if (err < 0 || err >= sys_nerr)
513
 
        strncpy(xbstrerror_buf, wsastrerror(err), BUFSIZ);
514
 
    else
515
 
        strncpy(xbstrerror_buf, strerror(err), BUFSIZ);
516
 
    return xbstrerror_buf;
517
 
}
518
 
 
519
 
#if defined(__MINGW32__)        /* MinGW environment */
520
 
int
521
 
_free_osfhnd(int filehandle)
522
 
{
523
 
    if (((unsigned) filehandle < SQUID_MAXFD) &&
524
 
            (_osfile(filehandle) & FOPEN) &&
525
 
            (_osfhnd(filehandle) != (long) INVALID_HANDLE_VALUE)) {
526
 
        switch (filehandle) {
527
 
        case 0:
528
 
            SetStdHandle(STD_INPUT_HANDLE, NULL);
529
 
            break;
530
 
        case 1:
531
 
            SetStdHandle(STD_OUTPUT_HANDLE, NULL);
532
 
            break;
533
 
        case 2:
534
 
            SetStdHandle(STD_ERROR_HANDLE, NULL);
535
 
            break;
536
 
        }
537
 
        _osfhnd(filehandle) = (long) INVALID_HANDLE_VALUE;
538
 
        return (0);
539
 
    } else {
540
 
        errno = EBADF;          /* bad handle */
541
 
        _doserrno = 0L;         /* not an OS error */
542
 
        return -1;
543
 
    }
544
 
}
545
 
#endif
546
 
 
547
 
struct errorentry {
548
 
    unsigned long WIN32_code;
549
 
    int POSIX_errno;
550
 
};
551
 
 
552
 
static struct errorentry errortable[] = {
553
 
    {ERROR_INVALID_FUNCTION, EINVAL},
554
 
    {ERROR_FILE_NOT_FOUND, ENOENT},
555
 
    {ERROR_PATH_NOT_FOUND, ENOENT},
556
 
    {ERROR_TOO_MANY_OPEN_FILES, EMFILE},
557
 
    {ERROR_ACCESS_DENIED, EACCES},
558
 
    {ERROR_INVALID_HANDLE, EBADF},
559
 
    {ERROR_ARENA_TRASHED, ENOMEM},
560
 
    {ERROR_NOT_ENOUGH_MEMORY, ENOMEM},
561
 
    {ERROR_INVALID_BLOCK, ENOMEM},
562
 
    {ERROR_BAD_ENVIRONMENT, E2BIG},
563
 
    {ERROR_BAD_FORMAT, ENOEXEC},
564
 
    {ERROR_INVALID_ACCESS, EINVAL},
565
 
    {ERROR_INVALID_DATA, EINVAL},
566
 
    {ERROR_INVALID_DRIVE, ENOENT},
567
 
    {ERROR_CURRENT_DIRECTORY, EACCES},
568
 
    {ERROR_NOT_SAME_DEVICE, EXDEV},
569
 
    {ERROR_NO_MORE_FILES, ENOENT},
570
 
    {ERROR_LOCK_VIOLATION, EACCES},
571
 
    {ERROR_BAD_NETPATH, ENOENT},
572
 
    {ERROR_NETWORK_ACCESS_DENIED, EACCES},
573
 
    {ERROR_BAD_NET_NAME, ENOENT},
574
 
    {ERROR_FILE_EXISTS, EEXIST},
575
 
    {ERROR_CANNOT_MAKE, EACCES},
576
 
    {ERROR_FAIL_I24, EACCES},
577
 
    {ERROR_INVALID_PARAMETER, EINVAL},
578
 
    {ERROR_NO_PROC_SLOTS, EAGAIN},
579
 
    {ERROR_DRIVE_LOCKED, EACCES},
580
 
    {ERROR_BROKEN_PIPE, EPIPE},
581
 
    {ERROR_DISK_FULL, ENOSPC},
582
 
    {ERROR_INVALID_TARGET_HANDLE, EBADF},
583
 
    {ERROR_INVALID_HANDLE, EINVAL},
584
 
    {ERROR_WAIT_NO_CHILDREN, ECHILD},
585
 
    {ERROR_CHILD_NOT_COMPLETE, ECHILD},
586
 
    {ERROR_DIRECT_ACCESS_HANDLE, EBADF},
587
 
    {ERROR_NEGATIVE_SEEK, EINVAL},
588
 
    {ERROR_SEEK_ON_DEVICE, EACCES},
589
 
    {ERROR_DIR_NOT_EMPTY, ENOTEMPTY},
590
 
    {ERROR_NOT_LOCKED, EACCES},
591
 
    {ERROR_BAD_PATHNAME, ENOENT},
592
 
    {ERROR_MAX_THRDS_REACHED, EAGAIN},
593
 
    {ERROR_LOCK_FAILED, EACCES},
594
 
    {ERROR_ALREADY_EXISTS, EEXIST},
595
 
    {ERROR_FILENAME_EXCED_RANGE, ENOENT},
596
 
    {ERROR_NESTING_NOT_ALLOWED, EAGAIN},
597
 
    {ERROR_NOT_ENOUGH_QUOTA, ENOMEM}
598
 
};
599
 
 
600
 
#define MIN_EXEC_ERROR ERROR_INVALID_STARTING_CODESEG
601
 
#define MAX_EXEC_ERROR ERROR_INFLOOP_IN_RELOC_CHAIN
602
 
 
603
 
#define MIN_EACCES_RANGE ERROR_WRITE_PROTECT
604
 
#define MAX_EACCES_RANGE ERROR_SHARING_BUFFER_EXCEEDED
605
 
 
606
 
void
607
 
WIN32_maperror(unsigned long WIN32_oserrno)
608
 
{
609
 
    int i;
610
 
 
611
 
    _doserrno = WIN32_oserrno;
612
 
    for (i = 0; i < (sizeof(errortable) / sizeof(struct errorentry)); ++i) {
613
 
        if (WIN32_oserrno == errortable[i].WIN32_code) {
614
 
            errno = errortable[i].POSIX_errno;
615
 
            return;
616
 
        }
617
 
    }
618
 
    if (WIN32_oserrno >= MIN_EACCES_RANGE && WIN32_oserrno <= MAX_EACCES_RANGE)
619
 
        errno = EACCES;
620
 
    else if (WIN32_oserrno >= MIN_EXEC_ERROR && WIN32_oserrno <= MAX_EXEC_ERROR)
621
 
        errno = ENOEXEC;
622
 
    else
623
 
        errno = EINVAL;
624
 
}
625
 
#endif