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_posix.c: memory-mapped file I/O support for POSIX systems */
36 /* */
37 /*************************************************************************/
38
39 #include <sys/types.h>
40 #include <sys/mman.h>
41 #include <sys/stat.h>
42 #include <fcntl.h>
43 #include <unistd.h>
44
45 #include "cst_file.h"
46 #include "cst_error.h"
47 #include "cst_alloc.h"
48
49
50 #ifdef __QNXNTO__
51 #include <sys/syspage.h>
52 #define getpagesize() (SYSPAGE_ENTRY( system_private )->PAGE_SIZE)
53 // #define getpagesize() (sysconf(_SC_PAGESIZE))
54 #else
55 #define MAP_NOSYNCFILE 0
56 #endif
57 // #define __page_size PAGE_SIZE
58
59
cst_mmap_file(const char * path)60 cst_filemap *cst_mmap_file(const char *path)
61 {
62 cst_filemap *fmap = NULL;
63 size_t pgsize;
64 struct stat buf;
65 int fd;
66 // unsigned int __page_size = PAGE_SIZE;
67
68
69 pgsize = getpagesize();
70 // pgsize = PAGE_SIZE;
71
72 if ((fd = open(path, O_RDONLY)) < 0) {
73 perror("cst_mmap_file: Failed to open file");
74 return NULL;
75 }
76 if ((fstat(fd, &buf)) < 0) {
77 perror("cst_mmap_file: fstat() failed");
78 return NULL;
79 }
80 fmap = cst_alloc(cst_filemap, 1);
81 fmap->fd = fd;
82 fmap->mapsize = (buf.st_size + pgsize - 1) / pgsize * pgsize;
83 if ((fmap->mem = mmap(0, fmap->mapsize, PROT_READ,
84 MAP_SHARED | MAP_NOSYNCFILE, fd, 0)) == (caddr_t)-1) {
85 perror("cst_mmap_file: mmap() failed");
86 cst_free(fmap);
87 return NULL;
88 }
89
90 return fmap;
91 }
92
cst_munmap_file(cst_filemap * fmap)93 int cst_munmap_file(cst_filemap *fmap)
94 {
95 if (munmap(fmap->mem, fmap->mapsize) < 0) {
96 perror("cst_munmap_file: munmap() failed");
97 return -1;
98 }
99 if (close(fmap->fd) < 0) {
100 perror("cst_munmap_file: close() failed");
101 return -1;
102 }
103 cst_free(fmap);
104 return 0;
105 }
106
cst_read_whole_file(const char * path)107 cst_filemap *cst_read_whole_file(const char *path)
108 {
109 cst_filemap *fmap;
110 struct stat buf;
111 int fd;
112
113 if ((fd = open(path, O_RDONLY)) < 0) {
114 perror("cst_read_whole_file: Failed to open file");
115 return NULL;
116 }
117 if ((fstat(fd, &buf)) < 0) {
118 perror("cst_read_whole_file: fstat() failed");
119 return NULL;
120 }
121
122 fmap = cst_alloc(cst_filemap, 1);
123 fmap->fd = fd;
124 fmap->mapsize = buf.st_size;
125 fmap->mem = cst_alloc(char, fmap->mapsize);
126 if ((int)read(fmap->fd, fmap->mem, fmap->mapsize) < (int)fmap->mapsize)
127 {
128 perror("cst_read_whole_file: read() failed");
129 close(fmap->fd);
130 cst_free(fmap->mem);
131 cst_free(fmap);
132 return NULL;
133 }
134
135 return fmap;
136 }
137
cst_free_whole_file(cst_filemap * fmap)138 int cst_free_whole_file(cst_filemap *fmap)
139 {
140 if (close(fmap->fd) < 0) {
141 perror("cst_free_whole_file: close() failed");
142 return -1;
143 }
144 cst_free(fmap->mem);
145 cst_free(fmap);
146 return 0;
147 }
148
cst_read_part_file(const char * path)149 cst_filemap *cst_read_part_file(const char *path)
150 {
151 cst_filemap *fmap;
152 struct stat buf;
153 cst_file fh;
154
155 if ((fh = cst_fopen(path, CST_OPEN_READ)) == NULL) {
156 perror("cst_read_part_file: Failed to open file");
157 return NULL;
158 }
159 if ((fstat(fileno(fh), &buf)) < 0) {
160 perror("cst_read_part_file: fstat() failed");
161 return NULL;
162 }
163
164 fmap = cst_alloc(cst_filemap, 1);
165 fmap->fh = fh;
166 fmap->mapsize = buf.st_size;
167
168 return fmap;
169 }
170
cst_free_part_file(cst_filemap * fmap)171 int cst_free_part_file(cst_filemap *fmap)
172 {
173 if (cst_fclose(fmap->fh) < 0) {
174 perror("cst_munmap_file: cst_fclose() failed");
175 return -1;
176 }
177 cst_free(fmap);
178 return 0;
179 }
180