1 ; ***********************************************************
  2 ; *                                                         *
  3 ; * Copyright, (C) Honeywell Bull Inc., 1987                *
  4 ; *                                                         *
  5 ; * Copyright, (C) Honeywell Information Systems Inc., 1986 *
  6 ; *                                                         *
  7 ; ***********************************************************
  8  page    55,132
  9 
 10 ; HISTORY COMMENTS:
 11 ;  1) change(85-12-22,Flegel), approve(87-07-13,MCR7580),
 12 ;     audit(87-07-13,Leskiw), install(87-08-07,MR12.1-1072):
 13 ;     Created.
 14 ;  2) change(86-02-15,Westcott), approve(87-07-13,MCR7580),
 15 ;     audit(87-07-13,Leskiw), install(87-08-07,MR12.1-1072):
 16 ;     Support of software interrupts.
 17 ;  3) change(88-01-26,Flegel), approve(88-02-29,MCR7853),
 18 ;     audit(88-03-10,Nakaska):
 19 ;     MOWSE made to drop DTR (disconnect) by default unless /H option
 20 ;     requested by user at command line.
 21 ;  4) change(88-02-10,Lee), approve(88-02-29,MCR7853),
 22 ;     audit(88-03-10,Nakaska):
 23 ;     Made parameter "lineparm" public so routine line_break() could
 24 ;     access it
 25 ;  5) change(88-06-17,Lee), approve(88-07-18,MCR7936), audit(88-08-10,Flegel):
 26 ;     Added support for Mark and Space parity
 27 ;                                                      END HISTORY COMMENTS
 28 
 29 ; PROCEDURE FUNCTION (initialize_mowse):
 30 ;
 31 ;Initialize the appropriate hardware and software interrupt vectors to enable
 32 ;the MOWSE environment on the PC.  This also includes enabling the RS232 port
 33 ;in preparation for PC<=>multics communications.
 34 
 35 ; NOTES
 36 ;
 37 ;Arguments:
 38 ;       lineparm - rs232 line parameters. This parameter is identical to
 39 ;                  the parameter required for the ROM-BIOS interrupt 14H
 40 ;                  except when parity is Mark or Space.
 41 ;
 42 ;   7       6       5        4       3        2        1       0
 43 ;   ----- Baud Rate --       -Parity--      Stopbit    --Word Length
 44 ;   000 - 110                X0 - NONE        0 - 1     10 - 7 Bits
 45 ;   001 - 150                01 - ODD         1 - 2     11 - 8 Bits
 46 ;   010 - 300                11 - EVEN
 47 ;   011 - 600
 48 ;   100 - 1200
 49 ;   101 - 2400
 50 ;   110 - 4800
 51 ;   111 - 9600
 52 ;
 53 ; (*) - for Mark or Space, bits 8 to 10 of lineparm are used as follows:
 54 ;
 55 ;  10       9        8
 56 ; - Mark/Space parity -
 57 ;    101 - Mark parity
 58 ;    111 - Space parity
 59 ;
 60 ;
 61 ;Mowse is a '.com' file which will terminate and stay resident.  All interrupt
 62 ;handlers and their associated modules also remain resident.
 63 ;
 64 ;        Interrupt vectors:
 65 ;                0Ch     hardware (RS232)
 66 ;                0Bh     software (MOWSE functions calls)
 67 ;                1Ch     timer interrupt
 68 ;                28h     console I/O interrupt
 69 
 70 
 71 include dos.mac                 ;Lattice include file
 72 include xoscall.mac             ;Bios and Dos Call macros
 73 include mowsdefs.mac
 74 include ws.mac
 75 include ws_buf.mac
 76 
 77 page
 78 ;*******************************************************************
 79 ;                                       DATA
 80 ;*******************************************************************
 81 dseg
 82 
 83 ;-------- External Declarations
 84 
 85 extrn   _TOP:word
 86 extrn   _BASE:word
 87 extrn   data_seg:word
 88 extrn   stackseg:word
 89 extrn   sp_base:word
 90 extrn   SOFTNO:word
 91 extrn   COM_NO:word
 92 extrn   COM_PORT:word
 93 extrn   HARDINTRPT:word                      ; hardware interrupt number
 94 extrn   MASK8259:byte
 95 extrn   startup_flags:word                   ; startup control options
 96 
 97 ;--------- Public Declarations
 98 public  terminal_over
 99 public  initialize_mowse
100 public  send_buffer
101 public  transmit_active
102 public  packet_mode
103 public  bg_in_use
104 public  mysystem;
105 public  fg_buf
106 public  bg_sav_buf
107 public  inbuff
108 public  in_protocol
109 public  sleepq
110 public  tikpermin
111 public  lineparm
112 
113 ;----------- Messages ---------------
114 
115 divword     dw   60
116 
117 lineparm    commparm <B9600,even_parity,stop1,data7>
118 
119 
120 ;------------ Received data buffer and associated pointers
121 ;------------ Used for debugging
122 
123         def_buf inbuff,1000
124 
125 ;------------ Transmitted data buffer and associated pointers
126 ;------------ Used for debugging
127 
128         def_buf fg_buf,WSPAKSIZ+10
129 
130 ;------------ Transmit buffer
131 ;------------ Contains all data to be transmitted over rs232 link
132 
133         def_buf send_buffer,BUFSIZE
134 
135 ;------------ Foreground buffer
136 
137 terminal_over    db      0                   ;terminal buffer overflow flag
138 
139 transmit_active  dw      0                   ; =1, if transmit interrupt active
140 send_buffer_over db      0                   ;send buffer overflow flag
141 mysystem         db      0                   ; system ID fo this mowse
142 packet_mode      dw      0                   ; =1, if in protocol running
143 in_protocol      dw      0                   ; set if protocol module is active
144 sleepq           dw      0                   ; pointer to first CAT entry on sleep queue
145 tikpermin        dw      0                   ; number of clock ticks per minute
146 bg_in_use        dw      0                   ; =1, if bg_sav_buf full
147 bg_sav_buf       db      WSPAKSIZ+10 dup (?)
148 ms_parity        db      0
149 
150 endds
151 
152 page
153 ;**************************************************************************
154 ;                               Program mainline
155 ;**************************************************************************
156 
157 pseg
158 
159 ;-------- External Procedures
160 
161 extrn   user_interrupt_handler:near
162 extrn   hardware_interrupt_handler:near
163 extrn   int13ep:near
164 extrn   int1cep:near
165 extrn   int28ep:near
166 extrn   init_inbuff:near
167 extrn   uisystem:word
168 public  INTSOFT,INT13,INT1C,INT28,IN_DOS, INTHARD
169 public  IN_SOFT,IN_NARC,IN_INT28
170 public  advance_count
171 public  time_count
172 public  mowse_time
173 public  ticpersec
174 public  calladvtmr
175 
176 initialize_mowse proc near
177 
178         push    bp
179         push    es
180 
181 ;get parameters to control the com port into variable lineparm
182 
183         mov     bp,sp
184         mov     ax,[bp+6]
185         mov     lineparm,al
186         mov     ms_parity,ah
187 
188 ;Test the interrupt vectors to see if they are already initialized
189 
190         mov     ax, SOFTNO
191         mov     ah, GETVECTOR
192         int     DOSFUNCTION
193         cmp     bx, offset user_interrupt_handler
194         jne     nonres
195 
196         mov     ax, HARDINTRPT
197         mov     ah, GETVECTOR
198         int     DOSFUNCTION
199         cmp     bx, offset hardware_interrupt_handler
200         jne     nonres
201 
202 ;If address of interrupt service routines are already in place then
203 ;- return with a 0 return value
204 
205         pop     es
206         pop     bp
207         xor     ax,ax                        ; indicate MOWSE already resident
208         ret
209 
210 nonres:
211 
212 ;complete initialization, initialize circular buffers
213 
214         init_buf send_buffer
215         init_buf inbuff
216         init_buf fg_buf
217 
218 ;save the pointers to the stack to be used when servicing an interrupt
219 
220         cli
221         push     DS                          ;save DS
222         push     SS                          ;save SS
223 
224 ;save parameters which define stack to be used during interrupts
225 
226         mov     ax,sp
227         sub     ax,FRAMESIZE
228         mov     CS:sp_base,ax                ;bottom of MOWSE stack
229         pop     CS:stackseg                  ;SS of MOWSE
230         pop     CS:data_seg                  ;DS of MOWSE
231 
232         mov     byte ptr mysystem,WSIBMPC
233         mov     byte ptr cs:uisystem,WSIBMPC
234 
235 ;set up Interrupt Vector for RS232 Interrupt
236 
237         push    DS
238         mov     ax,HARDINTRPT
239         mov     ah,35h
240         int     DOSFUNCTION
241         mov     word ptr CS:INTHARD+2,es
242         mov     word ptr CS:INTHARD,bx       ;save old vector address
243         mov     DX, offset hardware_interrupt_handler
244         mov     ax,HARDINTRPT                ;Set interrupt vector RS232
245         push    CS
246         pop     DS                           ;Point to RS232 ISR in DS:DX
247         mov     ah,25h
248         int     DOSFUNCTION
249         pop     DS
250 
251 ;initialize interrupt flags
252 
253         mov     ax, 1
254         mov     CS:IN_INT28,ax
255         mov     CS:IN_NARC,ax
256         mov     CS:IN_SOFT,ax
257         mov     transmit_active,ax
258         mov     in_protocol,0
259         mov     sleepq,0
260 
261 ;setup software interrupt vector
262 
263         mov     ax,SOFTNO
264         mov     ah,35h
265         int     DOSFUNCTION
266         mov     word ptr CS:INTSOFT+2,es
267         mov     word ptr CS:INTSOFT,bx       ;save old vector address
268         mov     dx, offset user_interrupt_handler
269         mov     ax,SOFTNO
270         push    ds
271         push    cs
272         pop     ds
273         mov     ah,25h
274         int     DOSFUNCTION
275 
276 ;trap INT13 interrupt
277 
278         mov     al,13h
279         mov     ah,35h
280         int     DOSFUNCTION
281         mov     word ptr CS:INT13+2,es
282         mov     word ptr CS:INT13,bx         ;save old vector address
283         mov     dx, offset int13ep
284         mov     al,13h
285         mov     ah,25h
286         int     DOSFUNCTION
287 
288 ;trap INT1C interrupt *
289 
290         mov     al,1Ch
291         mov     ah,35h
292         int     DOSFUNCTION
293         mov     word ptr CS:INT1C+2,es
294         mov     word ptr CS:INT1C,bx         ;save old vector address
295         mov     dx, offset int1Cep
296         mov     al,1Ch
297         mov     ah,25h
298         int     DOSFUNCTION
299 
300 ;trap INT28 interrupt
301 
302         mov     al,28h
303         mov     ah,35h
304         int     DOSFUNCTION
305         mov     word ptr CS:INT28+2,es
306         mov     word ptr CS:INT28,bx         ;save old vector address
307         mov     dx, offset int28ep
308         mov     al,28h
309         mov     ah,25h
310         int     DOSFUNCTION
311         pop     ds
312 
313 ;get address of in-dos flag
314 
315         mov     ah,34h
316         int     DOSFUNCTION
317         mov     word ptr CS:IN_DOS+2,es
318         mov     word ptr CS:IN_DOS,bx
319 
320 ;initialize interrupt flags
321 
322         xor     ax,ax
323         mov     CS:IN_INT28,ax
324         mov     CS:IN_NARC,ax
325         mov     CS:IN_SOFT,ax
326         mov     transmit_active,ax
327         mov     word ptr CS:time_count,ax
328         mov     word ptr CS:time_count+2,ax
329         mov     CS:advance_count,ax
330 
331 ;If hold_dtr (/H) option requested, then skip.  Otherwise default to dropping
332 ;DTR for disconnection
333 
334         mov     ax,startup_flags
335         and     ax,OPTION_H                  ; Hold DTR ?
336         jne     dtr_raise                    ;  YES, don't drop it
337 
338         mov     al,MASKMCR_DROP              ; Disable OUT2, drop DTR, RTS active low
339         mov     DX,MCR                       ; Address MCR
340         add     DX,COM_PORT
341         out     DX,AL
342 dtr_raise:
343 
344 ;Determine the number of clock ticks in every second, minute, and hour.
345 ;Count the number that occur in a 10 second interval and calculate the
346 ;rest.
347 
348         sti
349         mov     ah,2ch
350         int     DOSFUNCTION                  ; get time
351         push    word ptr CS:time_count+2     ; save current tick count
352         add     dh,10
353         cmp     dh,60
354         jl      tick1                        ; if more than 60 seconds
355         sub     dh,60
356         inc     cl
357         cmp     cl,60                        ; if more than 60 minutes
358         jl      tick1
359         xor     cl,cl
360         inc     ch
361         cmp     ch,24                        ; if more than 23 hours
362         jl      tick1
363         xor     ch,ch
364 
365 tick1:
366         mov     bx,cx                        ; save hours,minutes
367         mov     si,dx                        ; save seconds
368 
369 tick2:
370         mov     ah,2ch
371         int     DOSFUNCTION                  ; get time
372         cmp     ch,bh
373         jne     tick2                        ; if hours are not the same
374         cmp     cl,bl
375         ja      tick3
376         jb      tick2
377         cmp     dx,si
378         jl      tick2                        ; if 10 seconds hasn't elapsed
379 
380 tick3:
381         mov     ax,word ptr CS:time_count+2
382         pop     cx
383         sub     ax,cx                        ; ax = number of ticks in 10 seconds
384         shl     ax,1                         ; ax = number of ticks in 20 seconds
385         mov     dx,ax
386         shl     dx,1                         ; dx = number of ticks in 40 seconds
387         add     ax,dx                        ; dx = number of ticks in 60 seconds
388         mov     tikpermin,ax
389 
390 ;Calculate ticpersec = tikpermin / 60
391 
392         mov     ax,tikpermin
393         cwd
394         div     divword
395         mov     CS:ticpersec,ax
396 
397 ;set up RS232 port to paramters in lineparam
398 
399         mov     dx, COM_NO                   ;COMM port 1
400         mov     al, lineparm
401         @bioscall RS232,0
402 
403 ;check for handling SPACE and MARK parity
404 
405         mov     ah,ms_parity   ; al = 101b for MARK, 111b for SPACE
406         sal     ah,1           ; create parity bits mask for LCR
407         jz      not_ms_parity  ; ms_parity is 0, parity not mark or space
408 
409         sal     ah,1           ; complete creating LCR parity mask,
410         sal     ah,1           ;  00101000b for MARK, 00111000b for SPACE
411 
412         mov     dx,LCR         ; get offset into LCR
413         add     dx,COM_PORT    ; add base address of comm port
414         in      al,dx          ; get current LCR status
415         and     al,MASKLCR     ; reset DLAB
416         or      al,ah          ; set appropriate LCR parity control bits
417         out     dx,al          ; send to LCR
418 
419 not_ms_parity:
420         cli
421 
422 ;Enable DTR,RTS,OUT1,OUT2 on 8250 to get it into a known state
423 
424         mov     al,MASKMCR                   ;Disable OUT2, leave DTR, RTS active low
425         mov     DX,MCR                       ;Address MCR
426         add     DX,COM_PORT
427         out     DX,AL
428 
429 ;enable IRQ(3 4) on 8259 interrupt controller
430 
431         in      al,IMR8259                   ;Get current masks
432         and     al,MASK8259                  ;Reset IRQ(3 4) mask
433         out     IMR8259,al                   ;And restore to Interrupt Mask
434                                              ;Register
435 
436 
437 ;enable 8250 data ready interrupt
438 
439         cli
440         mov     dx,LCR                       ;Address LCR
441         add     dx,COM_PORT
442 
443         in      al,dx                        ;Reset DLAB for IER access
444         and     al,MASKLCR
445         out     dx,al
446 
447         mov     dx,IER                       ;Address IER
448         add     dx,COM_PORT
449 
450         xor     al,al                        ;Clear the IER
451         out     dx,al
452 
453         mov     al,MASKIER                   ;Enable 'Data Ready' Interrupt and
454         out     dx,al                        ;   Transmit holding register empty and
455                                              ;   Break Characters and
456                                              ;   Change in modem status
457 
458 ;enable Out2 on 8250
459 
460         mov     dx,MCR                       ;Address MCR
461         add     dx,COM_PORT
462 
463         mov     al,MASKMCR                   ;Enable OUT2
464         out     dx,al
465 
466 ;Allow interrupts
467 
468         mov     dx,MCR
469         add     dx,COM_PORT                  ; dx = COM_PORT
470         mov     al,MASKMCR                   ; al = enable OUT2
471         out     dx,al                        ; enable MCR
472         sti
473 
474 ;Return
475 
476         mov     ax, 1                        ; mowse initialized successfully
477         pop     es
478         pop     bp
479         ret
480 
481 initialize_mowse endp
482 
483 page
484 ;***********************************************************************
485 ;       Static storage for interrupt vectors
486 ;***********************************************************************
487 INT13         dd 0       ; Diskette services vector
488 INT1C         dd 0       ; Timer interrupt vector
489 INT28         dd 0       ; Console I/O vector
490 IN_DOS        dd 0       ; Address of in-dos flag
491 INTSOFT       dd 0       ; Old software Interrupt vector
492 INTHARD       dd 0       ; Old hardware interrupt vector
493 ;***********************************************************************
494 ;       Static storage for flags
495 ;***********************************************************************
496 IN_SOFT       dw 0       ; =1, if in software interrupt
497 IN_NARC       dw 0       ; =1, if in MOWSE
498 IN_INT28      dw 0       ; =1, if in Console I/O
499 advance_count dw 0       ;counter to tell if one second has passed
500 time_count    dd 0       ; tick counter for MOWSE timing
501                          ;so that Hal's "advtmr()" can be called
502 mowse_time    dw 0       ;seconds elapsed since startup
503 ticpersec     dw 0       ; number of clock ticks per second
504 calladvtmr    dw 0       ; flag indicating to call advtmr routine
505 
506 endps
507       end