27 #define alloca(x) _alloca(x) |
27 #define alloca(x) _alloca(x) |
28 #elif (defined MINGW) /* scary...hopefully this is okay. */ |
28 #elif (defined MINGW) /* scary...hopefully this is okay. */ |
29 #define alloca(x) __builtin_alloca(x) |
29 #define alloca(x) __builtin_alloca(x) |
30 #endif |
30 #endif |
31 |
31 |
32 #define LOWORDER_UINT64(pos) (PHYSFS_uint32)(pos & 0x00000000FFFFFFFF) |
32 #define LOWORDER_UINT64(pos) (PHYSFS_uint32) \ |
33 #define HIGHORDER_UINT64(pos) (PHYSFS_uint32)(pos & 0xFFFFFFFF00000000) |
33 (pos & 0x00000000FFFFFFFF) |
|
34 #define HIGHORDER_UINT64(pos) (PHYSFS_uint32) \ |
|
35 (((pos & 0xFFFFFFFF00000000) >> 32) & 0x00000000FFFFFFFF) |
34 |
36 |
35 /* GetUserProfileDirectory() is only available on >= NT4 (no 9x/ME systems!) */ |
37 /* GetUserProfileDirectory() is only available on >= NT4 (no 9x/ME systems!) */ |
36 typedef BOOL (STDMETHODCALLTYPE FAR * LPFNGETUSERPROFILEDIR) ( |
38 typedef BOOL (STDMETHODCALLTYPE FAR * LPFNGETUSERPROFILEDIR) ( |
37 HANDLE hToken, |
39 HANDLE hToken, |
38 LPTSTR lpProfileDir, |
40 LPTSTR lpProfileDir, |
58 /* |
60 /* |
59 * Users without the platform SDK don't have this defined. The original docs |
61 * Users without the platform SDK don't have this defined. The original docs |
60 * for SetFilePointer() just said to compare with 0xFFFFFFFF, so this should |
62 * for SetFilePointer() just said to compare with 0xFFFFFFFF, so this should |
61 * work as desired |
63 * work as desired |
62 */ |
64 */ |
63 #ifndef INVALID_SET_FILE_POINTER |
65 #define PHYSFS_INVALID_SET_FILE_POINTER 0xFFFFFFFF |
64 # define INVALID_SET_FILE_POINTER 0xFFFFFFFF |
|
65 #endif |
|
66 |
66 |
67 /* just in case... */ |
67 /* just in case... */ |
68 #ifndef INVALID_FILE_ATTRIBUTES |
68 #define PHYSFS_INVALID_FILE_ATTRIBUTES 0xFFFFFFFF |
69 # define INVALID_FILE_ATTRIBUTES 0xFFFFFFFF |
69 |
70 #endif |
|
71 |
70 |
72 |
71 |
73 /* |
72 /* |
74 * Figure out what the last failing Win32 API call was, and |
73 * Figure out what the last failing Win32 API call was, and |
75 * generate a human-readable string for the error message. |
74 * generate a human-readable string for the error message. |
254 { |
253 { |
255 UINT oldErrorMode; |
254 UINT oldErrorMode; |
256 DWORD tmp; |
255 DWORD tmp; |
257 BOOL retval; |
256 BOOL retval; |
258 |
257 |
259 /* Prevent windows warning message to appear when checking media size */ |
258 /* Prevent windows warning message appearing when checking media size */ |
260 oldErrorMode = SetErrorMode(SEM_FAILCRITICALERRORS); |
259 oldErrorMode = SetErrorMode(SEM_FAILCRITICALERRORS); |
261 |
260 |
262 /* If this function succeeds, there's media in the drive */ |
261 /* If this function succeeds, there's media in the drive */ |
263 retval = GetVolumeInformation(drive, NULL, 0, NULL, NULL, &tmp, NULL, 0); |
262 retval = GetVolumeInformation(drive, NULL, 0, NULL, NULL, &tmp, NULL, 0); |
264 |
263 |
396 } /* __PHYSFS_platformStricmp */ |
395 } /* __PHYSFS_platformStricmp */ |
397 |
396 |
398 |
397 |
399 int __PHYSFS_platformExists(const char *fname) |
398 int __PHYSFS_platformExists(const char *fname) |
400 { |
399 { |
401 BAIL_IF_MACRO(GetFileAttributes(fname) == INVALID_FILE_ATTRIBUTES, |
400 BAIL_IF_MACRO |
402 win32strerror(), 0); |
401 ( |
|
402 GetFileAttributes(fname) == PHYSFS_INVALID_FILE_ATTRIBUTES, |
|
403 win32strerror(), 0 |
|
404 ); |
403 return(1); |
405 return(1); |
404 } /* __PHYSFS_platformExists */ |
406 } /* __PHYSFS_platformExists */ |
405 |
407 |
406 |
408 |
407 int __PHYSFS_platformIsSymLink(const char *fname) |
409 int __PHYSFS_platformIsSymLink(const char *fname) |
477 |
479 |
478 /* Append the "*" to the end of the string */ |
480 /* Append the "*" to the end of the string */ |
479 strcat(SearchPath, "*"); |
481 strcat(SearchPath, "*"); |
480 |
482 |
481 dir = FindFirstFile(SearchPath, &ent); |
483 dir = FindFirstFile(SearchPath, &ent); |
482 BAIL_IF_MACRO(dir == INVALID_HANDLE_VALUE, win32strerror(), NULL); |
484 BAIL_IF_MACRO |
|
485 ( |
|
486 dir == PHYSFS_INVALID_HANDLE_VALUE, |
|
487 win32strerror(), NULL |
|
488 ); |
483 |
489 |
484 do |
490 do |
485 { |
491 { |
486 if (strcmp(ent.cFileName, ".") == 0) |
492 if (strcmp(ent.cFileName, ".") == 0) |
487 continue; |
493 continue; |
740 win32file *retval; |
746 win32file *retval; |
741 |
747 |
742 fileHandle = CreateFile(fname, mode, FILE_SHARE_READ, NULL, |
748 fileHandle = CreateFile(fname, mode, FILE_SHARE_READ, NULL, |
743 creation, FILE_ATTRIBUTE_NORMAL, NULL); |
749 creation, FILE_ATTRIBUTE_NORMAL, NULL); |
744 |
750 |
745 BAIL_IF_MACRO(fileHandle == INVALID_HANDLE_VALUE, win32strerror(), NULL); |
751 BAIL_IF_MACRO |
|
752 ( |
|
753 fileHandle == PHYSFS_INVALID_HANDLE_VALUE, |
|
754 win32strerror(), NULL |
|
755 ); |
746 |
756 |
747 retval = malloc(sizeof (win32file)); |
757 retval = malloc(sizeof (win32file)); |
748 if (retval == NULL) |
758 if (retval == NULL) |
749 { |
759 { |
750 CloseHandle(fileHandle); |
760 CloseHandle(fileHandle); |
773 { |
783 { |
774 void *retval = doOpen(filename, GENERIC_WRITE, OPEN_ALWAYS, 0); |
784 void *retval = doOpen(filename, GENERIC_WRITE, OPEN_ALWAYS, 0); |
775 if (retval != NULL) |
785 if (retval != NULL) |
776 { |
786 { |
777 HANDLE h = ((win32file *) retval)->handle; |
787 HANDLE h = ((win32file *) retval)->handle; |
778 if (SetFilePointer(h, 0, NULL, FILE_END) == INVALID_SET_FILE_POINTER) |
788 DWORD rc = SetFilePointer(h, 0, NULL, FILE_END); |
|
789 if (rc == PHYSFS_INVALID_SET_FILE_POINTER) |
779 { |
790 { |
780 const char *err = win32strerror(); |
791 const char *err = win32strerror(); |
781 CloseHandle(h); |
792 CloseHandle(h); |
782 free(retval); |
793 free(retval); |
783 BAIL_MACRO(err, NULL); |
794 BAIL_MACRO(err, NULL); |
838 |
849 |
839 int __PHYSFS_platformSeek(void *opaque, PHYSFS_uint64 pos) |
850 int __PHYSFS_platformSeek(void *opaque, PHYSFS_uint64 pos) |
840 { |
851 { |
841 HANDLE FileHandle = ((win32file *) opaque)->handle; |
852 HANDLE FileHandle = ((win32file *) opaque)->handle; |
842 DWORD HighOrderPos; |
853 DWORD HighOrderPos; |
|
854 DWORD *pHighOrderPos; |
843 DWORD rc; |
855 DWORD rc; |
844 |
856 |
845 /* Get the high order 32-bits of the position */ |
857 /* Get the high order 32-bits of the position */ |
846 HighOrderPos = HIGHORDER_UINT64(pos); |
858 HighOrderPos = HIGHORDER_UINT64(pos); |
847 |
859 |
848 /* !!! FIXME: SetFilePointer needs a signed 64-bit value. */ |
860 /* |
|
861 * MSDN: "If you do not need the high-order 32 bits, this |
|
862 * pointer must be set to NULL." |
|
863 */ |
|
864 pHighOrderPos = (HighOrderPos) ? &HighOrderPos : NULL; |
|
865 |
|
866 /* |
|
867 * !!! FIXME: MSDN: "Windows Me/98/95: If the pointer |
|
868 * !!! FIXME: lpDistanceToMoveHigh is not NULL, then it must |
|
869 * !!! FIXME: point to either 0, INVALID_SET_FILE_POINTER, or |
|
870 * !!! FIXME: the sign extension of the value of lDistanceToMove. |
|
871 * !!! FIXME: Any other value will be rejected." |
|
872 */ |
|
873 |
849 /* Move pointer "pos" count from start of file */ |
874 /* Move pointer "pos" count from start of file */ |
850 rc = SetFilePointer(FileHandle, LOWORDER_UINT64(pos), |
875 rc = SetFilePointer(FileHandle, LOWORDER_UINT64(pos), |
851 &HighOrderPos, FILE_BEGIN); |
876 pHighOrderPos, FILE_BEGIN); |
852 |
877 |
853 if ((rc == INVALID_SET_FILE_POINTER) && (GetLastError() != NO_ERROR)) |
878 if ( (rc == PHYSFS_INVALID_SET_FILE_POINTER) && |
|
879 (GetLastError() != NO_ERROR) ) |
|
880 { |
854 BAIL_MACRO(win32strerror(), 0); |
881 BAIL_MACRO(win32strerror(), 0); |
855 |
882 } /* if */ |
|
883 |
856 return(1); /* No error occured */ |
884 return(1); /* No error occured */ |
857 } /* __PHYSFS_platformSeek */ |
885 } /* __PHYSFS_platformSeek */ |
858 |
886 |
859 |
887 |
860 PHYSFS_sint64 __PHYSFS_platformTell(void *opaque) |
888 PHYSFS_sint64 __PHYSFS_platformTell(void *opaque) |
864 DWORD LowPos; |
892 DWORD LowPos; |
865 PHYSFS_sint64 retval; |
893 PHYSFS_sint64 retval; |
866 |
894 |
867 /* Get current position */ |
895 /* Get current position */ |
868 LowPos = SetFilePointer(FileHandle, 0, &HighPos, FILE_CURRENT); |
896 LowPos = SetFilePointer(FileHandle, 0, &HighPos, FILE_CURRENT); |
869 if ((LowPos == INVALID_SET_FILE_POINTER) && (GetLastError() != NO_ERROR)) |
897 if ( (LowPos == PHYSFS_INVALID_SET_FILE_POINTER) && |
|
898 (GetLastError() != NO_ERROR) ) |
870 { |
899 { |
871 BAIL_MACRO(win32strerror(), 0); |
900 BAIL_MACRO(win32strerror(), 0); |
872 } /* if */ |
901 } /* if */ |
873 else |
902 else |
874 { |
903 { |
887 DWORD SizeHigh; |
916 DWORD SizeHigh; |
888 DWORD SizeLow; |
917 DWORD SizeLow; |
889 PHYSFS_sint64 retval; |
918 PHYSFS_sint64 retval; |
890 |
919 |
891 SizeLow = GetFileSize(FileHandle, &SizeHigh); |
920 SizeLow = GetFileSize(FileHandle, &SizeHigh); |
892 if ((SizeLow == INVALID_SET_FILE_POINTER) && (GetLastError() != NO_ERROR)) |
921 if ( (SizeLow == PHYSFS_INVALID_SET_FILE_POINTER) && |
|
922 (GetLastError() != NO_ERROR) ) |
893 { |
923 { |
894 BAIL_MACRO(win32strerror(), -1); |
924 BAIL_MACRO(win32strerror(), -1); |
895 } /* if */ |
925 } /* if */ |
896 else |
926 else |
897 { |
927 { |