PDA

Просмотр полной версии : бегущая строка под Dos



fron
04.06.2007, 11:45
помогите плз с задачкой:
Составить программу для ввода с клавиатуры строки символов. Записать строку в буфер buf и организовать вывод бегущей строки.
Прога должна работать под управлением MS DOS.
Инструментальная среда TASM 5.10 (MASM 6.11).

спс.

somewhere
04.06.2007, 14:26
.model small
.386
.stack
.code
jmp @start

buf db 255, 0, 255 dup (0)
s_inputstring db 'Input string : $'
s_keypress db 0Dh, 0Ah, 'Press any key to exit$'
log_position dw 0
max_position dw 0
out_position dw 12

; ===================== Waiting timer
WaitTimer proc near
push es
push ax
xor ax, ax
mov es, ax
mov ax, es:[46Ch]
@waiting:
cmp ax, es:[46Ch]
jz @waiting
pop ax
pop es
ret
WaitTimer endp

; ===================== Running string output
OutRunString proc near
pusha
push es
cld
mov ax, 0B800h
mov es, ax
mov ax, Out_Position
imul ax, ax, 160 ; Calculating offset
mov di, ax
mov si, ax
mov cx, 80
mov ax, 03420h
rep stosw ; Filling whole line by spaces
mov cx, 80 ; Characters to end of line
mov di, si
mov si, offset Buf + 2 ; First char of string
movzx bp, [si-1]
add bp, si ; Last char of string + 1
mov ax, Log_Position
cmp ax, cx
jnc @no_offset ; If position >= 80 then no need to offset string

sub cx, ax
add di, cx
add di, cx
mov cx, ax ; Calc offset and length
jmp short @outstr
@no_offset:
sub ax, cx
add si, ax ; Calc first output character
@outstr:
jcxz @outend
mov ah, 034h
mov al, [si]
stosw ; Out character
inc si
cmp si, bp ; If end of line or end of string then exit
jz @outend
dec cx
jmp short @outstr
@outend:
pop es
popa
retn
OutRunString endp

; ========================= MAIN CODE ================================
@start:
push cs
pop ds
mov ax, 3 ; Videomode 80x25
int 10h
mov dx, offset s_inputstring
mov ah, 9
int 21h
mov ah, 0Ah
mov dx, offset buf
int 21h ; Buffered input
mov dx, offset s_keypress
mov ah, 9
int 21h
movzx ax, byte ptr buf + 1
add ax, 80
mov Max_Position, ax
@work:
call WaitTimer ; Waiting 1/18 sec.
inc Log_Position
mov ax, Log_Position
cmp ax, Max_Position ; If LogPos > MaxPos then LogPos = 0
jnz @skip
mov Log_Position, 0
@skip:
call OutRunString ; Out running string
mov ah, 0Bh
int 21h
or al, al ; If not key pressed, then continue
jz @work

mov ah, 0Ch
int 21h ; Flush key buffer

mov ax, 4C00h
int 21h

end

Это один из способов. Алгоритм использует больше вычислительных операций, зато не использует дополнительной памяти.

fron
04.06.2007, 15:45
Огромное спасибо! Очень выручил :)

ток возникает при линке ошибка:
Fatal: No program entry point
((
Не подскажешь почему?

somewhere
04.06.2007, 15:50
Это зависит от компилятора, по идее Entry Point в этой программе по умолчанию 0000:0000 - но более старшие версии могут поругаться, что она не задана - в любом случае фатальной ошибки быть не должно

BBB
04.06.2007, 17:31
Может, делу поможет замена самого последнего end на:
end @start
или
end start

Я в своих программках именно так писал. Правла, у меня метки отчего-то всегда были без "собачек" первым символом, т.примерно так:


.model tiny
.code

ORG 100h

start:

;; Do something here ...

end start

fron
05.06.2007, 03:14
Еще раз огромное спасибо!!))
Помогло) просто в конце исправил на end @start
Очень вам признателен.

BBB
05.06.2007, 10:07
Еще раз огромное спасибо!!))
Помогло) просто в конце исправил на end @start
Очень вам признателен.Посмотел чуть повнимательнее на свои тексты и на текст, выложенный somewhere. У него первым оператором (после строки .code)стоит jmp @start.
У меня всегда структура исх.текста была следующая:

.model tiny
.code

ORG 100h

start:
jmp begin

;; Здесь размещались различные процедуры и данные

begin:
;; Здесь начиналась собственно программа

end start

То есть, я хоче сказать, что не знаю (не помню), корректно ли указывать начальную точку программы (т.е. то, что пишется в последнем end) "посредине" исходного текста. Возможно, лучше указывать "самую верхнюю" точку. Т.е. начало кода somewhere изменить на:

.model small
.386
.stack
.code
@start_point:
jmp @start

А последней строкой тогда будет:

end @start_point

somewhere
05.06.2007, 10:27
Правла, у меня метки отчего-то всегда были без "собачек" первым символом
Это просто я так метки обозначаю, всегда начиная с "собачки"
По сути, ошибок нет, т.к. стоит директива .CODE - которая и обозначает Entry Point
Не знаю как там в MASM, но в TASM нет никаких вопросов
Вот типичный пример из книжки по TASM


.MODEL SMALL
.STACK 100h
.DATA
Message DB 'Привет!',13,10,'$'
.CODE
mov ax,@Data
mov dx,ax ; установить регистр DS таким
; образом, чтобы он указывал
; на сегмент данных
mov ah,9 ; функция DOS вывода строки
mov dx,OFFSET Message ; ссылка на сообщение "Привет!"
int 21h ; вывести "Привет!" на экран
mov ah,4ch ; функция DOS завершения
; программы
int 21h ; завершить программу
END


P.S. - оказывается даже здесь ошибки бывают, для тех кто не заметил - в самом начале