📄 gdk_posix.mx
字号:
int error = GetLastError(); if (error && error != ERROR_INVALID_HANDLE) SetLastError(ERROR_OPEN_FAILED); /* enforce EIO */ return -1; } return 0;}#endif#ifndef HAVE_OPENDIRDIR *opendir(const char *dirname){ DIR *result = NULL; char *mask; size_t k; if (dirname == NULL) return NULL; result = (DIR *) malloc(sizeof(DIR)); result->find_file_data = malloc(sizeof(WIN32_FIND_DATA)); result->dir_name = strdup(dirname); k = strlen(result->dir_name); if (k && result->dir_name[k - 1] == '\\') { result->dir_name[k - 1] = '\0'; k--; } mask = malloc(strlen(result->dir_name) + 3); sprintf(mask, "%s\\*", result->dir_name); result->find_file_handle = (unsigned int) FindFirstFile(mask, (LPWIN32_FIND_DATA) result->find_file_data); free(mask); if (result->find_file_handle == (unsigned int) INVALID_HANDLE_VALUE) { free(result->dir_name); free(result->find_file_data); free(result); SetLastError(ERROR_OPEN_FAILED); /* enforce EIO */ return NULL; } result->just_opened = TRUE; return result;}static char *basename(const char *file_name){ register char *base; if (file_name == NULL) return NULL; base = strrchr(file_name, '\\'); if (base) return base + 1; if (isalpha(file_name[0]) && file_name[1] == ':') return (char *) file_name + 2; return (char *) file_name;}struct direct *readdir(DIR *dir){ static struct direct result; if (dir == NULL) return NULL; if (dir->just_opened) dir->just_opened = FALSE; else { if (!FindNextFile((HANDLE) dir->find_file_handle, (LPWIN32_FIND_DATA) dir->find_file_data)) { int error = GetLastError(); if (error) { if (error != ERROR_NO_MORE_FILES) SetLastError(ERROR_OPEN_FAILED); /* enforce EIO */ return NULL; } } } strcpy(result.d_name, basename(((LPWIN32_FIND_DATA) dir->find_file_data)->cFileName)); result.d_namelen = (int) strlen(result.d_name); return &result;}voidrewinddir(DIR *dir){ char *mask; if (dir == NULL) return; if (!FindClose((HANDLE) dir->find_file_handle)) stream_printf(GDKerr, "rewinddir(): FindClose() failed\n"); mask = malloc(strlen(dir->dir_name) + 3); sprintf(mask, "%s\\*", dir->dir_name); dir->find_file_handle = (unsigned int) FindFirstFile(mask, (LPWIN32_FIND_DATA) dir->find_file_data); free(mask); if (dir->find_file_handle == (unsigned int) INVALID_HANDLE_VALUE) { SetLastError(ERROR_OPEN_FAILED); /* enforce EIO */ return; } dir->just_opened = TRUE;}intclosedir(DIR *dir){ if (dir == NULL) return -1; if (!FindClose((HANDLE) dir->find_file_handle)) { SetLastError(ERROR_OPEN_FAILED); /* enforce EIO */ return -1; } free(dir->dir_name); free(dir->find_file_data); free(dir); return 0;}#endif /* HAVE_OPENDIR */#ifndef HAVE_GETTIMEOFDAYstatic int nodays[12] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };#define LEAPYEAR(y) ((((y)%4)==0 && ((y)%100)!=0) || ((y)%400)==0)#define NODAYS(m,y) (((m)!=2)?nodays[(m)-1]:LEAPYEAR(y)?29:28)intgettimeofday(struct timeval *tv, int *ignore_zone){ unsigned int year, day, month; SYSTEMTIME st; (void) ignore_zone; GetSystemTime(&st); day = 0; for (year = 1970; year < st.wYear; year++) day += LEAPYEAR(year) ? 366 : 365; for (month = 1; month < st.wMonth; month++) day += NODAYS(month, st.wYear); day += st.wDay; tv->tv_sec = 60 * (day * 24 * 60 + st.wMinute) + st.wSecond; tv->tv_usec = 1000 * st.wMilliseconds; return 0;}#endifvoid *dlopen(const char *file, int mode){ (void) mode; if (file != NULL) { return (void *) LoadLibrary(file); } return GetModuleHandle(NULL);}intdlclose(void *handle){ if (handle != NULL) { return FreeLibrary((HINSTANCE) handle); } return -1;}void *dlsym(void *handle, const char *name){ if (handle != NULL) { return (void *) GetProcAddress((HINSTANCE) handle, name); } return NULL;}char *dlerror(void){ static char msg[1024]; FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM, NULL, GetLastError(), 0, msg, sizeof(msg), NULL); return msg;}/* dir manipulations fail in WIN32 if file name contains trailing * slashes; work around this */static char *reduce_dir_name(const char *src, char *dst, size_t cap){ size_t len = strlen(src); char *buf = dst; if (len >= cap) buf = malloc(len + 1); while (--len > 0 && src[len - 1] != ':' && src[len] == DIR_SEP) ; for (buf[++len] = 0; len > 0; buf[len] = src[len]) len--; return buf;}intwin_stat(const char *pathname, struct stat *st){ char buf[128], *p = reduce_dir_name(pathname, buf, sizeof(buf)); int ret = stat(p, st); if (p != buf) free(p); return ret;}intwin_rmdir(const char *pathname){ char buf[128], *p = reduce_dir_name(pathname, buf, sizeof(buf)); int ret = _rmdir(p); if (p != buf) free(p); return ret;}intwin_mkdir(const char *pathname, const int mode){ char buf[128], *p = reduce_dir_name(pathname, buf, sizeof(buf)); int ret = _mkdir(p); (void)mode; if (p != buf) free(p); return ret;}#if _WIN32_WINNT >= 0x500/* NTFS does support symbolic links */int win_link(const char* oldpath, const char* newpath) { return CreateHardLink(newpath, oldpath, NULL)?-1:0;} #endiftypedef struct { int w; /* windows version of error */ const char *s; /* text of windows version */ int e; /* errno version of error */} win_errmap_t;#ifndef EBADRQC#define EBADRQC 56#endif#ifndef ENODATA#define ENODATA 61#endif#ifndef ENONET#define ENONET 64#endif#ifndef ENOTUNIQ#define ENOTUNIQ 76#endif#ifndef ECOMM#define ECOMM 70#endif#ifndef ENOLINK#define ENOLINK 67#endifwin_errmap_t win_errmap[] = { {ERROR_INVALID_FUNCTION, "ERROR_INVALID_FUNCTION", EBADRQC}, {ERROR_FILE_NOT_FOUND, "ERROR_FILE_NOT_FOUND", ENOENT}, {ERROR_PATH_NOT_FOUND, "ERROR_PATH_NOT_FOUND", ENOENT}, {ERROR_TOO_MANY_OPEN_FILES, "ERROR_TOO_MANY_OPEN_FILES", EMFILE}, {ERROR_ACCESS_DENIED, "ERROR_ACCESS_DENIED", EACCES}, {ERROR_INVALID_HANDLE, "ERROR_INVALID_HANDLE", EBADF}, {ERROR_NOT_ENOUGH_MEMORY, "ERROR_NOT_ENOUGH_MEMORY", ENOMEM}, {ERROR_INVALID_DATA, "ERROR_INVALID_DATA", EINVAL}, {ERROR_OUTOFMEMORY, "ERROR_OUTOFMEMORY", ENOMEM}, {ERROR_INVALID_DRIVE, "ERROR_INVALID_DRIVE", ENODEV}, {ERROR_NOT_SAME_DEVICE, "ERROR_NOT_SAME_DEVICE", EXDEV}, {ERROR_NO_MORE_FILES, "ERROR_NO_MORE_FILES", ENFILE}, {ERROR_WRITE_PROTECT, "ERROR_WRITE_PROTECT", EROFS}, {ERROR_BAD_UNIT, "ERROR_BAD_UNIT", ENODEV}, {ERROR_SHARING_VIOLATION, "ERROR_SHARING_VIOLATION", EACCES}, {ERROR_LOCK_VIOLATION, "ERROR_LOCK_VIOLATION", EACCES}, {ERROR_SHARING_BUFFER_EXCEEDED, "ERROR_SHARING_BUFFER_EXCEEDED", ENOLCK}, {ERROR_HANDLE_EOF, "ERROR_HANDLE_EOF", ENODATA}, {ERROR_HANDLE_DISK_FULL, "ERROR_HANDLE_DISK_FULL", ENOSPC}, {ERROR_NOT_SUPPORTED, "ERROR_NOT_SUPPORTED", ENOSYS}, {ERROR_REM_NOT_LIST, "ERROR_REM_NOT_LIST", ENONET}, {ERROR_DUP_NAME, "ERROR_DUP_NAME", ENOTUNIQ}, {ERROR_BAD_NETPATH, "ERROR_BAD_NETPATH", ENXIO}, {ERROR_FILE_EXISTS, "ERROR_FILE_EXISTS", EEXIST}, {ERROR_CANNOT_MAKE, "ERROR_CANNOT_MAKE", EPERM}, {ERROR_INVALID_PARAMETER, "ERROR_INVALID_PARAMETER", EINVAL}, {ERROR_NO_PROC_SLOTS, "ERROR_NO_PROC_SLOTS", EAGAIN}, {ERROR_BROKEN_PIPE, "ERROR_BROKEN_PIPE", EPIPE}, {ERROR_OPEN_FAILED, "ERROR_OPEN_FAILED", EIO}, {ERROR_NO_MORE_SEARCH_HANDLES, "ERROR_NO_MORE_SEARCH_HANDLES", ENFILE}, {ERROR_CALL_NOT_IMPLEMENTED, "ERROR_CALL_NOT_IMPLEMENTED", ENOSYS}, {ERROR_INVALID_NAME, "ERROR_INVALID_NAME", ENOENT}, {ERROR_WAIT_NO_CHILDREN, "ERROR_WAIT_NO_CHILDREN", ECHILD}, {ERROR_CHILD_NOT_COMPLETE, "ERROR_CHILD_NOT_COMPLETE", EBUSY}, {ERROR_DIR_NOT_EMPTY, "ERROR_DIR_NOT_EMPTY", ENOTEMPTY}, {ERROR_SIGNAL_REFUSED, "ERROR_SIGNAL_REFUSED", EIO}, {ERROR_BAD_PATHNAME, "ERROR_BAD_PATHNAME", EINVAL}, {ERROR_SIGNAL_PENDING, "ERROR_SIGNAL_PENDING", EBUSY}, {ERROR_MAX_THRDS_REACHED, "ERROR_MAX_THRDS_REACHED", EAGAIN}, {ERROR_BUSY, "ERROR_BUSY", EBUSY}, {ERROR_ALREADY_EXISTS, "ERROR_ALREADY_EXISTS", EEXIST}, {ERROR_NO_SIGNAL_SENT, "ERROR_NO_SIGNAL_SENT", EIO}, {ERROR_FILENAME_EXCED_RANGE, "ERROR_FILENAME_EXCED_RANGE", EINVAL}, {ERROR_META_EXPANSION_TOO_LONG, "ERROR_META_EXPANSION_TOO_LONG", EINVAL}, {ERROR_INVALID_SIGNAL_NUMBER, "ERROR_INVALID_SIGNAL_NUMBER", EINVAL}, {ERROR_THREAD_1_INACTIVE, "ERROR_THREAD_1_INACTIVE", EINVAL}, {ERROR_BAD_PIPE, "ERROR_BAD_PIPE", EINVAL}, {ERROR_PIPE_BUSY, "ERROR_PIPE_BUSY", EBUSY}, {ERROR_NO_DATA, "ERROR_NO_DATA", EPIPE}, {ERROR_PIPE_NOT_CONNECTED, "ERROR_PIPE_NOT_CONNECTED", ECOMM}, {ERROR_MORE_DATA, "ERROR_MORE_DATA", EAGAIN}, {ERROR_DIRECTORY, "ERROR_DIRECTORY", EISDIR}, {ERROR_PIPE_CONNECTED, "ERROR_PIPE_CONNECTED", EBUSY}, {ERROR_PIPE_LISTENING, "ERROR_PIPE_LISTENING", ECOMM}, {ERROR_NO_TOKEN, "ERROR_NO_TOKEN", EINVAL}, {ERROR_PROCESS_ABORTED, "ERROR_PROCESS_ABORTED", EFAULT}, {ERROR_BAD_DEVICE, "ERROR_BAD_DEVICE", ENODEV}, {ERROR_BAD_USERNAME, "ERROR_BAD_USERNAME", EINVAL}, {ERROR_NOT_CONNECTED, "ERROR_NOT_CONNECTED", ENOLINK}, {ERROR_OPEN_FILES, "ERROR_OPEN_FILES", EAGAIN}, {ERROR_ACTIVE_CONNECTIONS, "ERROR_ACTIVE_CONNECTIONS", EAGAIN}, {ERROR_DEVICE_IN_USE, "ERROR_DEVICE_IN_USE", EAGAIN}, {ERROR_INVALID_AT_INTERRUPT_TIME, "ERROR_INVALID_AT_INTERRUPT_TIME", EINTR}, {ERROR_IO_DEVICE, "ERROR_IO_DEVICE", EIO},};#define GDK_WIN_ERRNO_TLS 13@h#define _errno win_errnogdk_export int *win_errno(void);@cint *win_errno(void){ /* get address of thread-local Posix errno; refresh its value from WIN32 error code */ int i, err = GetLastError() & 0xff; int *result = TlsGetValue(GDK_WIN_ERRNO_TLS); if (result == NULL) { result = (int *) malloc(sizeof(int)); *result = 0; TlsSetValue(GDK_WIN_ERRNO_TLS, result); } for (i = 0; win_errmap[i].w != 0; ++i) { if (err == win_errmap[i].w) { *result = win_errmap[i].e; break; } } SetLastError(err); return result;}#endif#ifndef WIN32#define MT_PAGESIZE(s) ((((s-1)/MT_pagesize())+1)*MT_pagesize())#if defined(MAP_ANON)#define MMAP_FLAGS(f) f|MAP_ANON#define MMAP_FD -1#define MMAP_OPEN_DEV_ZERO int fd = 1#define MMAP_CLOSE_DEV_ZERO (void)fd#else#define MMAP_FLAGS(f) f#define MMAP_FD fd#define MMAP_OPEN_DEV_ZERO int fd = open("/dev/zero", O_RDWR, 0666)#define MMAP_CLOSE_DEV_ZERO close(fd)#endifvoid *MT_vmalloc(size_t size, size_t * maxsize){ MMAP_OPEN_DEV_ZERO; char *q, *r = (char *) -1L; if (fd < 0) { return NULL; } size = MT_PAGESIZE(size); *maxsize = MT_PAGESIZE(*maxsize); if (*maxsize > size) { r = (char *) mmap(NULL, *maxsize, PROT_NONE, MMAP_FLAGS(MAP_PRIVATE | MAP_NORESERVE), MMAP_FD, 0); } if (r == (char *) -1L) { *maxsize = size; q = (char *) mmap(NULL, size, PROT_READ | PROT_WRITE, MMAP_FLAGS(MAP_PRIVATE), MMAP_FD, 0); } else { q = (char *) mmap(r, size, PROT_READ | PROT_WRITE, MMAP_FLAGS(MAP_PRIVATE | MAP_FIXED), MMAP_FD, 0); } if (q != (char *) -1L) { (void) MT_mmap_new("anonymous vm", q, *maxsize, -1, 1); } MMAP_CLOSE_DEV_ZERO; return (void *) ((q == (char *) -1L) ? NULL : q);}voidMT_vmfree(void *p, size_t size){ MT_mmap_del(p, size); size = MT_PAGESIZE(size); munmap(p, size);}void *MT_vmrealloc(void *voidptr, size_t oldsize, size_t newsize, size_t oldmaxsize, size_t * newmaxsize){ char *p = (char *) voidptr; char *q = (char *) -1L; /* sanitize sizes */ oldsize = MT_PAGESIZE(oldsize); newsize = MT_PAGESIZE(newsize); oldmaxsize = MT_PAGESIZE(oldmaxsize); *newmaxsize = MT_PAGESIZE(*newmaxsize); if (*newmaxsize < newsize) { *newmaxsize = newsize; } if (oldsize > newsize) { munmap(p + oldsize, oldsize - newsize); } else if (oldsize < newsize) { if (newsize < oldmaxsize) { MMAP_OPEN_DEV_ZERO; if (fd >= 0) { q = (char *) mmap(p + oldsize, newsize - oldsize, PROT_READ | PROT_WRITE, MMAP_FLAGS(MAP_PRIVATE | MAP_FIXED), MMAP_FD, (off_t) oldsize); MMAP_CLOSE_DEV_ZERO; } } if (q == (char *) -1L) { q = (char *) MT_vmalloc(newsize, newmaxsize); if (q != NULL) { memcpy(q, p, oldsize); MT_vmfree(p, oldmaxsize); return q; } } } *newmaxsize = MAX(oldmaxsize, newsize); return p;}#if defined(HAVE_LOCKF) && defined(__MACH__)/* lockf() seems to be there, but I didn't find any header file that declares the prototype ... */extern int lockf(int fd, int cmd, off_t len);#endif#ifndef HAVE_LOCKF
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -