Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014 #ifdef WIN32
00015
00016 #ifndef FRONTEND
00017 #include "postgres.h"
00018 #else
00019 #include "postgres_fe.h"
00020 #endif
00021
00022 #include <windows.h>
00023 #include <fcntl.h>
00024 #include <assert.h>
00025
00026
00027 static int
00028 openFlagsToCreateFileFlags(int openFlags)
00029 {
00030 switch (openFlags & (O_CREAT | O_TRUNC | O_EXCL))
00031 {
00032
00033 case 0:
00034 case O_EXCL:
00035 return OPEN_EXISTING;
00036
00037 case O_CREAT:
00038 return OPEN_ALWAYS;
00039
00040
00041 case O_TRUNC:
00042 case O_TRUNC | O_EXCL:
00043 return TRUNCATE_EXISTING;
00044
00045 case O_CREAT | O_TRUNC:
00046 return CREATE_ALWAYS;
00047
00048
00049 case O_CREAT | O_EXCL:
00050 case O_CREAT | O_TRUNC | O_EXCL:
00051 return CREATE_NEW;
00052 }
00053
00054
00055 return 0;
00056 }
00057
00058
00059
00060
00061 int
00062 pgwin32_open(const char *fileName, int fileFlags,...)
00063 {
00064 int fd;
00065 HANDLE h = INVALID_HANDLE_VALUE;
00066 SECURITY_ATTRIBUTES sa;
00067 int loops = 0;
00068
00069
00070 assert((fileFlags & ((O_RDONLY | O_WRONLY | O_RDWR) | O_APPEND |
00071 (O_RANDOM | O_SEQUENTIAL | O_TEMPORARY) |
00072 _O_SHORT_LIVED | O_DSYNC | O_DIRECT |
00073 (O_CREAT | O_TRUNC | O_EXCL) | (O_TEXT | O_BINARY))) == fileFlags);
00074
00075 sa.nLength = sizeof(sa);
00076 sa.bInheritHandle = TRUE;
00077 sa.lpSecurityDescriptor = NULL;
00078
00079 while ((h = CreateFile(fileName,
00080
00081 (fileFlags & O_RDWR) ? (GENERIC_WRITE | GENERIC_READ) :
00082 ((fileFlags & O_WRONLY) ? GENERIC_WRITE : GENERIC_READ),
00083
00084 (FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE),
00085 &sa,
00086 openFlagsToCreateFileFlags(fileFlags),
00087 FILE_ATTRIBUTE_NORMAL |
00088 ((fileFlags & O_RANDOM) ? FILE_FLAG_RANDOM_ACCESS : 0) |
00089 ((fileFlags & O_SEQUENTIAL) ? FILE_FLAG_SEQUENTIAL_SCAN : 0) |
00090 ((fileFlags & _O_SHORT_LIVED) ? FILE_ATTRIBUTE_TEMPORARY : 0) |
00091 ((fileFlags & O_TEMPORARY) ? FILE_FLAG_DELETE_ON_CLOSE : 0) |
00092 ((fileFlags & O_DIRECT) ? FILE_FLAG_NO_BUFFERING : 0) |
00093 ((fileFlags & O_DSYNC) ? FILE_FLAG_WRITE_THROUGH : 0),
00094 NULL)) == INVALID_HANDLE_VALUE)
00095 {
00096
00097
00098
00099
00100
00101 DWORD err = GetLastError();
00102
00103 if (err == ERROR_SHARING_VIOLATION ||
00104 err == ERROR_LOCK_VIOLATION)
00105 {
00106 pg_usleep(100000);
00107 loops++;
00108
00109 #ifndef FRONTEND
00110 if (loops == 50)
00111 ereport(LOG,
00112 (errmsg("could not open file \"%s\": %s", fileName,
00113 (err == ERROR_SHARING_VIOLATION) ? _("sharing violation") : _("lock violation")),
00114 errdetail("Continuing to retry for 30 seconds."),
00115 errhint("You might have antivirus, backup, or similar software interfering with the database system.")));
00116 #endif
00117
00118 if (loops < 300)
00119 continue;
00120 }
00121
00122 _dosmaperr(err);
00123 return -1;
00124 }
00125
00126
00127 if ((fd = _open_osfhandle((intptr_t) h, fileFlags & O_APPEND)) < 0)
00128 CloseHandle(h);
00129 else if (fileFlags & (O_TEXT | O_BINARY) &&
00130 _setmode(fd, fileFlags & (O_TEXT | O_BINARY)) < 0)
00131 {
00132 _close(fd);
00133 return -1;
00134 }
00135
00136 return fd;
00137 }
00138
00139 FILE *
00140 pgwin32_fopen(const char *fileName, const char *mode)
00141 {
00142 int openmode = 0;
00143 int fd;
00144
00145 if (strstr(mode, "r+"))
00146 openmode |= O_RDWR;
00147 else if (strchr(mode, 'r'))
00148 openmode |= O_RDONLY;
00149 if (strstr(mode, "w+"))
00150 openmode |= O_RDWR | O_CREAT | O_TRUNC;
00151 else if (strchr(mode, 'w'))
00152 openmode |= O_WRONLY | O_CREAT | O_TRUNC;
00153 if (strchr(mode, 'a'))
00154 openmode |= O_WRONLY | O_CREAT | O_APPEND;
00155
00156 if (strchr(mode, 'b'))
00157 openmode |= O_BINARY;
00158 if (strchr(mode, 't'))
00159 openmode |= O_TEXT;
00160
00161 fd = pgwin32_open(fileName, openmode);
00162 if (fd == -1)
00163 return NULL;
00164 return _fdopen(fd, mode);
00165 }
00166
00167 #endif