OSDN Git Service

Initial Import
[nethackexpress/trunk.git] / sys / atari / tos.c
1 /*      SCCS Id: @(#)tos.c      3.1     90/14/08
2 /* NetHack may be freely redistributed.  See license for details. */
3
4 /*
5  *  TOS system functions.
6  */
7
8 #define NEED_VARARGS
9 #include "hack.h"
10
11 #ifdef TTY_GRAPHICS
12 # include "tcap.h"
13 #else
14 /* To avoid error for tos.c; will be removed later */
15 static char *nh_HE="\033q";
16 #endif
17
18 #ifdef TOS
19
20 # include <osbind.h>
21 # ifndef WORD
22 #  define WORD short            /* 16 bits -- redefine if necessary */
23 # endif
24
25 #include <ctype.h>
26
27 static char NDECL(DOSgetch);
28 static char NDECL(BIOSgetch);
29 static void NDECL(init_aline);
30 char *_a_line;                  /* for Line A variables */
31 # ifdef TEXTCOLOR
32 boolean colors_changed = FALSE;
33 # endif
34
35 int
36 tgetch()
37 {
38         char ch;
39
40         /* BIOSgetch can use the numeric key pad on IBM compatibles. */
41         if (iflags.BIOS)
42                 ch = BIOSgetch();
43         else
44                 ch = DOSgetch();
45         return ((ch == '\r') ? '\n' : ch);
46 }
47
48 /*
49  *  Keyboard translation tables.
50  */
51 #define KEYPADLO        0x61
52 #define KEYPADHI        0x71
53
54 #define PADKEYS         (KEYPADHI - KEYPADLO + 1)
55 #define iskeypad(x)     (KEYPADLO <= (x) && (x) <= KEYPADHI)
56
57 /*
58  * Keypad keys are translated to the normal values below.
59  * When iflags.BIOS is active, shifted keypad keys are translated to the
60  *    shift values below.
61  */
62 static const struct pad {
63         char normal, shift, cntrl;
64 } keypad[PADKEYS] = {
65                         {C('['), 'Q', C('[')},          /* UNDO */
66                         {'?', '/', '?'},                /* HELP */
67                         {'(', 'a', '('},                /* ( */
68                         {')', 'w', ')'},                /* ) */
69                         {'/', '/', '/'},                /* / */
70                         {C('p'), '$', C('p')},          /* * */
71                         {'y', 'Y', C('y')},             /* 7 */
72                         {'k', 'K', C('k')},             /* 8 */
73                         {'u', 'U', C('u')},             /* 9 */
74                         {'h', 'H', C('h')},             /* 4 */
75                         {'.', '.', '.'},
76                         {'l', 'L', C('l')},             /* 6 */
77                         {'b', 'B', C('b')},             /* 1 */
78                         {'j', 'J', C('j')},             /* 2 */
79                         {'n', 'N', C('n')},             /* 3 */
80                         {'i', 'I', C('i')},             /* Ins */
81                         {'.', ':', ':'}                 /* Del */
82 }, numpad[PADKEYS] = {
83                         {C('['), 'Q', C('[')}   ,       /* UNDO */
84                         {'?', '/', '?'},                /* HELP */
85                         {'(', 'a', '('},                /* ( */
86                         {')', 'w', ')'},                /* ) */
87                         {'/', '/', '/'},                /* / */
88                         {C('p'), '$', C('p')},          /* * */
89                         {'7', M('7'), '7'},             /* 7 */
90                         {'8', M('8'), '8'},             /* 8 */
91                         {'9', M('9'), '9'},             /* 9 */
92                         {'4', M('4'), '4'},             /* 4 */
93                         {'.', '.', '.'},                /* 5 */
94                         {'6', M('6'), '6'},             /* 6 */
95                         {'1', M('1'), '1'},             /* 1 */
96                         {'2', M('2'), '2'},             /* 2 */
97                         {'3', M('3'), '3'},             /* 3 */
98                         {'i', 'I', C('i')},             /* Ins */
99                         {'.', ':', ':'}                 /* Del */
100 };
101
102 /*
103  * Unlike Ctrl-letter, the Alt-letter keystrokes have no specific ASCII
104  * meaning unless assigned one by a keyboard conversion table, so the
105  * keyboard BIOS normally does not return a character code when Alt-letter
106  * is pressed.  So, to interpret unassigned Alt-letters, we must use a
107  * scan code table to translate the scan code into a letter, then set the
108  * "meta" bit for it.  -3.
109  */
110 #define SCANLO          0x10
111
112 static const char scanmap[] = {         /* ... */
113         'q','w','e','r','t','y','u','i','o','p','[',']', '\n',
114         0, 'a','s','d','f','g','h','j','k','l',';','\'', '`',
115         0, '\\', 'z','x','c','v','b','N','m',',','.','?'        /* ... */
116 };
117
118 #define inmap(x)        (SCANLO <= (x) && (x) < SCANLO + SIZE(scanmap))
119
120 /*
121  * BIOSgetch gets keys directly with a BIOS call.
122  */
123 #define SHIFT           (0x1 | 0x2)
124 #define CTRL            0x4
125 #define ALT             0x8
126
127 static char
128 BIOSgetch()
129 {
130         unsigned char scan, shift, ch;
131         const struct pad *kpad;
132
133         long  x;
134
135         /* Get scan code.
136          */
137         x = Crawcin();
138         ch = x & 0x0ff;
139         scan = (x & 0x00ff0000L) >> 16;
140         /* Get shift status.
141          */
142         shift = Kbshift(-1);
143
144         /* Translate keypad keys */
145         if (iskeypad(scan)) {
146                 kpad = iflags.num_pad ? numpad : keypad;
147                 if (shift & SHIFT)
148                         ch = kpad[scan - KEYPADLO].shift;
149                 else if (shift & CTRL)
150                         ch = kpad[scan - KEYPADLO].cntrl;
151                 else
152                         ch = kpad[scan - KEYPADLO].normal;
153         }
154         /* Translate unassigned Alt-letters */
155         if ((shift & ALT) && !ch) {
156                 if (inmap(scan))
157                         ch = scanmap[scan - SCANLO];
158                 return (isprint(ch) ? M(ch) : ch);
159         }
160         return ch;
161 }
162
163 static char
164 DOSgetch()
165 {
166         return (Crawcin() & 0x007f);
167 }
168
169
170 long
171 freediskspace(path)
172 char *path;
173 {
174         int drive = 0;
175         struct {
176                 long freal; /*free allocation units*/
177                 long total; /*total number of allocation units*/
178                 long bps;   /*bytes per sector*/
179                 long pspal; /*physical sectors per allocation unit*/
180         } freespace;
181         if (path[0] && path[1] == ':')
182                 drive = (toupper(path[0]) - 'A') + 1;
183         if (Dfree(&freespace,drive)<0) return -1;
184         return freespace.freal*freespace.bps*freespace.pspal;
185 }
186
187 /*
188  * Functions to get filenames using wildcards
189  */
190 int
191 findfirst(path)
192 char *path;
193 {
194         return (Fsfirst(path, 0) == 0);
195 }
196
197 int
198 findnext()
199 {
200         return (Fsnext() == 0);
201 }
202
203 char *
204 foundfile_buffer()
205 {
206         return (char *)Fgetdta() + 30;
207 }
208
209 long
210 filesize(file)
211 char *file;
212 {
213         if (findfirst(file))
214                 return  (* (long *) ((char *)Fgetdta() + 26));
215         else
216                 return -1L;
217 }
218
219 /*
220  * Chdrive() changes the default drive.
221  */
222 void
223 chdrive(str)
224 char *str;
225 {
226         char *ptr;
227         char drive;
228
229         if ((ptr = index(str, ':')) != (char *)0) {
230                 drive = toupper(*(ptr - 1));
231                 (void)Dsetdrv(drive - 'A');
232         }
233         return;
234 }
235
236
237 void
238 get_scr_size()
239 {
240 # ifdef MINT
241 #  include <ioctl.h>
242         struct winsize win;
243         char *tmp;
244
245         if((tmp=nh_getenv("LINES")))
246                 LI = atoi(tmp);
247         else if((tmp=nh_getenv("ROWS")))
248                 LI = atoi(tmp);
249         if(tmp && (tmp=nh_getenv("COLUMNS")))
250                 CO = atoi(tmp);
251         else {
252             ioctl(0,TIOCGWINSZ, &win);
253             LI = win.ws_row;
254             CO = win.ws_col;
255         }
256 # else
257         init_aline();
258         LI = (*((WORD  *)(_a_line + -42L))) + 1;
259         CO = (*((WORD  *)(_a_line + -44L))) + 1;
260 # endif
261 }
262
263 # define BIGBUF  8192
264
265 int
266 _copyfile(from, to)
267 char *from, *to;
268 {
269         int fromfd, tofd, r;
270         char *buf;
271
272         if ((fromfd = open(from, O_RDONLY|O_BINARY, 0)) < 0)
273                 return -1;
274         if ((tofd = open(to, O_WRONLY|O_CREAT|O_TRUNC|O_BINARY, FCMASK)) < 0)
275                 return -1;
276         buf = (char *)alloc((size_t)BIGBUF);
277         while ( (r = read(fromfd, buf, BIGBUF)) > 0)
278                 write(tofd, buf, r);
279         close(fromfd);
280         close(tofd);
281         free(buf);
282         return 0;       /* successful */
283 }
284
285 int kbhit()
286 {
287         return Cconis();
288 }
289
290 static void
291 init_aline()
292 {
293 # ifdef __GNUC__
294 /* line A calls nuke registers d0-d2,a0-a2; not all compilers regard these
295    as scratch registers, though, so we save them
296  */
297         asm(" moveml d0-d2/a0-a2, sp@-");
298         asm(" .word 0xa000; movel d0, __a_line");
299         asm(" moveml sp@+, d0-d2/a0-a2");
300 # else
301         asm(" movem.l d0-d2/a0-a2, -(sp)");
302         asm(" .dc.w 0xa000");   /* tweak as necessary for your compiler */
303         asm(" move.l d0, __a_line");
304         asm(" movem.l (sp)+, d0-d2/a0-a2");
305 # endif
306 }
307
308 # ifdef TEXTCOLOR
309 /* used in termcap.c to decide how to set up the hilites */
310 unsigned long tos_numcolors = 2;
311
312 void
313 set_colors()
314 {
315         static char colorHE[] = "\033q\033b0";
316
317         if (!iflags.BIOS)
318                 return;
319         init_aline();
320         tos_numcolors = 1 << (((unsigned char *) _a_line)[1]);
321         if (tos_numcolors <= 2) {                       /* mono */
322                 iflags.use_color = FALSE;
323                 return;
324         } else {
325                 colors_changed = TRUE;
326                 nh_HE = colorHE;
327         }
328 }
329
330 void
331 restore_colors()
332 {
333         static char plainHE[] = "\033q";
334
335         if (colors_changed)
336                 nh_HE = plainHE;
337         colors_changed = FALSE;
338 }
339 # endif /* TEXTCOLOR */
340
341 # ifdef SUSPEND
342
343 #include        <signal.h>
344
345 #   ifdef MINT
346 extern int __mint;
347 #   endif
348
349 int
350 dosuspend() {
351 #   ifdef MINT
352         extern int kill();
353         if (__mint == 0) {
354 #   endif
355                 pline("Sorry, it seems we have no SIGTSTP here.  Try ! or S.");
356 #   ifdef MINT
357         }
358         else if(signal(SIGTSTP, SIG_IGN) == SIG_DFL) {
359                 suspend_nhwindows((char *)0);
360                 (void) signal(SIGTSTP, SIG_DFL);
361                 (void) kill(0, SIGTSTP);
362                 get_scr_size();
363                 resume_nhwindows();
364         } else {
365                 pline("I don't think your shell has job control.");
366         }
367 #   endif /* MINT */
368         return(0);
369 }
370 # endif /* SUSPEND */
371
372 #endif /* TOS */