Assembler czytanie z znaków

0

Mam zadanie: Wczytać jeden znak i go wyświetlić. Skorzystać z 10h i 16h.

Pobieram znak za pomocą 16h ale nie mogę go wyśwetlić. Znaczy nie wiem jak ;)

Pomyślałem, że ustawie AH na 09h czyli wyświetlanie napisów a DL na AL czyli tam gdzie z 16h wchodzi znak. Jednak wypisują się losowe głupoty.
Ktoś może pomóc? Czego szukać?

org 100h

	mov ah, 09h
	mov dx, FirstMsg
	int 21h
	
	mov dx, SecondMsg
	int 21h
	
	xor ax, ax
	int 16h
	
	mov ah, 09h
	mov dx, ThridMsg
	int 21h
	
	;mov ah, 09h
	mov dx, ax
	int 21h

mov ax, 4c00h
int 21h

FirstMsg db "Welcome", 10, "$"
SecondMsg db "Press key: ", "$"
ThridMsg db 10, "Pressed key: ", "$" 
1

Znak, który wczytujesz z klawiatury jest w AL, a rozkaz wyświetla go z DL. Musisz więc go przenieść z AL do DL

org 0x100
	mov ah, 0x09
	mov dx, komunikat
	int 0x21
	
	mov ah, 0x01
	int 0x21
	
	mov ah, 0x09
	mov dx, wynik
	int 0x21

	mov dl, al
	
	mov ah, 0x06
	int 0x21
	
	mov ah,0x4c
	int 21h
	
	komunikat db "Podaj znak: $"
	wynik db " Wynik: $"

Tutaj masz ładnie opisane dosowe przerwania: http://spike.scu.edu.au/~barry/interrupts.html

1

Bo robisz teraz jakieś glupoty. Pod dx ustawiłeś wartość ax tylko że int 21h przy ah=09h powoduje wypisanie ciągu znaków spod danego ADRESU aż do napotkania dolara. ADRESU! Więc twój program traktuje wczytany do al znak jako liczbę określającą offset pod którym szuka danych.
Albo wpiszesz gdzieś do pamięci tą wartość z al, zakończysz dolarem i potem wywołasz przerwanie z adresem pod którym to zapisałeś, albo wypisuj tylko ten jeden znak za pomocą int 21h przy ah=02h, gdzie znak do wypisania jest w dl

0

Dzięki za odpowiedzi. Mieliśmy nie używać 21h.

Teraz działa:

 org 100h

	mov ah, 09h
	mov dx, firstMsg
	int 21h
	
	mov dx, secondMsg
	int 21h
	
	xor ax, ax
	int 16h
	
	mov ah, 09h
	mov dx, thirdMsg
	int 21h
	
	mov ah, 0Eh
	mov dl, al
	int 10h

mov ax, 4c00h
int 21h

firstMsg db "Welcome to ", 22h, "program", 22h, ".", 0ah, "$"
secondMsg db "Press key: $"
thirdMsg db 0ah, "Pressed key: $"
1

Tak też działa i jest przejrzyściej bo nie do końca wiem co robi teletype output z int 10h.

	mov ah, 09h
	mov dx, firstMsg
	int 21h
	
	mov dx, secondMsg
	int 21h
	
	mov ah, 01h
	int 21h
	
	mov ah, 09h
	mov dx, thirdMsg
	int 21h
	
	mov ah, 02h
	mov dl, al
	int 21h
0

Przerwania 16h nie obsługują echa. Możesz zrobić pseudo-echo tak:

org 0x100
	mov ah, 0x09
	mov dx, komunikat
	int 0x21
	
	mov ah, 0x00
	int 0x16
	
	mov dl, al
	
	mov ah, 0x06
	int 0x21	
	
	mov ah, 0x09
	mov dx, wynik
	int 0x21	
	
	mov dl, al
	
	mov ah, 0x06
	int 0x21
	
	mov ah,0x4c
	int 21h
	
	komunikat db "Podaj znak: $"
	wynik db " Wynik: $"
0

nie do końca wiem co robi teletype output z int 10h

Wyświetla znak.
Niezrozumiałe może być znaczenie BH. Powinna tam być aktualna "strona" ekranu (ekran może mieć kilka stron między którymi można szybko się przełączać).
Aktywną stronę można pobrać odpowiednią funkcją, nawet od razu w rejestrze BH ją dostaniesz.

1 użytkowników online, w tym zalogowanych: 0, gości: 1