8088 Programming

 info@homebrew8088.com 
                    Home    8088 Programming    80x86 Assembly    8088 opcodes    Arduino    Troubleshoot 


Introduction:

    The programming information here is geared towards my 8088 sbc. The I/O port addresses and memory map may be different on your 8088 depending on how you built it. You should be able to modify my code to match your needs.

   To program your 8088 your going to need a rom burner and a good 8088 Assembler. My choice assembler is Netwide Assembler (NASM).



8255A:

    To communicate with the 8255 it is simple, you just set the operating mode in the control register. Then you can communicate in or out with Port A, B, or C. The three ports are divided into two groups when setting port modes. Group A is Port A and the upper 4 bits of Port C. Group B is Port B and the lower 4 bits of Port C. When setting the mode Group B has two options and Group A has three options. Mode 0 is basic Input/Output , Mode 1 Strobed Input/Output, Mode 2 Strobed Bidirectional Bus I/O.

    I usually use mode 0.
  
    Basic operating modes. Write this value to the control port/register.
 D7 D6 D5 D4 D3 D2 D1 D0
Group B
D0 = Port C Lower, 1 = Input \ 0 = Output
D1 = Port B, 1 = Input \ 0 = Output
D2 = Mode Selection, 0 = Mode 0 \ 1 = Mode 1

Group A
D3 = Port C Upper, 1 = Input \ 0 = Output
D4 = Port A, 1 = Input \ 0 = Output
D5/D6 = Mode Selection, 00 = Mode 0 \ 01 = Mode 1 \ 1X = Mode 2

D7 = Mode Set Flag, 1 = Active
   
    Basic 8255 operation.       
 A1A0 RD WR CS Input Operation (Read)
 0 0 1 0 Port A --> Data Bus
 0 101 0 Port B --> Data Bus
 1 0 0 1 0 Port C --> Data Bus
      Output Operation (Write)
 0 0 1 0 0 Data Bus --> Port A
 0 1 1 0 0 Data Bus --> Port B
 10 1 0 0 Data Bus --> Port C
 11100 Data Bus --> Control

    Code:

        MOV AL, 0x80            ;Set AL 10000000 = Port active \ A,B,C Outputs and mode 0.
        OUT 0x1F,  AL            ;Store the value in the Control Port

    or

        MOV AL, 0x9B            ;Set AL 10011011 = Port active \ A,B,C Inputs and mode 0.
        OUT 0x1F,  AL            ;Store the value in the Control Port


8259A - PROGRAMMABLE INTERRUPT CONTROLLER:

    The programmable interrupt controller has two writable port addresses that are used during the setup of the 8259A. Address line A0 selects which port you are writing to. To set up the controller you send Initialization Command Words to the 
8259A to determine how you want the controller to function. 

    Initialization Command Word 1
 A0 D7 D6 D5 D4 D3 D2 D1 D0
 0 A7 A6 A5 1 LTIM ADI SNGL ICW4

ICW41 = ICW4 NEEDED 
0 = NO ICW4 NEEDED
SNGL1 = SINGLE 
0 = CASCADE MODE
ADICALL ADDRESS INTERVAL
1 = INTERVAL OF 4
0 = INTERVAL OF 8
LTIM1 = LEVEL TRIGGERED MODE
0 = EDGE TRIGGERED MODE
A7 - A5NOT USED 8085 ONLY
A7 - A5 OF INTERRUPT VECTOR ADDRESS

    Initialization Command Word 2
 A0 D7 D6 D5 D4 D3 D2 D1 D0
 1 T7T6 T5  T4T3   

T7 - T3T7 - T3 OF INTERRUPT ADDRESS 

    Initialization Command Word 3 (Only require if you are in cascade mode)
 A0D7D6D5D4D3D2D1D0
1S7 S6  S5 S4 S3 S2 S1S0

S7 - S01 IR INPUT HAS SLAVE
0 IR INPUT DOES NOT HAVE SLAVE

    Initialization Command Word 4 (Required if ICW1 - D0 = 1)
A0D7D6D5D4D3D2D1D0
100 0SFNMBUFM/SAEOI PM

SFNM1 = SPECIAL FULLY NESTED MODE
0 = NOT 
SPECIAL FULLY NESTED MODE
BUFM/S 
 0
 1
 1

 
NON BUFFERED MODE 
BUFFERED MODE/SLAVE
BUFFERED MOVE/MASTER
AEOI1 = AUTO END OF INTERRUPT
0 = NORMAL END OF INTERRUPT
PM1 = 8086/8088 MODE
0 = 8085 MODE

    Code:
    
    This code example is with the base address of the 8259A at port 04

    ICW1: (Single 8259A, ICW4 required)
        MOV AL, 13 
        OUT 04, AL  

    ICW2: (Starting interrupt # 0x08)
        MOV AL, 08   ICW2
        OUT 05, AL        
  
    ICW3: (Not needed because there are no slave 8259A)
  
    ICW4: (Auto end of interrupt, 8088 mode)
        MOV AL, 03   ICW4
        OUT 05, AL  

    Note:

        If you don't auto end your interrupts you have to send an end of interrupt command to the 8259A using an Operation Control Word. This is done at the end of your interrupt sub routine.

    Operation Control Word 2 
A0D7D6D5D4D3D2D1D0
0RSL EOI00L2L1L0

    OCW2:
        MOV AL, 20 
        OUT 04, AL  



LCD:

    For my project I connected the LCD screen to Port B and the lower part of Port C of the 8255. What this does is control the Read/Write, Enable, And register select pins of the LCD with Port C and the data your sending with Port B. To make it simple you talk to the LCD through the 8255.
    
    Code:

    First thing make sure that the 8255 is set to all outputs and active.

        MOV AL, 0x80            ;Set AL 10000000 = Port active \ A,B,C Outputs and mode 0.
        OUT 0x1F,  AL            ;Store the value in the Control Port

    Then basic operations.

        MOV AL, 00000001b    ;Disable the EN pin. Effective disabling any read write functions of the LCD.
        OUT 0x1E, AL 

        MOV AL, 00000000b    ;Enable the EN pin, Write to the Command Register.
        OUT 0x1E, AL 

        MOV AL, 00000100b    ;Enable the EN pin, Write to the Data Register.
        OUT 0x1E, AL         

        MOV AL, Byte               ;Puts data on PORT B that is connected to D0 - D7.
        OUT 0x1D, AL   

    To set and turn on the LCD you need to send a set of control words to the Command register. 

        0x38  = Set 8 bit mode, 2 lines, 5x7 dots.
        0x06 = Entry mode.
        0x0F = Display on cursor blinking.
        0x01 = Clear screen.

    To write a character to the screen (after you set it up). Write the Hexadecimal value to the Data register.        

    I like to put the screen commands in an an Interrupt so that it is easy to interface. I picked Interrupt 0x10 because it is the normal interrupt for screen control. If you copy and paste this code into your bios it should work. Of course you need to make and entry on the interrupt vector table that points to the location of the code.
ISR10: 
    CMP AH, 0x00                ;Check the AH to determine what function is being called.
    JZ 0x0A                     ;Jump if 0x00
    CMP AH, 0x0E,               ;
    JZ 0x53,                    ;Jump if 0x0E   
    CMP AH, 0xC1,               ;   
    JZ 0x68,                    ;Jump if 0xC1

                                ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
                           ;Set Video MODE AH=00  (turn the screen on)   
                            ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

    MOV AL, 0x01
    OUT 0x1E, AL               ;Set LCD controls to write mode and control port.
    
    MOV CX, 0x00FF             ;LOOP HOLD FOR A BIT'
    LOOP 0xFE
    
    MOV AL, 0x38
    OUT 0x1D, AL 
                   
    MOV AL, 0x00              
    OUT 0x1E, AL              ;Enable LCD Write
    MOV CX, 0x00FF             ;LOOP HOLD FOR A BIT'
    LOOP 0xFE
    MOV AL, 0x01
    OUT 0x1E, AL               ;Disable LCD Write
    
    MOV AL, 0x06
    OUT 0x1D, AL  
                   
    MOV AL, 0x00              
    OUT 0x1E, AL             ;Enable LCD Write
    MOV CX, 0x00FF             ;LOOP HOLD FOR A BIT'
    LOOP 0xFE
    MOV AL, 0x01
    OUT 0x1E, AL              ;Disable LCD Write

    MOV AL, 0x0F
    OUT 0x1D, AL   
                  
    MOV AL, 0x00              
    OUT 0x1E, AL             ;Enable LCD Write
    MOV CX, 0x00FF         ;LOOP HOLD FOR A BIT'
    LOOP 0xFE
    MOV AL, 0x01
    OUT 0x1E, AL               ;Disable LCD Write
    
    MOV AL, 0x01               ; 01 Clears the screen
    OUT 0x1D, AL                     
    MOV AL, 0x00              
    OUT 0x1E, AL              ;Enable LCD Write
    MOV CX, 0x00FF             ;LOOP HOLD FOR A BIT'
    LOOP 0xFE
    MOV AL, 0x01
    OUT 0x1E, AL               ;Disable LCD Write
    
    IRET    
    
                                ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
                                ;Teletype output AH=0E, AL="Letter"                                  
                                ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; 
    MOV AH, AL               ;Store the Letter

    MOV AL, 0x05
    OUT 0x1E, AL             ;Set LCD controls to write mode and data port.       

    MOV AL, AH                ;Get the  Letter
    OUT 0x1D, AL             ;Put the letter on the data port

    MOV AL, 0x04
    OUT 0x1E, AL             ;Enable Write    
    MOV CX, 0x0020
    LOOP 0xFE,         ;LOOP HOLD FOR A BIT'
    MOV AL, 0x05
    OUT 0x1E, AL             ;Disable Write
    MOV AH, 0x0E               ;(For Repeat Typing)
    IRET
    
                                ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; 
                                ;CLEAR AH=C1   
                                ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;                                    
    MOV AL, 0x01
    OUT 0x1E, AL             ;Set LCD controls to write mode and control port.

    MOV AL, 0x01             ; 01 Clears the screen
    OUT 0x1D, AL             ;Put 01 on the data port  
    MOV AL, 0x00              
    OUT 0x1E, AL             ;Enable LCD Write
    MOV CX, 0x0FFF           ;LOOP HOLD FOR A BIT'
    LOOP 0xFE
    MOV AL, 0x01
    OUT 0x1E, AL             ;Disable LCD Write
    IRET