1 /*************************************************************************/
2 /*                                                                       */
3 /*                           Cepstral, LLC                               */
4 /*                        Copyright (c) 2001                             */
5 /*                        All Rights Reserved.                           */
6 /*                                                                       */
7 /*  Permission is hereby granted, free of charge, to use and distribute  */
8 /*  this software and its documentation without restriction, including   */
9 /*  without limitation the rights to use, copy, modify, merge, publish,  */
10 /*  distribute, sublicense, and/or sell copies of this work, and to      */
11 /*  permit persons to whom this work is furnished to do so, subject to   */
12 /*  the following conditions:                                            */
13 /*   1. The code must retain the above copyright notice, this list of    */
14 /*      conditions and the following disclaimer.                         */
15 /*   2. Any modifications must be clearly marked as such.                */
16 /*   3. Original authors' names are not deleted.                         */
17 /*   4. The authors' names are not used to endorse or promote products   */
18 /*      derived from this software without specific prior written        */
19 /*      permission.                                                      */
20 /*                                                                       */
21 /*  CEPSTRAL, LLC AND THE CONTRIBUTORS TO THIS WORK DISCLAIM ALL         */
22 /*  WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED       */
23 /*  WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL         */
24 /*  CEPSTRAL, LLC NOR THE CONTRIBUTORS BE LIABLE FOR ANY SPECIAL,        */
25 /*  INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER          */
26 /*  RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION    */
27 /*  OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR  */
28 /*  IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.          */
29 /*                                                                       */
30 /*************************************************************************/
31 /*             Author:  David Huggins-Daines (dhd@cepstral.com)          */
32 /*               Date:  October 2001                                     */
33 /*************************************************************************/
34 /*                                                                       */
35 /* cst_mmap_win32.c: memory-mapped file I/O support for Win32 systems    */
36 /*                                                                       */
37 /*************************************************************************/
38 
39 #include <windows.h>
40 
41 #ifndef MEM_TOP_DOWN
42 #define MEM_TOP_DOWN 0
43 #endif
44 
45 #include "cst_file.h"
46 #include "cst_error.h"
47 #include "cst_alloc.h"
48 
cst_mmap_file(const char * path)49 cst_filemap *cst_mmap_file(const char *path)
50 {
51 	HANDLE ffm;
52 	cst_filemap *fmap = NULL;
53 
54 	/* By default, CreateFile uses wide-char strings; this doesn't do the expected
55 	   thing when passed non-wide strings
56 
57 	   We're explicitly using the non-wide version of CreateFile to
58 	   sidestep this issue.  If you're having problems with unicode
59 	   pathnames, you'll need to change this to call CreateFileW (and
60 	   then ensure you're always passing a wide-char string). */
61 
62 	ffm = CreateFileA(path,GENERIC_READ,FILE_SHARE_READ,NULL,
63 			 OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL);
64 	if (ffm == INVALID_HANDLE_VALUE) {
65 		return NULL;
66 	} else {
67 		fmap = cst_alloc(cst_filemap,1);
68 		fmap->h = CreateFileMapping(ffm,NULL,PAGE_READONLY,0,0,NULL);
69 		fmap->mapsize = GetFileSize(fmap->h, NULL);
70 		fmap->mem = MapViewOfFile(fmap->h,FILE_MAP_READ,0,0,0);
71 		if (fmap->h == NULL || fmap->mem == NULL) {
72 			CloseHandle(ffm);
73 			cst_free(fmap);
74 			return NULL;
75 		}
76 	}
77 
78 	return fmap;
79 }
80 
cst_munmap_file(cst_filemap * fmap)81 int cst_munmap_file(cst_filemap *fmap)
82 {
83 	UnmapViewOfFile(fmap->mem);
84 	CloseHandle(fmap->h);
85 	cst_free(fmap);
86 	return 0;
87 }
88 
cst_read_whole_file(const char * path)89 cst_filemap *cst_read_whole_file(const char *path)
90 {
91     cst_filemap *fmap;
92     cst_file fh;
93 
94     if ((fh = cst_fopen(path, CST_OPEN_READ)) == NULL) {
95 	cst_errmsg("cst_read_whole_file: Failed to open file\n");
96 	return NULL;
97     }
98 
99     fmap = cst_alloc(cst_filemap, 1);
100     fmap->fh = fh;
101     cst_fseek(fmap->fh, 0, CST_SEEK_ENDREL);
102     fmap->mapsize = cst_ftell(fmap->fh);
103     fmap->mem = VirtualAlloc(NULL, fmap->mapsize, MEM_COMMIT|MEM_TOP_DOWN,
104 			     PAGE_READWRITE);
105     cst_fseek(fmap->fh, 0, CST_SEEK_ABSOLUTE);
106     cst_fread(fmap->fh, fmap->mem, 1, fmap->mapsize);
107 
108     return fmap;
109 }
110 
cst_free_whole_file(cst_filemap * fmap)111 int cst_free_whole_file(cst_filemap *fmap)
112 {
113     if (cst_fclose(fmap->fh) < 0) {
114 	cst_errmsg("cst_read_whole_file: cst_fclose() failed\n");
115 	return -1;
116     }
117     VirtualFree(fmap->mem, fmap->mapsize, MEM_DECOMMIT);
118     cst_free(fmap);
119     return 0;
120 }
121 
cst_read_part_file(const char * path)122 cst_filemap *cst_read_part_file(const char *path)
123 {
124     cst_filemap *fmap;
125     cst_file fh;
126 
127     if ((fh = cst_fopen(path, CST_OPEN_READ)) == NULL) {
128 	cst_errmsg("cst_read_part_file: Failed to open file\n");
129 	return NULL;
130     }
131 
132     fmap = cst_alloc(cst_filemap, 1);
133     fmap->fh = fh;
134 
135     return fmap;
136 }
137 
cst_free_part_file(cst_filemap * fmap)138 int cst_free_part_file(cst_filemap *fmap)
139 {
140     if (cst_fclose(fmap->fh) < 0) {
141 	cst_errmsg("cst_read_part_file: cst_fclose() failed\n");
142 	return -1;
143     }
144     cst_free(fmap);
145     return 0;
146 }
147