1 ; ***********************************************************
  2 ; *                                                         *
  3 ; * Copyright, (C) Honeywell Bull Inc., 1987                *
  4 ; *                                                         *
  5 ; * Copyright, (C) Honeywell Information Systems Inc., 1986 *
  6 ; *                                                         *
  7 ; ***********************************************************
  8 
  9 ; HISTORY COMMENTS:
 10 ;  1) change(86-01-09,Flegel), approve(87-07-13,MCR7580),
 11 ;     audit(87-07-13,Leskiw), install(87-08-07,MR12.1-1072):
 12 ;     Created.
 13 ;  2) change(86-05-14,Westcott), approve(87-07-13,MCR7580),
 14 ;     audit(87-07-13,Leskiw), install(87-08-07,MR12.1-1072):
 15 ;     Support local data.
 16 ;                                                      END HISTORY COMMENTS
 17 
 18 ;/* : PROCEDURE FUNCTION (setup_stack, reset_stack)
 19 ;
 20 ;setup_stack - Manipulate the stack such that the NARC uses its own stack
 21 ;              segment (which is in the DS) and adjust the SP appropriately.
 22 ;              ALL relevant registers are preserved here.
 23 ;              Data addressability is established and ES will contain the old
 24 ;              DS for addressing into the other data.
 25 ;reset_stack - Adjust the stack segment and stack pointer to be what they were
 26 ;              BEFORE the LATEST interrupt occurred.
 27 ;              ALL preserved registers are restored here.
 28 ;              Data addressability is restored.
 29 ;*/
 30 
 31 ;/* : NOTES
 32 ;
 33 ;Syntax:
 34 ;     extrn setup_stack:near,reset_stack:near
 35 ;     push cx
 36 ;     mov  cx, size_of_local_data
 37 ;     call setup_stack
 38 ;        ...
 39 ;     call reset_stack
 40 ;
 41 ;Arguments:
 42 ;     setup_stack: cx = size of local data area
 43 ;                  current stack contains return
 44 ;*/
 45 
 46 PAGE 55,132
 47 
 48 include dos.mac
 49 include util.mac
 50 include mowsdefs.mac
 51 include ws_stack.mac
 52 
 53 
 54 page
 55 ;**************************************************************
 56 ;                                       DATA
 57 ;**************************************************************
 58 dseg
 59 
 60 ;-------- External Declarations
 61 extrn   _BASE:word
 62 
 63 ;--------- Public Declarations
 64 public  setup_stack
 65 public  reset_stack
 66 public  data_seg
 67 public  stackseg
 68 public  sp_base
 69 
 70 endds
 71 
 72 page
 73 ;**************************************************************
 74 ;                                       SETUP STACK
 75 ;**************************************************************
 76 pseg
 77 
 78 setup_stack proc near
 79         cli                            ;turn interrupts off for safety
 80         push    ax
 81         push    bx
 82         push    bp
 83         push    ds
 84         mov     ds,CS:data_seg         ;set up addressability to local data
 85         mov     ax,cs:sp_base
 86         mov     bx,ax
 87         sub     bx,cx
 88         sub     bx,ws_stack.wsparm - ws_stack.ipreg + 4
 89         inc     bx
 90         and     bl,0feh                ;ensure stack address is even
 91         push    bx
 92         sub     bx,FRAMESIZE           ;allow space for stack operations
 93         mov     cs:sp_base,bx          ;set stack frame
 94         cmp     bx,_BASE
 95         ja      no_change              ;lots of stack space left
 96 
 97 ;/* : Handle STACK OVERFLOW here */
 98 
 99         sti
100         push    ax
101         mov     al,20h
102         out     20h,al
103         pop     ax
104 
105 ;/* : save registers on new stack
106 ;     save address of old stackframe in new stack frame   */
107 
108 no_change:
109         mov     [bx],ax
110 
111 ;/* : clean up old stack */
112 
113         pop     bx                     ;bx = base address of ws_stack
114         pop     dsreg[bx]
115         pop     bpreg[bx]
116         pop     bxreg[bx]
117         pop     axreg[bx]
118         mov     cxreg[bx],cx
119         pop     cx                     ; cx = return address from setup_stack
120         mov     dxreg[bx],dx           ; save users registers
121         mov     sireg[bx],si
122         mov     direg[bx],di
123         mov     spreg[bx],sp
124         mov     esreg[bx],es
125         mov     ssreg[bx],ss
126         mov     bpsave[bx],bx
127 
128 ;/* : now set up new stack pointers */
129 
130         mov     ss,cs:stackseg
131         mov     sp,bx
132 
133 ;/* :  set bp = address of local data area */
134 
135         mov     bp,bx
136         push    ds
137         pop     es                     ; for lattice c es=ds
138         mov     ax,axreg[bp]
139         mov     bx,bxreg[bp]
140 
141 ;/* : return */
142 
143         push    cx                     ;push return address
144         mov     cx,cxreg[bp]
145         sti                            ; turn interrupts back on
146         ret
147 
148 setup_stack endp
149 
150 page
151 ;**************************************************************
152 ;                         RESET STACK
153 ;**************************************************************
154 
155 reset_stack proc near
156 
157         cli                            ; turn interrupts off for safety
158 
159 ;/* : save return address */
160 
161         pop     dx                     ;get the return address of the NARC
162                                        ;   function which made the call
163 
164 ;/* : restore user's stack registers */
165 
166         mov     bx,bp                  ; bx = address of ws_stack
167 
168         mov     ax,ssreg[bx]           ; swap in users stack stuff
169         mov     cx,spreg[bx]
170         mov     ss,ax
171         mov     sp,cx
172 
173 ;/* : restore registers */
174 
175         push    dx                     ;push return address
176         push    bxreg[bx]
177         push    dsreg[bx]
178         mov     ax,axreg[bx]           ;swap in saved registers
179         mov     cx,cxreg[bx]
180         mov     dx,dxreg[bx]
181         mov     si,sireg[bx]
182         mov     di,direg[bx]
183         mov     es,esreg[bx]
184         mov     bp,bpreg[bx]
185 
186 ;/* : restore previous stack frame  */
187 
188         mov     bx,cs:sp_base
189         mov     bx,[bx]                ; bx = address of previous stack frame
190         mov     cs:sp_base,bx
191         pop     ds
192         pop     bx
193         sti
194         ret
195 
196 reset_stack endp
197 
198 page
199 ;**************************************************************
200 ;                       LOCAL DATA (must be in CS)
201 ;**************************************************************
202 ;  These are in the CS so that they are addressible by interrupt
203 ;  handlers which do not know the DS yet
204 
205 ;---------- NARC segment and stack --------
206 data_seg        dw      ?               ;NARC DS
207 stackseg        dw      ?               ;NARC SS
208 sp_base         dw      ?               ;NARC sp
209 
210         endps
211         end
212 ;/* pc:: END */
213 ^Z