     1                                  ; Retro UNIX 386 v1 Terminal Program (DOS version)
     2                                  ; (Standalone DOS program)
     3                                  ; by Erdogan TAN
     4                                  ;
     5                                  ; Last Update: 10/11/2015	
     6                                  ;
     7                                  ; serial5.s - 10/11/2015 NASM 2.11 (buffered read)
     8                                  ;
     9                                  ; SERIAL4.ASM - 26/10/2015 (Retro UNIX 386 v1 - Kernel v0.2.0.15)
    10                                  ; SERIAL1.ASM (Retro UNIX 8086 v1)
    11                                  ; 08/07/2014, 23/07/2013, 27/07/2014 
    12                                  ; (06/07/2014, 05/07/2014, 04/07/2014, 03/07/2014)
    13                                  
    14                                  ; Assembler: NASM 2.11 
    15                                  
    16                                  [BITS 16]
    17                                  
    18                                  		[ORG 100h]
    19                                  
    20                                  		; 10/11/2015
    21                                  		; clear bss section
    22 00000000 B9[3406]                		mov	cx, bss_end
    23 00000003 BF[2004]                		mov	di, bss_start
    24 00000006 31C0                    		xor	ax, ax
    25 00000008 29F9                    		sub	cx, di
    26 0000000A D1E9                    		shr	cx, 1
    27 0000000C F3AB                    		rep	stosw
    28                                  		;
    29 0000000E B80006                  		mov 	ax, 0600h  ; Scroll up, clear (AL=0)
    30 00000011 B707                    		mov	bh, 07h    ; Black backround (0), 
    31                                  				   ; Light gray foreground (7)
    32                                  		;sub	cx, cx     ; Left-Upper column, row
    33 00000013 BA4F18                  		mov	dx, 184Fh  ; Righ-Lower column, row
    34 00000016 CD10                    		int 	10h			 
    35                                  		;
    36 00000018 B402                    		mov	ah, 2	   ; Set cursor position 	
    37 0000001A 31D2                    		xor	dx, dx	   ; Row 0 (DH), Column 0 (DL)	
    38 0000001C 30FF                    		xor	bh, bh ; 0
    39 0000001E CD10                    		int 	10h
    40                                  		;
    41 00000020 BE[0203]                		mov	si, StartMsg
    42 00000023 B307                    		mov	bl, 7
    43 00000025 E85002                  		call	proc_printmsg
    44                                  		;
    45 00000028 31C0                    		xor 	ax, ax
    46 0000002A 8ED8                    		mov	ds, ax
    47 0000002C BE6C00                  		mov	si, 27*4 
    48                                  				   ; INT 1Bh vector
    49 0000002F BF[2204]                		mov	di, old_ctrlbrk
    50 00000032 A5                                      movsw              ; Save the old ctrl+brk interrupt 
    51 00000033 A5                                      movsw
    52                                  		; 06/11/2015
    53                                  		;mov	si, 28*4 
    54                                  				   ; INT 1Ch vector
    55                                  		;mov	di, old_timer
    56 00000034 A5                                      movsw              ; Save the old timer interrupt 
    57 00000035 A5                                      movsw
    58                                  		;
    59 00000036 0E                                      push    cs
    60 00000037 1F                      		pop	ds
    61 00000038 FA                      		cli	; 06/11/2215
    62 00000039 8EC0                    		mov	es, ax
    63 0000003B B8[6802]                		mov	ax, ctrlbrk
    64 0000003E BF6C00                  		mov	di, 27*4   ; INT 1Bh vector - offset
    65 00000041 AB                      		stosw		
    66 00000042 8CC8                    		mov	ax, cs
    67 00000044 AB                      		stosw		   ; INT 1Bh vector - segment
    68                                  
    69                                  		; 06/11/2015
    70                                  		; INT 1Ch periodic timer interrupt (18.2 times per second)
    71                                  		;mov	di, 28*4   ; INT 1Ch vector - offset
    72                                  		;cli	; 06/11/2015
    73 00000045 B8[6E02]                		mov 	ax, _timer
    74 00000048 AB                      		stosw
    75 00000049 8CC8                      		mov	ax, cs
    76 0000004B AB                      		stosw		   ; INT 1Ch vector - segment
    77                                  
    78 0000004C 8EC0                    		mov	es, ax
    79 0000004E FB                      		sti	; 06/11/2015
    80                                  s0:
    81 0000004F 30E4                    		xor	ah, ah
    82 00000051 CD16                    		int 	16h
    83                                  		;
    84 00000053 3C31                    		cmp	al, '1'
    85 00000055 7426                    		je	short s1
    86 00000057 3C32                    		cmp	al, '2'
    87 00000059 7408                    		je	short _0
    88                                  		;
    89 0000005B B007                    		mov	al, 07h	   ; BEEP !
    90 0000005D B40E                    		mov	ah, 0Eh
    91 0000005F CD10                    		int	10h
    92 00000061 EBEC                    		jmp	short s0
    93                                  _0:
    94 00000063 BE[1504]                		mov	si, _3F8h + 1
    95 00000066 FE0C                    		dec 	byte [SI]	; 2F8h
    96 00000068 83C602                  		add	si, 2
    97 0000006B FE0C                    		dec 	byte [SI]	; 2F9h
    98                                  		; 28/10/2015
    99                                  		;add	si, 2
   100                                  		;dec 	byte [SI]	; 2FAh
   101 0000006D 83C602                  		add	si, 2
   102 00000070 FE0C                    		dec 	byte [SI]	; 2FCh
   103 00000072 83C602                  		add	si, 2
   104 00000075 FE0C                    		dec 	byte [SI]	; 2FDh
   105                                  		;add	si, 2
   106                                  		;dec 	byte [SI]	; 2FEh
   107                                  		;
   108 00000077 BE[1204]                		mov	si, _EFh
   109 0000007A C604F7                  		mov 	byte [SI], 0F7h	
   110                                  s1:
   111 0000007D 2C31                    		sub	al, '1'
   112 0000007F A2[2004]                		mov	byte [port], al
   113                                  		;
   114 00000082 BE[9D03]                		mov     si, ComSMsg
   115 00000085 004404                                  add     byte [SI+4], al
   116                                  		;mov	bx, 7
   117 00000088 E8ED01                  		call	proc_printmsg
   118                                  		;
   119                                  		; 26/10/2015
   120 0000008B E8F601                  		call	set_spcp ; Set communication parameters
   121 0000008E 7309                    		jnc	short s2
   122 00000090 BE[E903]                                mov     si, ErrMsg
   123                                  		;mov	bx, 7
   124 00000093 E8E201                  		call	proc_printmsg
   125 00000096 E9D600                  		jmp	_exit
   126                                  s2:
   127                                  		; 06/11/2015
   128 00000099 8A16[2004]              		mov	dl, byte [port]
   129                                  				   ; hook serial port interrupt
   130 0000009D 31C0                    		xor	ax, ax ; 0
   131 0000009F 8ED8                    		mov 	ds, ax	   ; IVT base
   132                                  
   133 000000A1 BE2C00                  		mov	si, 0Bh*4  ; Port 1 (COM2)
   134 000000A4 20D2                    		and	dl, dl     ; Port 0 (COM1) ?
   135 000000A6 7503                    		jnz	short s3
   136 000000A8 83C604                  		add	si, 4	   ; 0Ch*4 (COM1)
   137                                  s3:
   138 000000AB 56                      		push	si
   139 000000AC BF[2A04]                                mov     di, old_serial
   140 000000AF A5                                      movsw              ; Save the old serial port interrupt   
   141 000000B0 A5                                      movsw
   142                                          	;
   143 000000B1 0E                      		push	cs
   144 000000B2 1F                      		pop	ds
   145 000000B3 8EC0                                    mov     es, ax     ; 0
   146 000000B5 5F                      		pop	di
   147                                  		;
   148 000000B6 FA                      		cli
   149 000000B7 B8[EB01]                		mov 	ax, serial  ; serial port interrupt handler
   150 000000BA AB                      		stosw		   ; INT 0Ch (0Bh) vector -   
   151 000000BB 8CC8                    		mov	ax, cs
   152 000000BD AB                      		stosw		   ; INT 0Ch (0Bh) vector - segment	
   153                                  		;mov	es, ax
   154 000000BE FB                      		sti              
   155                                  		;
   156 000000BF BE[B103]                		mov     si, AnyKeyMsg
   157 000000C2 E8B301                  		call	proc_printmsg
   158                                  		;
   159 000000C5 30E4                    		xor	ah, ah
   160 000000C7 CD16                    		int 	16h
   161                                  		;
   162 000000C9 3C1B                    		cmp	al, 1Bh    ; ESC key
   163 000000CB 0F84B700                                je      _return 
   164                                  		;
   165 000000CF 1E                      		push	ds
   166 000000D0 07                      		pop	es
   167                                  		;
   168 000000D1 B80006                  		mov 	ax, 0600h  ; Scroll up, clear (AL=0)
   169 000000D4 B717                    		mov	bh, 17h    ; Blue backround (1), 
   170                                  				   ; Light gray foreground (7)
   171 000000D6 29C9                    		sub	cx, cx     ; Left-Upper column, row
   172 000000D8 BA4F18                  		mov	dx, 184Fh  ; Righ-Lower column, row
   173 000000DB CD10                    		int 	10h			 
   174                                  		;
   175 000000DD B402                    		mov	ah, 2	   ; Set cursor position 	
   176 000000DF 29D2                    		sub	dx, dx	   ; Row 0 (DH), Column 0 (DL)	
   177 000000E1 BB0700                  		mov	bx, 7	
   178 000000E4 CD10                    		int 	10h
   179                                  		;
   180                                  		; 28/10/2015
   181 000000E6 29C0                    		sub	ax, ax 	   ; null
   182                                  		; 06/11/2015
   183 000000E8 A3[3004]                		mov	word [ticks], ax ; 0 ; reset timer ticks
   184 000000EB EB7A                                    jmp     short _3 ; query (initialization, wakeup signal)
   185                                  
   186                                  sendchr:
   187                                  		; 10/11/2015
   188 000000ED E8A500                  		call	print  ; move and print received chars on the screen
   189                                  		;
   190 000000F0 3826[2104]              		cmp 	byte [cbrk], ah ; 0 ; ctrl + break
   191 000000F4 7779                                    ja      short _exit
   192                                                  ; 06/11/2015
   193 000000F6 A0[2F04]                		mov 	al, byte [rchar]
   194 000000F9 08C0                    		or	al, al
   195 000000FB 7512                    		jnz	short s4
   196 000000FD FEC8                    		dec	al ; 0FFh
   197 000000FF 3806[2E04]              		cmp	byte [schar], al ; 0FFh
   198 00000103 7423                    		je	short getchr
   199                                  response:
   200                                  		; the remote process is waiting for response !
   201 00000105 A2[2E04]                		mov 	byte [schar], al ; 0FFh  ; response
   202 00000108 FEC0                    		inc	al
   203 0000010A A3[3004]                		mov	word [ticks], ax ; 0 ; reset connection timeout
   204 0000010D EB55                    		jmp	short _2 ; _1
   205                                  s4:
   206 0000010F 3826[2E04]              		cmp 	byte [schar], ah ; 0  ; query (wait for response)
   207 00000113 770B                    		ja	short s5
   208 00000115 3CFF                    		cmp	al, 0FFh ; response
   209 00000117 740F                    		je	short getchr
   210                                  query:
   211                                  		; connection time out ! wait for response ...
   212 00000119 30C0                    		xor	al, al ; ax = 0
   213 0000011B A3[3004]                		mov	word [ticks], ax ;0 ; reset connection timeout
   214 0000011E EB1C                    		jmp	short _1 ; _2	 	
   215                                  s5:
   216 00000120 813E[3004]A101          		cmp	word [ticks], 417
   217 00000126 732D                     		jnb	short rq
   218                                  getchr:	
   219 00000128 B401                    		mov	ah, 1
   220 0000012A CD16                    		int	16h
   221 0000012C 7505                    		jnz	short s6
   222                                  		;hlt
   223                                  		;nop
   224                                  		;nop
   225                                  		;nop
   226                                  		; 10/11/2015
   227                                  		; Do somethings while waiting for
   228                                  		; 'transmitter holding register empty' status
   229                                  		;
   230 0000012E E86400                  		call 	print	; move and print received chars on the screen
   231                                  		;
   232 00000131 EBF5                    		jmp	short getchr
   233                                  s6:
   234 00000133 30E4                    		xor	ah, ah 	   ; 0
   235 00000135 CD16                    		int	16h	   ; Read character
   236                                  		; 28/10/2015
   237 00000137 A2[2E04]                		mov 	byte [schar], al
   238 0000013A 28E4                    		sub	ah, ah
   239                                  _1:
   240                                  		; 06/11/2015
   241 0000013C 3826[2104]              		cmp	byte [cbrk], ah ; exit sign
   242 00000140 772D                    		ja	short _exit
   243                                  		; 29/10/2015
   244 00000142 8B16[1A04]              		mov	dx, word [_3FDh] ; Line status register 
   245 00000146 EC                      		in	al, dx	   ; read register
   246 00000147 EB00                    		JMP	$+2	   ; I/O DELAY
   247 00000149 A880                    		test	al, 80h	   ; time out error
   248 0000014B 740E                    		jz	short s7
   249 0000014D 813E[3004]A101          		cmp	word [ticks], 417
   250 00000153 72E7                     		jb	short _1
   251                                  rq:
   252 00000155 8826[2E04]              		mov 	byte [schar], ah ; 0  ; query (wait for response) 
   253 00000159 EBBE                    		jmp	short query
   254                                  s7:
   255 0000015B 2420                    		and	al, 20h	   ; Transmitter holding reg. empty?
   256 0000015D 7505                    		jnz	short _2   ; yes, ready to send
   257                                  		;
   258                                  		;xor	dh, dh
   259                                  		;mov	dl, byte [port]
   260                                  		;mov	ah, 3
   261                                  		;int	14h
   262                                  		;and	ah, 32 	   ;trasmitter holding register empty
   263                                  		;jnz	short _2   ;yes, ready to send
   264                                  		;
   265                                  		;hlt		   ;no, check status again
   266                                  		;nop
   267                                  		;nop
   268                                  		;jmp	short _1
   269                                  		;
   270                                  		; 10/11/2015
   271                                  		; Do somethings while waiting for 
   272                                  		; 'transmitter holding register empty' status
   273                                  		;
   274 0000015F E83300                  		call 	print	; move and print received chars on the screen
   275                                  		;
   276 00000162 EBD8                    		jmp	short _1
   277                                  _2:
   278 00000164 A0[2E04]                		mov 	al, byte [schar]
   279                                  _3:
   280 00000167 8B16[1404]              		mov	dx, word [_3F8h] ; data port
   281 0000016B EE                      		out	dx, al	   ; send on serial port
   282                                  		; ah = 0
   283                                  		; 10/11/2015
   284 0000016C E97EFF                                  jmp    sendchr
   285                                  
   286                                  _exit:
   287                                  				   ; Restore old interrupt vectors
   288 0000016F 31C0                    		xor	ax, ax
   289 00000171 8EC0                                    mov	es, ax     ; 0
   290 00000173 BE[2A04]                                mov	si, old_serial
   291 00000176 BF2C00                  		mov	di, 0Bh*4 ; (COM2)
   292 00000179 FE0E[2004]              		dec	byte [port] 
   293 0000017D 7403                    		jz	short s8
   294 0000017F 83C704                  		add	di, 4	   ; 0Ch*4 (COM1)
   295                                  s8:
   296 00000182 FA                      		cli
   297 00000183 A5                                      movsw              ; Restore
   298 00000184 A5                                      movsw
   299 00000185 FB                      		sti        
   300                                  _return:
   301 00000186 BE[2204]                		mov	si, old_ctrlbrk
   302 00000189 BF6C00                  		mov	di, 27*4 
   303                                  				   ; INT 1Bh vector
   304 0000018C A5                                      movsw              ; Restore 
   305 0000018D A5                                      movsw
   306                                  		; 06/11/2015
   307                                  		;mov	si, old_timer
   308                                  		;mov	di, 28*4 
   309                                  				   ; INT 1Ch vector
   310 0000018E A5                                      movsw              ; Restore 
   311 0000018F A5                                      movsw
   312                                  		;
   313 00000190 CD20                    		int 20h
   314                                  here:
   315 00000192 F4                      		hlt
   316 00000193 EBFD                    		jmp	 short here
   317                                  
   318                                  print:
   319                                  		; 10/11/2015
   320                                  		;
   321                                  		; write received chars (in buffer) to screen
   322                                  		;
   323 00000195 BE[3205]                		mov	si, rbuffer
   324 00000198 BF[3204]                		mov	di, wbuffer
   325 0000019B 893E[1E04]              		mov	word [wb_off], di
   326 0000019F FA                      		cli	; interrupts off		
   327 000001A0 8B0E[1C04]              		mov	cx, word [rb_off] ; read buffer offset
   328 000001A4 29F1                    		sub	cx, si
   329 000001A6 7702                    		ja	short p0
   330                                  		; empty buffer !
   331 000001A8 FB                      		sti	; interrupts on	
   332 000001A9 C3                      		retn
   333                                  p0:
   334                                  		; move chars to writing buffer (from reading buffer)
   335                                  		; while serial port interrupt is disabled
   336                                  		;
   337 000001AA 010E[1E04]              		add	word [wb_off], cx ; byte/char count
   338                                  		;
   339 000001AE F3A4                    		rep	movsb
   340                                  		;
   341 000001B0 C706[1C04][3205]        		mov	word [rb_off], rbuffer ; reset
   342 000001B6 FB                      		sti	; interrupts on
   343                                  		;
   344 000001B7 BE[3204]                		mov	si, wbuffer
   345                                  		;
   346 000001BA BB0700                  		mov	bx, 7    ; video page 0, color 7
   347 000001BD B40E                    		mov	ah, 0Eh  ; write chars as teletype output
   348                                  p1:	
   349                                  		; print chars (in writing buffer) on the screen
   350                                  		; while serial port interrupt is enabled (again)
   351                                  		;
   352 000001BF AC                      		lodsb
   353                                  		;
   354                                  		; 26/10/2015
   355 000001C0 3C09                    		cmp 	al, 9	   ; TAB key ?
   356 000001C2 751E                    		jne	short p3
   357 000001C4 51                      		push	cx
   358 000001C5 B403                    		mov 	ah, 3	  ; Get cursor position
   359                                  		;mov	bh, 0
   360 000001C7 CD10                    		int 	10h
   361 000001C9 59                      		pop 	cx
   362 000001CA 30E4                    		xor	ah, ah
   363 000001CC 88D0                    		mov	al, dl	   ; row
   364 000001CE B208                    		mov	dl, 8
   365 000001D0 F6F2                    		div	dl
   366 000001D2 B208                    		mov 	dl, 8
   367 000001D4 28E2                    		sub	dl, ah
   368 000001D6 B020                    		mov	al, 20h
   369 000001D8 B40E                    		mov	ah, 0Eh
   370                                  		;mov	bx, 7
   371                                  p2:
   372 000001DA FECA                    		dec	dl
   373 000001DC 7404                    		jz	short p3
   374 000001DE CD10                    		int	10h	   ; Write character on TTY display
   375 000001E0 EBF8                    		jmp 	short p2	
   376                                  p3:
   377 000001E2 CD10                    		int	10h	   ; Write character on TTY display
   378                                  		;
   379                                  		; 10/11/2015
   380 000001E4 3B36[1E04]              		cmp	si, word [wb_off]
   381 000001E8 72D5                    		jb	short p1
   382 000001EA C3                      		retn
   383                                  
   384                                  serial:		
   385                                  		; 10/11/2015
   386                                  		; 06/11/2015
   387                                  		; 28/10/2015
   388                                  		; 26/10/2015
   389                                  		;
   390                                                  ; INT 0Ch (0Bh) serial port interrupt handler        
   391                                  		;
   392 000001EB 1E                      		push	ds
   393 000001EC 50                      		push	ax
   394 000001ED 53                      		push	bx
   395 000001EE 52                      		push	dx
   396                                  		;
   397 000001EF 8CC8                    		mov	ax, cs
   398 000001F1 8ED8                    		mov	ds, ax
   399                                  		;
   400                                  		; 06/11/2015
   401 000001F3 C706[3004]0000          		mov	word [ticks], 0 ; Reset connection timeout
   402                                  		;
   403                                  		; 28/10/2015
   404 000001F9 8B16[1A04]              		mov	dx, word [_3FDh] ; Line status register 
   405 000001FD EC                      		in	al, dx	   ; read register
   406 000001FE EB00                    		JMP	$+2	   ; I/O DELAY
   407 00000200 2401                    		and	al, 01h	   ; Data ready?
   408 00000202 745B                    		jz	short _5   ; no
   409                                  		; 28/10/2015
   410 00000204 8B16[1404]              		mov	dx, word [_3F8h]
   411                                  				   ;data register
   412 00000208 EC                      		in	al, dx     ;read character
   413 00000209 EB00                    		JMP	$+2	   ; I/O DELAY
   414                                  		; 06/11/2015
   415 0000020B A2[2F04]                		mov	byte [rchar], al ; received char
   416                                  		; query
   417 0000020E 20C0                    		and 	al, al	   ; 0
   418 00000210 751C                    		jnz	short _4
   419                                                  ; response
   420 00000212 C606[2E04]00            		mov 	byte [schar], 0
   421 00000217 8B16[1A04]              		mov	dx, word [_3FDh] ; Line status register 
   422 0000021B EC                      		in	al, dx	   ; read register
   423 0000021C EB00                    		JMP	$+2	   ; I/O DELAY
   424 0000021E 2420                    		and	al, 20h	   ; Transmitter holding reg. empty?
   425 00000220 743D                    		jz	short _5   ; no
   426                                  		;
   427 00000222 B0FF                    		mov 	al, 0FFh   ; response			
   428 00000224 8B16[1404]              		mov	dx, word [_3F8h] ; data port
   429 00000228 EE                      		out	dx, al	   ; send on serial port
   430                                  		;JMP	$+2	   ; I/O DELAY
   431 00000229 A2[2E04]                		mov	byte [schar], al ; 0FFh
   432 0000022C EB31                    		jmp	short _5
   433                                  _4:
   434                                  		; 06/11/2015
   435 0000022E FEC0                    		inc	al	  ; al = FFh -> 0
   436 00000230 742D                    		jz	short _5  ; al = 0 (response, FFh)
   437 00000232 FEC8                    		dec	al		
   438                                  		; 10/11/2015 - Receive char and put it in read buffer
   439 00000234 8B1E[1C04]              		mov	bx, word [rb_off] ; read buffer offset
   440 00000238 BA[3206]                		mov 	dx, rbuffer + 256
   441 0000023B 39D3                    		cmp	bx, dx
   442 0000023D 7320                    		jnb	short _5 ; nothing to to (buffer is full!)
   443                                  		;
   444 0000023F 8807                                    mov     byte [bx], al  ; put character in buffer
   445                                  		;
   446 00000241 43                      		inc	bx	 ; points to next char address in buffer	
   447 00000242 891E[1C04]              		mov	word [rb_off], bx ; read buffer offset
   448 00000246 39D3                    		cmp 	bx, dx  ; end of buffer
   449 00000248 7215                    		jb	short _5
   450                                  		;
   451                                  		; Send query (0) and save time for printing
   452                                  		; all received chars on the screen 
   453                                  		; before buffer full status.
   454                                  		;
   455                                  		; 06/11/2015
   456 0000024A 8B16[1A04]              		mov	dx, word [_3FDh] ; Line status register 
   457 0000024E EC                      		in	al, dx	   ; read register
   458 0000024F EB00                    		JMP	$+2	   ; I/O DELAY
   459 00000251 2420                    		and	al, 20h	   ; Transmitter holding reg. empty?
   460 00000253 740A                    		jz	short _5   ; no
   461                                  		;
   462 00000255 28C0                    		sub	al, al     ; 0, query		
   463 00000257 8B16[1404]              		mov	dx, word [_3F8h] ; data port
   464 0000025B EE                      		out	dx, al	   ; send on serial port
   465                                  		;JMP	$+2	   ; I/O DELAY
   466 0000025C A2[2E04]                		mov	byte [schar], al ; 0
   467                                  _5:
   468 0000025F B020                    		mov	al, 20h
   469 00000261 E620                    		out	20h, al	   ;end of interrupt
   470                                  		;
   471 00000263 5A                      		pop	dx
   472 00000264 5B                      		pop	bx
   473 00000265 58                      		pop	ax
   474 00000266 1F                      		pop	ds
   475 00000267 CF                      		iret		
   476                                  
   477                                  ctrlbrk:
   478                                  		; INT 1Bh (control+break) handler		
   479                                  		;
   480 00000268 2EFE06[2104]                            inc     byte [CS:cbrk] 
   481 0000026D CF                      		iret
   482                                  _timer:
   483                                  		; 06/11/2015
   484                                  		; INT 1Ch (periodic timer interrupt (18.2 times per second)		
   485                                  		;
   486 0000026E 2EFF06[3004]                            inc     word [CS:ticks]
   487                                  		;iret 
   488 00000273 2EFF2E[2604]                            jmp     far [CS:old_timer] 
   489                                  
   490                                  proc_printmsg:
   491 00000278 B40E                    		mov	ah, 0Eh
   492                                  		;mov	bx, 7
   493                                  s9:
   494 0000027A AC                      		lodsb
   495 0000027B 20C0                    		and	al, al
   496 0000027D 7404                    		jz	short s10
   497 0000027F CD10                    		int 	10h
   498 00000281 EBF7                    		jmp	short s9
   499                                  s10:          
   500 00000283 C3                      		retn
   501                                  
   502                                  set_spcp: ; Set serial port communication parameters
   503                                  	; 26/10/2015 (SERIAL3.ASM)
   504                                  	; 29/06/2015 (Retro UNIX 386 v1 - u0.s)
   505                                  	;
   506                                  	;  Communication parameters (except BAUD RATE):
   507                                  	;	Bit	4	3	2	1	0
   508                                  	;		-PARITY--   STOP BIT  -WORD LENGTH-	 		 
   509                                  	;  this one -->	00 = none    0 = 1 bit  11 = 8 bits
   510                                  	;		01 = odd     1 = 2 bits	10 = 7 bits
   511                                  	;		11 = even
   512                                  	;  Baud rate setting bits: (29/06/2015)
   513                                  	;		Retro UNIX 386 v1 feature only !
   514                                  	;	Bit	7    6    5  | Baud rate
   515                                  	;		------------------------
   516                                  	;	value	0    0    0  | Default (Divisor = 1)
   517                                  	;		0    0    1  | 9600 (12)
   518                                  	;		0    1    0  | 19200 (6) 
   519                                  	;		0    1	  1  | 38400 (3) 
   520                                  	;		1    0	  0  | 14400 (8)
   521                                  	;		1    0	  1  | 28800 (4)
   522                                  	;		1    1    0  | 57600 (2)
   523                                  	;		1    1    1  | 115200 (1) 
   524                                  	;	
   525                                  	; References:	
   526                                  	; (1) IBM PC-XT Model 286 BIOS Source Code
   527                                  	;     RS232.ASM --- 10/06/1985 COMMUNICATIONS BIOS (RS232)
   528                                  	; (2) Award BIOS 1999 - ATORGS.ASM
   529                                  	; (3) http://wiki.osdev.org/Serial_Ports
   530                                  	;
   531                                  	; (COM1 base port address = 3F8h, COM1 Interrupt = IRQ 4)
   532                                  	; (COM2 base port address = 2F8h, COM1 Interrupt = IRQ 3)
   533                                  	;
   534                                  	; ((Modified registers: EAX, ECX, EDX, EBX))
   535                                  	;
   536                                  	;mov	cl, 1 ; divisor = 1 (115200 baud)
   537                                  	;mov	ch, 3 ; communication parameters except divisor 
   538 00000284 B90103                  	mov	cx, 301h
   539                                  sp_i1:
   540 00000287 BAF803                  	mov	dx, 3F8h  ; COM1 Data register
   541                                  	; 26/10/2015
   542 0000028A A0[2004]                	mov 	al, byte [port]
   543 0000028D 08C0                    	or	al, al
   544 0000028F 7402                    	jz	short sp_i2 ;  COM1 (AL = 0)
   545                                  	;
   546 00000291 FECE                    	dec	dh ; 2F8h, COM2 Data register
   547                                  sp_i2:
   548                                    	;-----	INITIALIZE THE COMMUNICATIONS PORT
   549                                  	; 28/10/2015
   550 00000293 FEC2                    	inc	dl	; 3F9h (2F9h)	; 3F9h, COM1 Interrupt enable register 
   551 00000295 B000                    	mov	al, 0
   552 00000297 EE                      	out	dx, al			; disable serial port interrupt
   553 00000298 EB00                    	JMP	$+2			; I/O DELAY
   554 0000029A 80C202                  	add	dl, 2 	; 3FBh (2FBh)	; COM1 Line control register (3FBh)
   555 0000029D B080                    	mov	al, 80h			
   556 0000029F EE                      	out	dx, al			; SET DLAB=1 ; divisor latch access bit
   557 000002A0 EB00                    	JMP	$+2			; I/O DELAY
   558                                  	;-----	SET BAUD RATE DIVISOR
   559                                  	; 26/10/2015
   560 000002A2 80EA03                  	sub 	dl, 3   ; 3F8h (2F8h)	; register for least significant byte
   561                                  					; of the divisor value
   562 000002A5 88C8                    	mov	al, cl	; 1
   563 000002A7 EE                      	out	dx, al			; 1 = 115200 baud (Retro UNIX 386 v1)
   564                                  					; 2 = 57600 baud
   565                                  					; 3 = 38400 baud
   566                                  					; 6 = 19200 baud
   567                                  					; 12 = 9600 baud (Retro UNIX 8086 v1)
   568 000002A8 EB00                    	JMP	$+2			; I/O DELAY
   569 000002AA 28C0                    	sub	al, al
   570 000002AC FEC2                    	inc	dl      ; 3F9h (2F9h)	; register for most significant byte
   571                                  					; of the divisor value
   572 000002AE EE                      	out	dx, al ; 0
   573 000002AF EB00                    	JMP	$+2			; I/O DELAY
   574                                  	;	
   575 000002B1 88E8                    	mov	al, ch ; 3		; 8 data bits, 1 stop bit, no parity
   576                                  	;and	al, 1Fh ; Bits 0,1,2,3,4	
   577 000002B3 80C202                  	add	dl, 2	; 3FBh (2FBh)	; Line control register
   578 000002B6 EE                      	out	dx, al			
   579 000002B7 EB00                    	JMP	$+2			; I/O DELAY
   580                                  	; 29/10/2015
   581 000002B9 FECA                    	dec 	dl 	; 3FAh (2FAh)	; FIFO Control register (16550/16750)
   582 000002BB 30C0                    	xor	al, al			; 0
   583 000002BD EE                      	out	dx, al			; Disable FIFOs (reset to 8250 mode)	
   584 000002BE EB00                    	JMP	$+2
   585                                  sp_i3:
   586                                  	;-----	COMM PORT STATUS ROUTINE
   587                                  	; 28/10/2015
   588                                  	; 26/10/2015
   589 000002C0 80C203                  	add	dl, 3	; 3FDh (2FDh)	; COM1 Line status register (3FDh) 
   590 000002C3 8A26[3206]              	mov	ah, byte [error]
   591 000002C7 08E4                    	or	ah, ah ; 0?
   592 000002C9 7512                    	jnz	short sp_i4 ; error! 
   593 000002CB EC                      	in	al, dx			; GET LINE CONTROL STATUS
   594 000002CC EB00                    	JMP	$+2			; I/O DELAY
   595 000002CE A880                    	test	al, 80h			; Timeout!?
   596 000002D0 740D                    	jz	short sp_i5
   597 000002D2 FEC4                    	inc	ah ; 1
   598 000002D4 8826[3206]              	mov	byte [error], ah
   599 000002D8 B90E03                          mov     cx, 30Eh 		; Reset to 9600 baud
   600 000002DB EBAA                    	jmp 	short sp_i1
   601                                  sp_i4:
   602 000002DD F9                      	stc
   603 000002DE C3                      	retn
   604                                  sp_i5:
   605                                  	; 02/11/2015
   606                                  	; 28/10/2015
   607                                  	; 26/10/2015
   608                                  	; 29/06/2015
   609                                  	;; COM1 - enabling IRQ 4
   610                                  	;; (COM2 - enabling IRQ 3)
   611 000002DF 8B16[1804]              	mov	dx, word [_3FCh]	; modem control register
   612 000002E3 EC                      	in	al, dx 	   		; read register
   613 000002E4 EB00                    	JMP	$+2			; I/O DELAY
   614 000002E6 0C08                    	or	al, 8      		; enable bit 3 (OUT2)
   615 000002E8 EE                      	out	dx, al     		; write back to register
   616 000002E9 EB00                    	JMP	$+2			; I/O DELAY
   617 000002EB 8B16[1604]              	mov	dx, word [_3F9h]	; interrupt enable register
   618 000002EF EC                      	in	al, dx     		; read register
   619 000002F0 EB00                    	JMP	$+2			; I/O DELAY
   620                                  	;or	al, 3      		; transmitter empty 
   621                                  					; interrupt enable and
   622 000002F2 0C01                    	or	al, 1			; receiver data interrupt enable
   623 000002F4 EE                      	out	dx, al 	   		; write back to register
   624 000002F5 EB00                    	JMP	$+2        		; I/O DELAY
   625 000002F7 E421                    	in	al, 21h    		; read interrupt mask register
   626 000002F9 EB00                    	JMP	$+2        		; I/O DELAY
   627 000002FB 2206[1204]                      and     al, byte [_EFh]     ; enable IRQ 4 (IRQ 3)
   628 000002FF E621                    	out	21h, al    		; write back to register
   629                                  	;
   630 00000301 C3                      	retn
   631                                  
   632                                  StartMsg:
   633 00000302 0D0A                                    db 0Dh,0Ah
   634 00000304 5465726D696E616C20-                     db 'Terminal program for Retro UNIX 386 v1... (10/11/2015)'
   635 0000030D 70726F6772616D2066-
   636 00000316 6F7220526574726F20-
   637 0000031F 554E49582033383620-
   638 00000328 76312E2E2E20283130-
   639 00000331 2F31312F3230313529 
   640 0000033A 0D0A                    		db 0Dh, 0Ah
   641 0000033C 28274374726C2B4272-                     db "('Ctrl+Break' must be used to exit!)"
   642 00000345 65616B27206D757374-
   643 0000034E 206265207573656420-
   644 00000357 746F20657869742129 
   645 00000360 0D0A                                    db 0Dh, 0Ah
   646 00000362 0D0A                    		db 0Dh, 0Ah
   647 00000364 507265737320312066-     		db 'Press 1 for COM 1 or press 2 for COM2 serial port...' 
   648 0000036D 6F7220434F4D203120-
   649 00000376 6F7220707265737320-
   650 0000037F 3220666F7220434F4D-
   651 00000388 322073657269616C20-
   652 00000391 706F72742E2E2E     
   653 00000398 0D0A                    		db 0Dh, 0Ah
   654 0000039A 0D0A00                  		db 0Dh,0Ah,0h
   655                                  ComSMsg:
   656 0000039D 07                      		db 07h
   657 0000039E 434F4D312073656C65-     		db 'COM1 selected...'
   658 000003A7 637465642E2E2E     
   659 000003AE 0D0A00                  		db  0Dh, 0Ah, 0
   660                                  AnyKeyMsg:
   661 000003B1 50726573732061206B-                     db "Press a key to continue. (Press 'ESC' key to cancel.)"
   662 000003BA 657920746F20636F6E-
   663 000003C3 74696E75652E202850-
   664 000003CC 726573732027455343-
   665 000003D5 27206B657920746F20-
   666 000003DE 63616E63656C2E29   
   667 000003E6 0D0A00                                  db 0Dh,0Ah,0h
   668                                  ErrMsg:
   669 000003E9 0D0A                    		db 0Dh, 0Ah
   670 000003EB 0D0A                    		db 0Dh, 0Ah
   671 000003ED 53657269616C20506F-     		db 'Serial Port (115200 baud) Error !'
   672 000003F6 727420283131353230-
   673 000003FF 302062617564292045-
   674 00000408 72726F722021       
   675 0000040E 0D0A00                  		db 0Dh, 0Ah, 0
   676 00000411 90                      align 2
   677                                  
   678 00000412 EF00                    _EFh:		dw 0EFh
   679                                  ;
   680 00000414 F803                    _3F8h:		dw 3F8h
   681 00000416 F903                    _3F9h:		dw 3F9h
   682                                  ;_3FAh:		dw 3FAh
   683                                  ;_3FBh:		dw 3FBh
   684 00000418 FC03                    _3FCh:		dw 3FCh
   685 0000041A FD03                    _3FDh:		dw 3FDh	
   686                                  ;_3FEh:		dw 3FEh	
   687                                  ;
   688                                  
   689                                  ; 10/11/2015
   690 0000041C [3205]                  rb_off:		dw rbuffer  ; Write buffer offset
   691 0000041E [3204]                  wb_off:		dw wbuffer  ; Read buffer offset
   692                                  
   693                                  ;; align 2
   694                                  
   695                                  ; 10/11/2015 (bss)
   696                                  bss_start:
   697                                  
   698                                  ABSOLUTE bss_start
   699                                  
   700 00000420 <res 00000001>          port:		resb 1
   701 00000421 <res 00000001>          cbrk:		resb 1
   702                                  
   703 00000422 <res 00000004>          old_ctrlbrk:	resd 1
   704 00000426 <res 00000004>          old_timer:	resd 1 ; 06/11/2015
   705 0000042A <res 00000004>          old_serial:	resd 1
   706                                  
   707                                  ; 06/11/2015
   708 0000042E <res 00000001>          schar:		resb 1
   709 0000042F <res 00000001>          rchar:		resb 1
   710 00000430 <res 00000002>          ticks:		resw 1
   711                                  
   712 00000432 <res 00000100>          wbuffer:	resb 256 ; Print (with INT 10h) routine will use this one
   713                                  
   714 00000532 <res 00000100>          rbuffer:	resb 256 ; Interrupt handler will use this one
   715                                  
   716 00000632 <res 00000001>          error:		resb 1
   717 00000633 <res 00000001>          		resb 1
   718                                  
   719                                  bss_end:
