Initial release of Maemo 5 port of gnuplot
[gnuplot] / src / pcgraph.asm
1 TITLE   PC graphics module
2 ;       uses LINEPROC.MAC
3
4 ;       Michael Gordon - 8-Dec-86
5 ;
6 ; Certain routines were taken from the Hercules BIOS of Dave Tutelman - 8/86
7 ; Others came from pcgraph.asm included in GNUPLOT by Colin Kelley
8 ;
9 ; modified slightly by Colin Kelley - 22-Dec-86
10 ;       added header.mac, parameterized declarations
11 ; added dgroup: in HVmodem to reach HCh_Parms and HGr_Parms - 30-Jan-87
12 ;
13 ; modified and added to for use in plot(3) routines back end.
14 ; Gil Webster.
15 ;
16 ; Assemble with masm ver. 4.  
17
18 include header.mac
19
20 if1
21 include lineproc.mac
22 endif
23
24 GPg1_Base equ 0B800h    ; Graphics page 1 base address
25
26         extrn _inter:far
27
28 _text   segment
29
30         public _PC_line, _PC_color, _PC_mask, _PC_curloc, _PC_puts, _Vmode
31         public _erase, _save_stack, _ss_interrupt
32
33 pcpixel proc near
34         ror word ptr linemask,1
35         jc cont
36         ret
37 cont:
38         push ax
39         push bx
40         push cx
41         push dx
42         push bp
43         mov cx,ax               ; x
44         mov dx,bx               ; y
45         mov ah,0ch              ; ah = write pixel
46         mov al,byte ptr color
47
48         mov bh, 0               ; page 0
49         int 10h
50         pop bp
51         pop dx
52         pop cx
53         pop bx
54         pop ax
55         ret
56 pcpixel endp
57
58 lineproc _PC_line, pcpixel
59
60 ;
61 ; erase - clear page 1 of the screen buffer to zero (effectively, blank
62 ;       the screen)
63 ;
64 beginproc _erase
65         push es
66         push ax
67         push cx
68         push di
69         mov ax, GPg1_Base
70         mov es, ax
71         xor di, di
72         mov cx, 4000h
73         xor ax, ax
74         cld
75         rep stosw                       ; zero out screen page
76         pop di
77         pop cx
78         pop ax
79         pop es
80         ret
81 _erase endp
82
83 beginproc _PC_color
84         push bp
85         mov bp,sp
86         mov al,[bp+X]                   ; color
87         mov byte ptr color,al
88         pop bp
89         ret
90 _PC_color endp
91
92 beginproc _PC_mask
93         push bp
94         mov bp,sp
95         mov ax,[bp+X]                   ; mask
96         mov word ptr linemask,ax
97         pop bp
98         ret
99 _PC_mask endp
100
101 beginproc _Vmode
102         push bp
103         mov bp,sp
104         push si
105         push di
106         mov ax,[bp+X]
107         int 10h
108         pop di
109         pop si
110         pop bp
111         ret
112 _Vmode  endp
113
114 beginproc _PC_curloc
115         push bp
116         mov bp,sp
117         mov dh, byte ptr [bp+X] ; row number
118         mov dl, byte ptr [bp+X+2] ; col number
119         mov bh, 0
120         mov ah, 2
121         int 10h
122         pop bp
123         ret
124 _PC_curloc endp
125
126 ;
127 ; thanks to watale!broehl for finding a bug here--I wasn't pushing BP
128 ;   and reloading AH before INT 10H, which is necessary on genuine IBM
129 ;   boards...
130 ;
131 beginproc _PC_puts
132         push bp
133         mov bp,sp
134         push si
135         mov bl,byte ptr color
136         mov si,[bp+X]           ; offset
137
138 ifdef LARGE_DATA
139         mov es,[bp+X+2]         ; segment if large or compact data model
140 endif
141
142 puts2:
143
144 ifdef LARGE_DATA
145         mov al,es:[si]
146 else
147         mov al,[si]
148 endif
149         or al,al
150         jz puts3
151         mov ah,0eh              ; write TTY char
152         int 10h
153         inc si
154         jmp short puts2
155 puts3:  pop si
156         pop bp
157         ret
158 _PC_puts endp
159
160
161 ; int kbhit();
162 ;   for those without MSC 4.0
163 ; Use BIOS interrupt 16h to determine if a key is waiting in the buffer.
164 ; Return nonzero if so.
165 ;
166
167 beginproc _kbhit
168         mov ah, 1               ; function code 1 is keyboard test
169         int 16h                 ; keyboard functions
170         jnz kbfin               ; Exit if char available
171         xor ax, ax              ; No char:  return zero.
172 kbfin:  ret
173 _kbhit  endp
174
175
176 ; _save_stack and _ss_interrupt are needed due to a bug in the MSC 4.0
177 ; code when run under MS-DOS 3.x.  Starting with 3.0, MS-DOS automatically
178 ; switches to an internal stack during system calls.  This leaves SS:SP
179 ; pointing at MS-DOS's stack when the ^C interrupt (INT 23H) is triggered.
180 ; MSC should restore its own stack before calling the user signal() routine,
181 ; but it doesn't.
182 ;
183 ; Presumably this code will be unnecessary in later releases of the compiler.
184 ;
185
186 ; _save_stack saves the current SS:SP to be loaded later by _ss_interrupt.
187 ;
188
189 beginproc _save_stack
190         mov ax,ss
191         mov cs:save_ss,ax
192         mov ax,sp
193         mov cs:save_sp,ax
194         ret
195 _save_stack endp
196
197
198 ; _ss_interrupt is called on ^C (INT 23H).  It restores SS:SP as saved in
199 ; _save_stack and then jumps to the C routine interrupt().
200 ;
201 beginproc _ss_interrupt
202         cli                     ; no interrupts while the stack is changed!
203         mov ax,-1               ; self-modifying code again
204 save_ss equ this word - 2
205         mov ss,ax
206         mov sp,-1               ; here too
207 save_sp equ this word - 2
208         sti
209         jmp far ptr _inter; now it's safe to call the real routine
210 _ss_interrupt endp
211
212
213 _text   ends
214
215
216 const   segment
217 linemask dw -1
218 color    db 1
219 const   ends
220
221         end