| /*
|
| Copyright (C) 1996-1997 Id Software, Inc.
|
|
|
| This program is free software; you can redistribute it and/or
|
| modify it under the terms of the GNU General Public License
|
| as published by the Free Software Foundation; either version 2
|
| of the License, or (at your option) any later version.
|
|
|
| This program is distributed in the hope that it will be useful,
|
| but WITHOUT ANY WARRANTY; without even the implied warranty of
|
| MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
|
|
| See the GNU General Public License for more details.
|
|
|
| You should have received a copy of the GNU General Public License
|
| along with this program; if not, write to the Free Software
|
| Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
|
| */
|
| // sys_sun.h -- Sun system driver |
| |
| #include "quakedef.h" |
| #include "errno.h" |
| #include <sys/types.h> |
| #include <sys/time.h> |
| #include <sys/stat.h> |
| #include <sys/mman.h> |
| #include <sys/param.h> |
| #include <fcntl.h> |
| #include <stddef.h> |
| #include <sys/types.h> |
| #include <fcntl.h> |
| #include <sys/mman.h> |
| #include <stdio.h> |
| |
| qboolean isDedicated; |
| |
| /* |
| =============================================================================== |
| |
| FILE IO |
| |
| =============================================================================== |
| */ |
| |
| #define MAX_HANDLES 10 |
| |
| typedef struct |
| { |
| FILE *hFile; |
| char *pMap; |
| int nLen; |
| int nPos; |
| } MEMFILE; |
| |
| MEMFILE sys_handles[MAX_HANDLES]; |
| |
| int findhandle (void) |
| { |
| int i; |
| |
| for (i=1 ; i<MAX_HANDLES ; i++) |
| if (!sys_handles[i].hFile) |
| return i; |
| Sys_Error ("out of handles"); |
| return -1; |
| } |
| |
| /* |
| ================ |
| filelength |
| ================ |
| */ |
| int filelength (FILE *f) |
| { |
| int pos; |
| int end; |
| |
| pos = ftell (f); |
| fseek (f, 0, SEEK_END); |
| end = ftell (f); |
| fseek (f, pos, SEEK_SET); |
| |
| return end; |
| } |
| |
| int Sys_FileOpenRead (char *path, int *hndl) |
| { |
| FILE *f; |
| int i; |
| |
| i = findhandle (); |
| |
| f = fopen(path, "rb"); |
| if (!f) |
| { |
| *hndl = -1; |
| return -1; |
| } |
| sys_handles[i].hFile = f; |
| sys_handles[i].nLen = filelength(f); |
| sys_handles[i].nPos = 0; |
| sys_handles[i].pMap = mmap( 0, sys_handles[i].nLen, PROT_READ, MAP_SHARED, fileno( sys_handles[i].hFile ), 0 ); |
| if (!sys_handles[i].pMap || (sys_handles[i].pMap == (char *)-1)) |
| { |
| printf( "mmap %s failed!", path ); |
| sys_handles[i].pMap = NULL; |
| } |
| |
| *hndl = i; |
| |
| return( sys_handles[i].nLen ); |
| } |
| |
| int Sys_FileOpenWrite (char *path) |
| { |
| FILE *f; |
| int i; |
| |
| i = findhandle (); |
| |
| f = fopen(path, "wb"); |
| if (!f) |
| Sys_Error ("Error opening %s: %s", path,strerror(errno)); |
| sys_handles[i].hFile = f; |
| sys_handles[i].nLen = 0; |
| sys_handles[i].nPos = 0; |
| sys_handles[i].pMap = NULL; |
| |
| return i; |
| } |
| |
| void Sys_FileClose (int handle) |
| { |
| if (sys_handles[handle].pMap) |
| if (munmap( sys_handles[handle].pMap, sys_handles[handle].nLen ) != 0) |
| printf( "failed to unmap handle %d\n", handle ); |
| |
| fclose (sys_handles[handle].hFile); |
| sys_handles[handle].hFile = NULL; |
| } |
| |
| void Sys_FileSeek (int handle, int position) |
| { |
| if (sys_handles[handle].pMap) |
| { |
| sys_handles[handle].nPos = position; |
| } |
| else fseek (sys_handles[handle].hFile, position, SEEK_SET); |
| } |
| |
| int Sys_FileRead (int handle, void *dest, int count) |
| { |
| if (sys_handles[handle].pMap) |
| { |
| int nPos = sys_handles[handle].nPos; |
| if (count < 0) count = 0; |
| if (nPos + count > sys_handles[handle].nLen) |
| count = sys_handles[handle].nLen - nPos; |
| memcpy( dest, &sys_handles[handle].pMap[nPos], count ); |
| sys_handles[handle].nPos = nPos + count; |
| return( count ); |
| } |
| else return fread (dest, 1, count, sys_handles[handle].hFile); |
| } |
| |
| int Sys_FileWrite (int handle, void *data, int count) |
| { |
| if (sys_handles[handle].pMap) |
| Sys_Error( "Attempted to write to read-only file %d!\n", handle ); |
| return fwrite (data, 1, count, sys_handles[handle].hFile); |
| } |
| |
| int Sys_FileTime (char *path) |
| { |
| FILE *f; |
| |
| f = fopen(path, "rb"); |
| if (f) |
| { |
| fclose(f); |
| return 1; |
| } |
| |
| return -1; |
| } |
| |
| void Sys_mkdir (char *path) |
| { |
| mkdir( path, 0777 ); |
| } |
| |
| /* |
| =============================================================================== |
| |
| SYSTEM IO |
| |
| =============================================================================== |
| */ |
| |
| void Sys_MakeCodeWriteable (unsigned long startaddr, unsigned long length) |
| { |
| |
| int r; |
| unsigned long addr; |
| int psize = getpagesize(); |
| |
| addr = (startaddr & ~(psize-1)) - psize; |
| |
| // fprintf(stderr, "writable code %lx(%lx)-%lx, length=%lx\n", startaddr, |
| // addr, startaddr+length, length); |
| |
| r = mprotect((char*)addr, length + startaddr - addr + psize, 7); |
| |
| if (r < 0) |
| Sys_Error("Protection change failed\n"); |
| |
| } |
| |
| |
| void Sys_Error (char *error, ...) |
| { |
| va_list argptr; |
| |
| printf ("Sys_Error: "); |
| va_start (argptr,error); |
| vprintf (error,argptr); |
| va_end (argptr); |
| printf ("\n"); |
| Host_Shutdown(); |
| exit (1); |
| } |
| |
| void Sys_Printf (char *fmt, ...) |
| { |
| va_list argptr; |
| |
| va_start (argptr,fmt); |
| vprintf (fmt,argptr); |
| va_end (argptr); |
| } |
| |
| void Sys_Quit (void) |
| { |
| Host_Shutdown(); |
| exit (0); |
| } |
| |
| double Sys_FloatTime (void) |
| { |
| struct timeval tp; |
| struct timezone tzp; |
| static int secbase; |
| |
| gettimeofday(&tp, &tzp); |
| |
| if (!secbase) |
| { |
| secbase = tp.tv_sec; |
| return tp.tv_usec/1000000.0; |
| } |
| |
| return (tp.tv_sec - secbase) + tp.tv_usec/1000000.0; |
| } |
| |
| char *Sys_ConsoleInput (void) |
| { |
| static char text[256]; |
| int len; |
| fd_set readfds; |
| int ready; |
| struct timeval timeout; |
| |
| timeout.tv_sec = 0; |
| timeout.tv_usec = 0; |
| FD_ZERO(&readfds); |
| FD_SET(0, &readfds); |
| ready = select(1, &readfds, 0, 0, &timeout); |
| |
| if (ready>0) |
| { |
| len = read (0, text, sizeof(text)); |
| if (len >= 1) |
| { |
| text[len-1] = 0; // rip off the /n and terminate |
| return text; |
| } |
| } |
| |
| return 0; |
| } |
| |
| void Sys_Sleep (void) |
| { |
| } |
| |
| #if !id386 |
| void Sys_HighFPPrecision (void) |
| { |
| } |
| |
| void Sys_LowFPPrecision (void) |
| { |
| } |
| #endif |
| |
| void Sys_Init(void) |
| { |
| #if id386 |
| Sys_SetFPCW(); |
| #endif |
| } |
| |
| //============================================================================= |
| |
| int main (int argc, char **argv) |
| { |
| static quakeparms_t parms; |
| float time, oldtime, newtime; |
| |
| parms.memsize = 16*1024*1024; |
| parms.membase = malloc (parms.memsize); |
| parms.basedir = "."; |
| parms.cachedir = NULL; |
| |
| COM_InitArgv (argc, argv); |
| |
| parms.argc = com_argc; |
| parms.argv = com_argv; |
| |
| printf ("Host_Init\n"); |
| Host_Init (&parms); |
| |
| Sys_Init(); |
| |
| // unroll the simulation loop to give the video side a chance to see _vid_default_mode |
| Host_Frame( 0.1 ); |
| VID_SetDefaultMode(); |
| |
| oldtime = Sys_FloatTime(); |
| while (1) |
| { |
| newtime = Sys_FloatTime(); |
| Host_Frame (newtime - oldtime); |
| oldtime = newtime; |
| } |
| return 0; |
| } |
| |
| |
| |
| |