q_shlinux.c (4121B)
1 #include <sys/types.h> 2 #include <errno.h> 3 #include <stdio.h> 4 #include <dirent.h> 5 #include <sys/stat.h> 6 #include <unistd.h> 7 #include <sys/mman.h> 8 #include <sys/time.h> 9 10 #include "../linux/glob.h" 11 12 #include "../qcommon/qcommon.h" 13 14 //=============================================================================== 15 16 byte *membase; 17 int maxhunksize; 18 int curhunksize; 19 20 void *Hunk_Begin (int maxsize) 21 { 22 // reserve a huge chunk of memory, but don't commit any yet 23 maxhunksize = maxsize + sizeof(int); 24 curhunksize = 0; 25 membase = mmap(0, maxhunksize, PROT_READ|PROT_WRITE, 26 MAP_PRIVATE|MAP_ANONYMOUS, -1, 0); 27 if (membase == NULL || membase == (byte *)-1) 28 Sys_Error("unable to virtual allocate %d bytes", maxsize); 29 30 *((int *)membase) = curhunksize; 31 32 return membase + sizeof(int); 33 } 34 35 void *Hunk_Alloc (int size) 36 { 37 byte *buf; 38 39 // round to cacheline 40 size = (size+31)&~31; 41 if (curhunksize + size > maxhunksize) 42 Sys_Error("Hunk_Alloc overflow"); 43 buf = membase + sizeof(int) + curhunksize; 44 curhunksize += size; 45 return buf; 46 } 47 48 int Hunk_End (void) 49 { 50 byte *n; 51 52 n = mremap(membase, maxhunksize, curhunksize + sizeof(int), 0); 53 if (n != membase) 54 Sys_Error("Hunk_End: Could not remap virtual block (%d)", errno); 55 *((int *)membase) = curhunksize + sizeof(int); 56 57 return curhunksize; 58 } 59 60 void Hunk_Free (void *base) 61 { 62 byte *m; 63 64 if (base) { 65 m = ((byte *)base) - sizeof(int); 66 if (munmap(m, *((int *)m))) 67 Sys_Error("Hunk_Free: munmap failed (%d)", errno); 68 } 69 } 70 71 //=============================================================================== 72 73 74 /* 75 ================ 76 Sys_Milliseconds 77 ================ 78 */ 79 int curtime; 80 int Sys_Milliseconds (void) 81 { 82 struct timeval tp; 83 struct timezone tzp; 84 static int secbase; 85 86 gettimeofday(&tp, &tzp); 87 88 if (!secbase) 89 { 90 secbase = tp.tv_sec; 91 return tp.tv_usec/1000; 92 } 93 94 curtime = (tp.tv_sec - secbase)*1000 + tp.tv_usec/1000; 95 96 return curtime; 97 } 98 99 void Sys_Mkdir (char *path) 100 { 101 mkdir (path, 0777); 102 } 103 104 char *strlwr (char *s) 105 { 106 while (*s) { 107 *s = tolower(*s); 108 s++; 109 } 110 } 111 112 //============================================ 113 114 static char findbase[MAX_OSPATH]; 115 static char findpath[MAX_OSPATH]; 116 static char findpattern[MAX_OSPATH]; 117 static DIR *fdir; 118 119 static qboolean CompareAttributes(char *path, char *name, 120 unsigned musthave, unsigned canthave ) 121 { 122 struct stat st; 123 char fn[MAX_OSPATH]; 124 125 // . and .. never match 126 if (strcmp(name, ".") == 0 || strcmp(name, "..") == 0) 127 return false; 128 129 sprintf(fn, "%s/%s", path, name); 130 if (stat(fn, &st) == -1) 131 return false; // shouldn't happen 132 133 if ( ( st.st_mode & S_IFDIR ) && ( canthave & SFF_SUBDIR ) ) 134 return false; 135 136 if ( ( musthave & SFF_SUBDIR ) && !( st.st_mode & S_IFDIR ) ) 137 return false; 138 139 return true; 140 } 141 142 char *Sys_FindFirst (char *path, unsigned musthave, unsigned canhave) 143 { 144 struct dirent *d; 145 char *p; 146 147 if (fdir) 148 Sys_Error ("Sys_BeginFind without close"); 149 150 // COM_FilePath (path, findbase); 151 strcpy(findbase, path); 152 153 if ((p = strrchr(findbase, '/')) != NULL) { 154 *p = 0; 155 strcpy(findpattern, p + 1); 156 } else 157 strcpy(findpattern, "*"); 158 159 if (strcmp(findpattern, "*.*") == 0) 160 strcpy(findpattern, "*"); 161 162 if ((fdir = opendir(findbase)) == NULL) 163 return NULL; 164 while ((d = readdir(fdir)) != NULL) { 165 if (!*findpattern || glob_match(findpattern, d->d_name)) { 166 // if (*findpattern) 167 // printf("%s matched %s\n", findpattern, d->d_name); 168 if (CompareAttributes(findbase, d->d_name, musthave, canhave)) { 169 sprintf (findpath, "%s/%s", findbase, d->d_name); 170 return findpath; 171 } 172 } 173 } 174 return NULL; 175 } 176 177 char *Sys_FindNext (unsigned musthave, unsigned canhave) 178 { 179 struct dirent *d; 180 181 if (fdir == NULL) 182 return NULL; 183 while ((d = readdir(fdir)) != NULL) { 184 if (!*findpattern || glob_match(findpattern, d->d_name)) { 185 // if (*findpattern) 186 // printf("%s matched %s\n", findpattern, d->d_name); 187 if (CompareAttributes(findbase, d->d_name, musthave, canhave)) { 188 sprintf (findpath, "%s/%s", findbase, d->d_name); 189 return findpath; 190 } 191 } 192 } 193 return NULL; 194 } 195 196 void Sys_FindClose (void) 197 { 198 if (fdir != NULL) 199 closedir(fdir); 200 fdir = NULL; 201 } 202 203 204 //============================================ 205