home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 8 Other / 08-Other.zip / rng-810.zip / c0.asm < prev    next >
Assembly Source File  |  1994-01-28  |  10KB  |  322 lines

  1. ;
  2. ; Copyright (c) Sirius Software 1992.
  3. ; All rights reserved.
  4. ; But the readme.doc from Sirius Software files says:
  5. ; This software is hereby placed in the public domain.
  6. ; RANDDRV.SYS random number driver for RNG-810 or similar hardware
  7. ; Copyright (C) 1994 Paul Elliot
  8. ;
  9. ; This program is free software; you can redistribute it and/or
  10. ; modify it under the terms of the GNU General Public License
  11. ; as published by the Free Software Foundation; either version 2
  12. ; of the License, or (at your option) any later version.
  13. ;
  14. ; This program is distributed in the hope that it will be useful,
  15. ; but WITHOUT ANY WARRANTY; without even the implied warranty of
  16. ; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  17. ; GNU General Public License for more details.
  18. ;
  19. ; You should have received a copy of the GNU General Public License
  20. ; along with this program; if not, write to the Free Software
  21. ; Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  22. ;
  23. ;Paul.Elliott@Hrnowl.LoneStar.Org
  24. ;
  25. ;Paul Elliott
  26. ;
  27. ;3986 South Gessner #224 Houston TX 77063
  28. ;
  29. %pagesize
  30. ;use ideal mode instead of masm mode
  31. IDEAL
  32. %title    "assembly language interface for os/2 random number generator driver"
  33. %pagesize    55,132
  34. ;show code actually assembled by fancy assembler directives!
  35. %MACS
  36. ;
  37. ;
  38. ; file_name = c0.asm
  39. ;
  40. ; Notes :
  41. ;    - created June 28 1991 GWS
  42. ;    - Borland C startup file for OS/2 device drivers
  43. ;    - changed to BC++ for DOS May 2, 1993 GWS
  44. ;
  45. ; This is a startup file for OS/2 device drivers written entirely with 
  46. ; Borland 3.0 DOS based tools. OS/2 device drivers are not difficult but
  47. ; they are different than regular C programs, they don't have a main()
  48. ; function. The OS calls an entry point defined by the device driver
  49. ; header. The entry point is called Entry and is in this module. The
  50. ; entry point calls the startup code if the startup code hasn't been run
  51. ; before and then transfers to a function called Strategy passing the pointer
  52. ; to the device request packet as the only parameter.
  53. ;
  54. ; This code handles 1 entry point but more can be added by creating more 
  55. ; entry point and strategy handlers.
  56. ;
  57. %pagesize
  58.  
  59. ;        Memory layout.
  60. ;
  61. ; OS/2 drivers have two segments. Data and code segments.
  62. ; the data segment must begin with the device header
  63. ;
  64. ; When the driver is called with the INIt packet,
  65. ; the driver returns 2 memory limits for each of these
  66. ; segments. Memory beond these limits is removed and returned
  67. ; to OS free store. IT IS IMPORTANT  that memory beond
  68. ; these limits not be used to store data or code to be
  69. ; used after the INIT functions returned.
  70.  
  71. ; also it is important that code and data which is not used
  72. ; after the INIT packet, be placed after these memory limits
  73. ; to conserve memory.
  74.  
  75. ; I have used two strategies to place code and data
  76. ; in their proper places with respect to these memory limits.
  77.  
  78. ; one strategy is used to group code with respect to its memory
  79. ; limit. borland c++ uses one segment _TEXT and assumes cs points
  80. ; to it. In the compact model, no group is used for this code segment.
  81. ; No group statment generated by bcc mentions _TEXT.
  82. ; to deal with this I create an assembly module codeend.asm
  83. ; which defines the memory limit for the code segment in _TEXT
  84. ; all modules that are to be resident after the INIT packet
  85. ; are placed before codeend.obj in the TLINK command line
  86. ; modules that are not to be resident after the INIT packet
  87. ; are placed after the codend.obj in the TLINK command line.
  88. ; i.e.
  89. ; tlink /m/s c0+$(BASENAME)+rand+movmem+codend+startup+start,\
  90. ;    $(BASENAME),,$(COMPILER_PATH)\lib\cc.lib $(OS2_LIB),$(BASENAME)/m;
  91.  
  92. ; in this example the code for c0.obj, $(BASENAME)=randdrv.obj
  93. ; rand.obj, movmem.obj
  94. ; must remain after the INIT packet is processed.
  95. ; the code from startup.obj, start.obj and the BCC rtl
  96. ; are only used during the processing for the INIT packet.
  97. ; movmem.obj is from the BCC RTL but must be compiled seperately
  98. ; so that it can be placed before codend. as it is used by RANDDRV.OBJ
  99. ; after INIT.
  100. ; there is one exception to this strategy, c0.asm does contain
  101. ; some code to be used only during INIT. But since c0 is written
  102. ; in assembler, This code is placed in its own segment _ITEXT
  103. ; a group directive is used to place this segment after _TEXT in
  104. ; memory.
  105. ; group CGROUP    _TEXT,_ITEXT
  106. ; since the _TEXT segment appears first, the assumption made
  107. ; by the BCC code is not broken and the assembly module c0.asm
  108. ; can use the group statement to address its data.
  109. %pagesize
  110. ;    layout of the data segment
  111. ; BCC does use GROUPS segment directives for its data.
  112. ; therefore GROUP statements and segments can be used
  113. ; to place data with respect to the data memory limit.
  114. ; the data memory limit, _memoryend, is placed in the
  115. ; segment _BBSEND. segments are place before or
  116. ; after this segment for the DGROUP data segment
  117. ; depending on wheater the data should be retained
  118. ; after the INIT.
  119. ;;  BCC modules that must be used after the INIT are compiled
  120. ; with the switches:
  121. ; -zD_RBSS -zR_RDATA -zBDATA
  122. ; this directs data to the segment RDATA
  123. ; and uninitialized data to RBSS.
  124.  
  125. ; modules that are not needed after the INIT
  126. ; are compiled normally and the segments go after the
  127. ; memory limit. Thus the RTL does not need to be re-compiled.
  128.  
  129. ; the module movmem is used after the INIT, therefore it must
  130. ; be specially compiled with the switches to place its data
  131. ; properly.
  132.  
  133. ; I have devided the uninitialized data segment _BSS into 2
  134. ; segments, _BSS and _RBSS. _RBSS is used for data that
  135. ; remains after INIT. Since we are writting the startup code
  136. ; c0.asm we can arrange to have both zeroed.
  137.  
  138. ; like wise there are 2 DATA segments _DATA and _RDATA.
  139.  
  140. ;must use compact model because the stack is far in a driver therefore
  141. ;local data is far.
  142. %pagesize
  143. ; model
  144. ASMMODEL EQU COMPACT
  145.  
  146.  
  147. ;os/2 now requires 386.
  148. P386
  149. ;enable local symbols
  150. locals
  151.  
  152. ;
  153. ; define all sequences
  154. macro    DefineSegment    segmentName,alignmentType,classType
  155. segment    segmentName    alignmentType public classType
  156. ends    segmentName    
  157. endm
  158. ; make sure the data segment is the first one in the .sys module
  159. ;
  160. ; Header must be first in data segment.
  161.     DefineSegment    _HEADER,para,'DATA'
  162.     DefineSegment    _RDATA,para,'DATA'
  163.     DefineSegment    _RBSS,word,'DATA'
  164. ; _RBSSEND defines end of resident data.
  165.     DefineSegment    _RBSSEND,byte,'DATA'
  166.     DefineSegment    _DATA,para,'DATA'
  167.     DefineSegment    _INIT_,word,'INITDATA'
  168.     DefineSegment    _INITEND_,byte,'INITDATA'
  169.     DefineSegment    _EXIT_,word,'EXITDATA'
  170.     DefineSegment    _EXITEND_,byte,'EXITDATA'
  171.     DefineSegment    _BSS,word,'BSS'
  172.     DefineSegment    _BSSEND,byte,'BSSEND'
  173.     DefineSegment    _TEXT,word,'CODE'
  174.     DefineSegment    _ITEXT,word,'CODE'
  175. ;driver requires first group be data, second code
  176. ;driver header must be first.
  177.  
  178. ; segemnts before _RBSSEND are resident
  179. group    DGROUP    _HEADER,_RDATA,_INIT_,_INITEND_,_EXIT_,_EXITEND_,_RBSS,_RBSSEND,_BSS,_BSSEND,_DATA
  180. ;
  181. ; _ITEXT is used only by c0.asm
  182. ; only used during INIT.
  183. group CGROUP    _TEXT,_ITEXT
  184. ;
  185. PUBLIC _AHINCR,_AHSHIFT
  186.  
  187.  
  188. _AHINCR        =     1000h
  189. _AHSHIFT       =     12
  190. ;
  191. ; these segments delimit the startup data for c++
  192. SEGMENT        _INIT_        
  193. label FirstStartupEntry byte
  194. ENDS    _INIT_        
  195. ;
  196. SEGMENT _INITEND_    
  197. label EndOfStartup    byte
  198. ENDS    _INITEND_    
  199. ;
  200. SEGMENT     _BSS        
  201. label    BSSStart    byte
  202. ENDS    _BSS        
  203. ;
  204. SEGMENT     _BSSEND        
  205. label   BSSEnd        byte
  206. ENDS    _BSSEND        
  207. SEGMENT     _RBSS        
  208. label    RBSSStart    byte
  209. ENDS    _RBSS        
  210. ;
  211. SEGMENT     _RBSSEND        
  212. label   RBSSEnd        byte
  213. ;
  214. ;delimit end of data segments.
  215. ;
  216. ; _memoryEnd is the end of the residnet data in the DATA segment.
  217. public    _memoryEnd
  218. label    _memoryEnd    byte
  219. ENDS    _RBSSEND        
  220. ;
  221. ; use 16 bit addressing in os/2 driver
  222. ; use c language for interface to c,c++ code
  223.     model USE16 ASMMODEL,C
  224.     ASSUME CS:CGROUP
  225. ;
  226. ; external procedures
  227. extrn    _CodeEnd:byte
  228. extrn    memset:proc
  229. CODESEG
  230. extrn    CallStartup:proc
  231. extrn    Strategy1:proc
  232. ;
  233. SEGMENT _HEADER
  234. extrn Entry:word
  235. ENDS _HEADER
  236. CODESEG
  237. ;
  238. ; This procedure is the entry point after the INIT is processed.
  239. ; it is resident.
  240. proc    Entry2    far                ;
  241.     ;call driver startegy code defined in randdrv.cpp
  242. ;     simply call the c++ strategy routine using es:bx
  243. ;     as the parameter.
  244.     call    near Strategy1 C,es bx        ;
  245. ;add redirect
  246.      ret                    ;
  247. endp    Entry2                    ;
  248.  
  249. %pagesize
  250. ; code exists only until INIT is completed.
  251. SEGMENT    _ITEXT
  252.     ASSUME CS:CGROUP
  253.  
  254. ;
  255. ; clear the BSS then call all the initialisers
  256. ;
  257. proc    DoStartup    near NOLANGUAGE    
  258.     pusha                    ;
  259.     push    es                ;
  260.  
  261.  
  262. ;     clear RBSS. resident uninitialized data.
  263.     mov    ax,offset DGROUP:RBSSEnd        ;
  264.     sub    ax,offset DGROUP:RBSSStart    ; ax = the length of the BSS
  265.  
  266.     call    memset    C,ds offset DGROUP:RBSSStart,0,ax        ;
  267.     
  268.                         ; Clear the BSS
  269.  
  270. ;    clear BSS non-resident uninitialized data.
  271.     mov    ax,offset DGROUP:BSSEnd        ;
  272.     sub    ax,offset DGROUP:BSSStart    ; ax = the length of the BSS
  273.  
  274.     call    memset    C,ds offset DGROUP:BSSStart,0,ax        ;
  275.     
  276. ;    call the c++ initializers.
  277.     call    near CallStartup C,ds offset DGROUP:FirstStartupEntry,ds offset DGROUP:EndOfStartup
  278.                         ;
  279.     pop    es                ;
  280.     popa                    ;
  281.     ret
  282. endp    DoStartup    
  283. ;This is the initial entry point for the driver.
  284. ;entry point is moved after when finished.
  285. ;
  286. public    Entry1            
  287. proc    Entry1    far                ;
  288.     ; call startup initialization code
  289.     call    near DoStartup NOLANGUAGE            ;
  290.     ;call driver startegy code defined in randdrv.cpp
  291.     call    near Strategy1 C,es bx        ;
  292.  
  293. ;    add redirect
  294. ;    driver has been initialized redefine
  295. ;    driver entry point to be resident code ENTRY2.
  296. ;    by adjusting pointer in DRIVER header.
  297.     mov    [Entry],offset CGROUP:Entry2
  298.  
  299.      ret                    ;
  300. endp    Entry1                    ;
  301. ;    end of segment. exists only during INIT.
  302. ENDS    _ITEXT
  303. %pagesize
  304. CODESEG
  305. ;
  306. ;
  307. ; The following definitions are required when linking in the sprintf/sscanf
  308. ; routines to stop them from hauling in all sorts of floating point and
  309. ; error handling code.
  310. ;
  311. public abort
  312. label    abort        word
  313. ;
  314.                 public _RealCvtVector
  315. label     _RealCvtVector word
  316. ;
  317. public     _ScanTodVector
  318. label     _ScanTodVector word
  319. ;
  320.     end                        ;
  321.  
  322.