Last Updated or created 2023-01-08
This year i’ve been really into assembly on Intel x86 machines.
With EDK we made some demo’s and generally trying to find the limits of the machines we had.
Funny story, edk made a program which changed the palette every scanline (if memory serves me right), while running the program and looking at the screen the colors faded to grayscale. (Something with run-away tables) We look at eachother and said: We must have been using up all colors, we need to refill the graphics card.
I previously made a copperbar alike thingy on a hercules system. (Have not seen them before on a pc back then )
But with below program, i could display pictures which removed the borders.
Below a nsfw video example (pass protected), but a simplified example in pictures below that.


Test image i’ve used on a 320×200 screen resolution
name split_screen
.286
parm_vert equ 0
data segment
intmsk db ?
oldvidtab db 18h dup (?) ;actuele video-parameters
newvidtab label byte
;HORIZONTAAL
db 0
db 12
db 12
db 0
;VERTIKAAL
db 0
db 5
db 5
db 0;-40
;
db 0
db 0
db 0
db 0
db 0
db 0
db 0
db 0
db 0
db 0
db 0
; REGISTER 13H (OFFSET)
db 0
;
db 18h dup (0)
data ends
stack segment stack
dw 128 dup (?)
stack ends
code segment
assume cs:code,ds:data
cols label byte
set_scrparms:
mov dx,3d4h
mov al,11h
out dx,al
inc dx
in al,dx
and al,7fh ;clear bit 7: enable writes to vga reg 0..7
out dx,al
dec dx
mov al,13h ;offset register
out dx,al
inc dx
in al,dx ;get actual value
add al,4
out dx,al
ret
;
; RE-INIT DISPLAY ROUTINE
;
get_oldvidparms:
mov dx,3d4h
mov cx,18h ;18h registers
mov di,offset oldvidtab
mov bl,0 ;begin met register 0
govp1:
mov al,bl ;register index
out dx,al
inc dx ;3d5
in al,dx ;get actual register content
dec dx
mov [di],al
inc di
inc bl ;volgend register
loop govp1
mov si,offset oldvidtab
mov di,offset newvidtab
mov cx,18h
donewparms:
mov al,[si]
add al,[di]
mov [di],al
inc si
inc di
loop donewparms
ret
set_newvidparms:
mov dx,3d4h
mov cx,18h ;18h registers
mov si,offset newvidtab
mov bl,0 ;begin met register 0
snvp1:
mov al,bl ;register index
out dx,al
inc dx ;3d5
mov al,[si]
inc si
out dx,al ;set register value
dec dx
inc bl ;volgend register
loop snvp1
ret
;
; MAIN ENTRY POINT
;
init:
mov ax,data
mov ds,ax
in al,21h
mov intmsk,al
cli
mov al,11111101b
out 21h,al
sti
mov ax,13h
int 10h
;extend video-memory to 256kb or more
mov dx,3ceh
mov al,06h
out dx,al
inc dx
in al,dx
and al,0f3h
out dx,al
;
mov ax,0a000h
mov es,ax
call set_scrparms
call get_oldvidparms
call set_newvidparms
mov dx,3cch
in al,dx
and al,03fh
mov ah,parm_vert
ror ah,2
or al,ah
mov dx,3c2h
out dx,al
;
;
push ds
mov ax,5000h
mov ds,ax
;
; pallet
;
setpal:
mov dx,3c8h
xor al,al
out dx,al
inc dx
mov cx,256*3
mov si,100h
cld
rep outsb
;disp picture routine
mov ax,6000h
mov ds,ax
mov si,0
mov di,0
mov ax,0
mov cx,352*8
cld
rep stosw
mov si,di
mov cx,8
cld
rep stosw
mov bp,170
mov si,di
hiero:
mov cx,320
cld
rep movsb
mov ax,0
mov cx,16
cld
rep stosw
mov si,di
dec bp
jnz hiero
xor si,si
xor di,di
mov ax,0b000h
mov es,ax
mov ax,07000h
mov ds,ax
mov cx,3000
cld
mov ax,0
rep stosw
mov ax,0a000h
mov es,ax
mov ax,6000h
mov ds,ax
mov di,0
mov si,di
rhiero:
push ax
mov ah,8
int 21h
pop ax
std
mov cx,-1
rep movsb
xor si,si
xor di,di
mov ax,0b000h
mov es,ax
mov ax,07000h
mov ds,ax
mov cx,3000
cld
rep movsw
mov ax,0a000h
mov es,ax
pop ds
;
mloop:
mov dx,3dah
wtv1:
in al,dx
test al,8
jnz wtv1
wtv2:
in al,dx
test al,8
jz wtv2
mov ah,1
int 16h
jz mloop
xor ah,ah
int 16h
exit:
mov ax,3
int 10h
cli
mov al,intmsk
out 21h,al
sti
mov ax,4c00h
int 21h
code ends
end init
