[comp.os.msdos.programmer] communication port programming on 386

envbvs@epb7.lbl.gov (Brian V. Smith) (01/25/91)

I have some in-line assembly code that I have used with Turbo Pascal
3.0, 4.0 and 5.0 to initialize the communication ports and do I/O with
them.  This has worked fine on an 8086 and an 80286 (AT).  However, I can't
get it to work at all with an 80386.  I have tried it on two different
machines (a laptop by by DATAworld and a generic 386 desktop model).

Here is the code I have been using for several years now.  The put() proc
seems to timeout as does the get() procedure.

Can anyone help me?   Are there differences in the communications ports
from the 286 to the 386?
Thanks for any help.


{----------------------------------------------------------------------------}

{  get : Get one character from 'port' into 'chr'                            }

procedure get(port :integer; var chr : char);
begin
  inline (
    $C4/$BE/chr/      {       les   di,chr[bp]  ; get ptr to the char        }
    $B4/$02/          {       mov   ah,2        ; get char                   }
    $8B/$96/port/     {       mov   dx,port[bp] ; port                       }
    $CD/$14/          {       int   14h         ; call int                   }
    $26/$88/$05       {       mov    es:[di],al ; store char                 }
  )
end; { get }

{----------------------------------------------------------------------------}

{  put : Print 'chr' to 'port'                                               }

procedure put(port :integer; chr : char);

begin
  inline (
    $8A/$96/chr/      {       mov   dl,chr      ; get char to print          }
    $8A/$C2/          {       mov   al,dl       ; put char in al             }
    $B4/$01/          {       mov   ah,1        ; print char                 }
    $8B/$96/port/     {       mov   dx,port[bp] ; port                       }
    $CD/$14           {       int   14h         ; call int                   }
  )
end; { put }

{----------------------------------------------------------------------------}

procedure clearaux(port : integer);
begin
  inline (
    $B4/$03/    {loop:  mov   ah,3      ; status check                       }
    $8B/$96/port/{      mov   dx,port[bp]    ; port                          }
    $CD/$14/    {       int   14h       ; call aux status                    }
    $80/$e4/$01/{       and   ah,1      ; check for data ready               }
    $74/$0A/    {       jz    exit      ; no chars, return                   }
    $B4/$02/    {       mov   ah,2      ; get char                           }
    $8B/$96/port/{      mov   dx,port[bp]    ; port                          }
    $CD/$14/    {       int   14h       ; get the char                       }
    $EB/$E9/    {       jmp   loop      ; check if another                   }
    $90         {exit:  nop             ; that's all                         }
  )
end; { clearaux }


{----------------------------------------------------------------------------}

procedure init9600(port :integer);
begin
  inline (
    $B4/$00/     { mov   ah,0      ; function 0                              }
    $B0/$E2/     { mov   al,0E2h   ; 9600 baud, no parity, 1 stop bit, 7 data}
    $8B/$96/port/{ mov   dx,port[bp]    ; port                               }
    $CD/$14      { int   14h       ; call int                                }
  );
  clearaux(port);
end; { init9600 }

-- 
Brian V. Smith    (bvsmith@lbl.gov)
Lawrence Berkeley Laboratory
I don't speak for LBL; they don't pay me enough for that.