PDA

View Full Version : [Assembler] Convertitore Binario-Decimale


Lupino.86
19-10-2005, 19:00
Save a tutti,
potete aiutarmi a scrivere un convertitore Binario-Decimale usando il linguaggio Assembler?
Conosco il linguaggio, ma mi pare che sia una bella gatta da pelare.....voi che dite?



Vi ringrazio anticipatamente,
Lupino.86

cionci
19-10-2005, 19:06
Cioè prendi un input binario da tastiera (solo 0 e 1 da tastiera) ?

Lupino.86
19-10-2005, 19:17
Cioè prendi un input binario da tastiera (solo 0 e 1 da tastiera) ?

No..... devo acquisire da tastiera un numero decimale, convertirlo in binario.

Successivamente devo anche scrivere un programma per moltiplicare due numeri decimali utilizzando però i numeri binari:
1) acquisisto il moltiplicando decimale
2) acquisisto il moltiplicatore decimale
3) converto moltiplicando e moltiplicatore in binario
4) eseguo la moltiplicazione utlizzando le cifre binarie e non decimali :doh:
5) il risultato binario lo converto in decimale :muro:


Per ora mi basta sapere la sola conversione :D

Goldrake_xyz
19-10-2005, 20:39
beh, acquisire da tastiera con l'assembler mi sembra un proggetto
piuttosto impegnativo, a meno che non hai delle routine già pronte.
se riesci a salvare la cifra decimale in memoria in BCD ad esempio,
poi è facile da convertire in binario puro.
la conversione devi farla in binario complemento 2 ?
una volta convertiti usa la famosa istruzione IMUL xyz :D
se invece sono numeri reali, con la virgola, la questione si complica
xchè c'è bisogno di convertirli in esponente e mantissa normalizzati
e poi darli in pasto al coprocessore numerico ... :sofico:

ciao :D

P.S. x la conversione di numeri interi da dec. a binario usando l'asm
è abbastanza semplice. come anche il vice-versa ;)

Goldrake_xyz
19-10-2005, 20:43
Acc dovrei averlo scritto un programmino del genere, (tanti anni fà :cry: )
se lo ritrovo, lo allego :)

Lupino.86
19-10-2005, 23:19
beh, acquisire da tastiera con l'assembler mi sembra un proggetto
piuttosto impegnativo, a meno che non hai delle routine già pronte.

Cosa intendi per routine???


se riesci a salvare la cifra decimale in memoria in BCD ad esempio,
poi è facile da convertire in binario puro.
So salvare in memoria la cifra decimale tramite la divisione per 10..... ma nn so convertire da decimale a binario!

la conversione devi farla in binario complemento 2 ?
prchè esiste qualche altra conversione binaria? :rolleyes:


una volta convertiti usa la famosa istruzione IMUL xyz :D
se invece sono numeri reali, con la virgola, la questione si complica
xchè c'è bisogno di convertirli in esponente e mantissa normalizzati
e poi darli in pasto al coprocessore numerico ... :sofico:

Nonononono, sono numeri senza virgola.
L'istruzione IMUL mi da sempre errore.... cosa sbaglio?
per esempio: IMUL bl,bx ; moltiplico il registro Bl con il registro BX, il risultavo va a finire in BL.... tutto OK?



P.S. x la conversione di numeri interi da dec. a binario usando l'asm
è abbastanza semplice. come anche il vice-versa ;)

Se è semplice MI PUOI DIRE COME SI Fà ??? :help:

Lupino.86
19-10-2005, 23:22
Acc dovrei averlo scritto un programmino del genere, (tanti anni fà :cry: )
se lo ritrovo, lo allego :)

Spero con ansia che hai tuttora quel programmino :help:

71104
19-10-2005, 23:32
Cosa intendi per routine??? funzioni, procedure, sottoprogrammi, sub; al limite vanno bene anche le macro :D
cmq acquisire da tastiera diventa semplicissimo se il file che devi generare è un binario puro (estensione .com): in tal caso basta usare il bios emulato da Windows.

cionci
20-10-2005, 00:09
per esempio: IMUL bl,bx ; moltiplico il registro Bl con il registro BX, il risultavo va a finire in BL.... tutto OK?
Non puoi usare bh e bx come operatori... bl fa parte di bx...

cj++
20-10-2005, 05:31
scrivilo in C poi usa il codice ottimizzato generato dal compilatore :D

repne scasb
20-10-2005, 10:51
Non hai specificato il sistema operativo, ne la modalita' del processore; ho scelto io DOS/WIN_VM modalita' reale:


ENTER_KEY1 EQU 1C0Dh
ENTER_KEY2 EQU 0E00Dh
BACKSPACE_KEY EQU 0E08h

data segment byte 'DATA'

dos_message_1:
DB 'Moltiplicazioni in ASM',0Dh,0Ah,'$'
dos_message_2:
DB 0Dh,0Ah,'Inserire 1° operando: $'
dos_message_3:
DB 0Dh,0Ah,'Inserire 2° operando: $'
dos_message_4:
DB 0Dh,0Ah,0Dh,0Ah,'Risultato: $'

_1st_val_str:
DB 0Ah DUP (?)
_2nd_val_str:
DB 0Ah DUP (?)
_1st_val_bin:
DD ?
_2nd_val_bin:
DD ?

data ends

.386P
.ALPHA

code segment para use16 'CODE'
assume cs:code

Init proc near

push DATA
pop ds
mov dx,OFFSET dos_message_1
call Write_Message
mov dx,OFFSET dos_message_2
call Write_Message
mov si,OFFSET _1st_val_str
call Get_Input
mov di,OFFSET _1st_val_bin
call Str_Dec_To_Bin
mov dx,OFFSET dos_message_3
call Write_Message
mov si,OFFSET _2nd_val_str
call Get_Input
mov di,OFFSET _2nd_val_bin
call Str_Dec_To_Bin
mov dx,OFFSET dos_message_4
call Write_Message
mov eax,ds: dword ptr [_2nd_val_bin]
mul ds: dword ptr [_1st_val_bin]
call Write_Dec_Num64
mov ax,4C00h
int 21h

init endp

;#############################################################################

Get_Input proc near

pusha
xor bx,bx
loop_get_key:
call Get_Key
cmp bx,9h
je test_alt_key
cmp ah,2h
jb test_num_alt
cmp ah,0Bh
ja test_num_alt
test_num_low:
cmp al,'0'
jb test_num_alt
cmp al,'9'
ja test_num_alt
call Write_Char
mov ds: byte ptr [bx+si],al
inc bx
jmp loop_get_key
test_num_alt:
cmp ah,47h
jb test_alt_key
cmp ah,52h
jbe test_num_low
test_alt_key:
cmp ax,BACKSPACE_KEY
jne test_exit
or bx,bx
je loop_get_key
call Get_Cursor_Position
dec dl
call Set_Cursor_Position
dec bx
mov al,' '
call Write_Char
call Set_Cursor_Position
jmp loop_get_key
test_exit:
cmp ax,ENTER_KEY1
je exit_get_input
cmp ax,ENTER_KEY2
jne loop_get_key
exit_get_input:
mov ds: byte ptr [bx+si],0h
popa
ret

Get_Input endp

;#############################################################################

Get_Key proc near

pusha
mov ah,10h
int 16h
mov bp,sp
mov ss: word ptr [bp+0Eh],ax
popa
ret

Get_Key endp

;#############################################################################

Str_Dec_To_Bin proc near

pushad
mov ds: dword ptr [di],0h
call Str_Len
or ax,ax
je exit_str_dec_to_bin
dec ax
xchg ax,bx
xor eax,eax
mov edx,1h
loop_char_str:
movzx ecx,ds: byte ptr [bx+si]
sub cl,'0'
imul ecx,edx
add eax,ecx
imul edx,10d
sub bx,1h
jnc loop_char_str
mov ds: dword ptr [di],eax
exit_str_dec_to_bin:
popad
ret

Str_Dec_To_Bin endp

;#############################################################################

Write_Dec_Num64 proc near

pushad
push eax
push edx
mov edi,0Ah
xor bh,bh
next_dec_long_left:
push eax
mov eax,edx
xor edx,edx
div edi
mov ebp,eax
pop eax
div edi
mov edx,ebp
inc bh
or edx,edx
jne next_dec_long_left
or eax,eax
jne next_dec_long_left
call Get_Cursor_Position
add dl,bh
dec dl
call Set_Cursor_Position
pop edx
pop eax
mov ebx,0Ah
next_dec_long:
push eax
mov eax,edx
xor edx,edx
div ebx
mov ebp,eax
pop eax
div ebx
add dl,'0'
xchg ax,dx
call Write_Char
xchg ax,dx
call Get_Cursor_Position
sub dl,2h
call Set_Cursor_Position
mov edx,ebp
or edx,edx
jne next_dec_long
or eax,eax
jne next_dec_long
popad
ret

Write_Dec_Num64 endp

;#############################################################################

Write_Message proc near

pusha
mov ah,9h
int 21h
popa
ret

Write_Message endp

;#############################################################################

Write_Char proc near

pusha
mov ah,0Eh
int 10h
popa
ret

Write_Char endp

;#############################################################################

Set_Cursor_Position proc near

pusha
mov ah,2h
xor bh,bh
int 10h
popa
ret

Set_Cursor_Position endp

;#############################################################################

Get_Cursor_Position proc near

pusha
mov ah,3h
xor bh,bh
int 10h
mov bp,sp
mov ss: word ptr [bp+0Ah],dx
popa
ret

Get_Cursor_Position endp

Str_Len proc near

push es
push ds
pop es
push cx
push di
mov di,si
mov cx,0FFFFh
xor al,al
repne scasb
not cx
dec cx
xchg ax,cx
pop di
pop cx
pop es
ret

Str_Len endp

code ends
end init


In allegato troverai l'eseguibile. A meno di bug "sembra funzionare" (ho avuto a disposizione poco tempo), non ci sono commente in quanto il sorgente e' autoespicativo, spero ti sia utile a scopo didattico.

Goldrake_xyz
20-10-2005, 15:07
I numeri binari possono anche essere in complemento 2,
questa rappresentazione è usata per i numeri interi positivi e negativi.
Ad esempio in binario normale si ha con 8 bit
Min = 00000000 = 0 ; MAX = 11111111 = 255
mentre in complemento 2 si hanno i valori (sempre x 8 bit)
Min = 10000000 = -128 ; MAX = 011111111 = 127

E questo si riflette anche nel linguaggio C, gli unsigned char è un byte
che può essere convertito in un intero da 0 a 255, mentre
i signed char possono essere convertiti in un numero da -128 a 127

IMUL è un' istruzione per la moltiplicazione di interi con segno,
cioè di numeri binari complemento2,

MUL è un' istruzione pre la moltiplicazione di interi senza segno,
cioè di numeri binari positivi

Esempio : voglio moltiplicare n1 x n2 (ovviamente n1 e n2 sono cifre)

MOV AX, n1 ; carico il registro AX
MOV BX, n2 ; carico il registro BX

IMUL BX ; esegue la moltiplicazione

IL risultato viene messo nei registri DX,AX

Goldrake_xyz
20-10-2005, 15:11
Sto cercando di trovare il programma che mi hai chiesto,
frà le migliaia di file dei miei programmi ... :fagiano:

Ah eccone uno (in allegato) :rolleyes:
Scritto mooolto tempo fà x MS-DOS e compilato con il TURBO ASSEMBLER 2.0,
a quel tempo non esistevano i caratteri proporzionali, e quindi
il programma può risultare disallineato ... :huh:

Ciao :D

Goldrake_xyz
20-10-2005, 15:38
Ooops, nel programma allegato si può anche vedere l'uso delle istruzioni
MUL e DIV con registri a 32 Bit (del 386 : EAX, EBX, ecc. ecc.)
Cmq. per fare la conversione si possono usare anche altri metodi,
che sono forse anche migliori ... :rolleyes:
Su google si trova tutto ! :O

Ciao :D

Lupino.86
20-10-2005, 22:36
Non puoi usare bh e bx come operatori... bl fa parte di bx...

Era un esempio stupido....... più scemo che stupido :banned:

Lupino.86
20-10-2005, 22:38
scrivilo in C poi usa il codice ottimizzato generato dal compilatore :D

Come come come? :mbe:

Lupino.86
20-10-2005, 22:50
Non hai specificato il sistema operativo, ne la modalita' del processore; ho scelto io DOS/WIN_VM modalita' reale:


In allegato troverai l'eseguibile. A meno di bug "sembra funzionare" (ho avuto a disposizione poco tempo), non ci sono commente in quanto il sorgente e' autoespicativo, spero ti sia utile a scopo didattico.

Inanzitutto ti ringrazio per il codice sorgente e l'eseguibile.

Scusa la totale ignoranza in materia, ma credo di nn sbagliare se ti dico che lavoriamo con DOS (al massimo scriviamo con il NotePad e salviamo in .ASM) e usiamo la programmazione Intel 80x86 :stordita:


Cmq ti giuro che nn ho MAi visto certe istruzioni....... potreti spiegarmele oppure devo trovarmi una guida?
Questo programma converte solo da decimale a binario oppure fa anche la moltiplicazione binaria e stampa il risultato convertito in decimale? :confused:

cionci
20-10-2005, 23:02
fa anche la moltiplicazione binaria
Rifletti su quanto hai detto...non esiste una moltiplicazione binaria, intera o esadeciamale... Una moltiplicazione è una moltiplicazione e basta... La base in cui esprimi operatori e risultato non contano...

Lupino.86
20-10-2005, 23:13
IMUL è un' istruzione per la moltiplicazione di interi con segno,
cioè di numeri binari complemento2,

MUL è un' istruzione pre la moltiplicazione di interi senza segno,
cioè di numeri binari positivi



io devo usare l'istruzione MUL perchè nn mi importa del segno..... però moltiplicare i numeri negativi sarebbe una finezza da pochi!


Posso dire che nn ho capito bene come si comporta la funzione MUL? :muro:

Lupino.86
20-10-2005, 23:21
Rifletti su quanto hai detto...non esiste una moltiplicazione binaria, intera o esadeciamale... Una moltiplicazione è una moltiplicazione e basta... La base in cui esprimi operatori e risultato non contano...

Sono d'accordo..... nn mi sono spiegato bene: la moltiplicazione deve essere eseguita a livello binario cioè con numeri binari

00000101 = 5
00000010 = 2
00000110= ----> stampo 10

cioè il programma deve convertire in binario, moltiplicare con i numeri binari e stampare a video il numero decimale :help:

cj++
21-10-2005, 02:22
Come come come? :mbe:

nn so che compilatore/IDE usi... ma è probabile che qualunque serio ti permetta di disassemblare il codice e quindi di averlo tradotto in assembly :D

vs lo fa ad esempio, ma probabilmente anche molti altri

cionci
21-10-2005, 09:15
Sono d'accordo..... nn mi sono spiegato bene: la moltiplicazione deve essere eseguita a livello binario cioè con numeri binari
Appunto...non ha senso dire: voglio fare una moltiplicazione in binario... Una moltiplicazione è una moltiplicazione e basta...qualsiasi sia la sua base...

Cioè se io leggo il carattere ASCII '5' da tastiera e poi ci sottraggo il carattere ASCII '0' ottengo il numero 5 (5 è 5 rappresentato in decimale, 5 in ottale, 5 in esadecimale, 101 in binario)...leggo il carattere ASCII '8' da tastiera e poi ci sottraggo il carattere ASCII '0' ottengo il numero 8 (8 è 8 rappresentato in decimale, 10 in ottale, 8 in esadecimale, 1000 in binario)...
Li moltiplico fra loro:

8 x 5 è 40 in decimale, 50 in ottale, 28 in esadecimale, 101000 in binario

Ma i numeri sono sempre numeri...la base è solo una questione di rappresentazione del numero... Quindi puoi dire: prendo due numeri decimali da tastiera, li moltiplico fra di loro e stampo il risultato in decimale... Puoi dire anche: prendo due numeri ottali da tastiera, li moltiplico fra di loro e stampo il risultato in esadecimale...
Ma non puoi dire: prendo due numeri decimali da tastiera, li converto in binario (questa conversione non avviene !!! Ma avviene una conversione da carattere ASCII a intero), li moltiplico in binario (una moltiplicazione è indipendente dalla rappresentazione) fra di loro e il risultato lo converto da binario a decimale (anche questa non avviene, perchè avviene una conversione da numero intero a carattere ASCII) e lo stampo...

Insomma...un numero è sempre un numero qualsiasi rappresentazione tu scelga...ed una moltiplicazione, presa come operazione, è sempre una moltiplicazione qualsiasi rappresentazione tu scelga degli operandi e del risultato...

Devi considerare la natura binaria dei registri e della memoria solo quando vai a fare una operazione bit a bit... Per carità, puoi chiamare moltiplicazione binaria l'algoritmo che moltiplica due operandi binari (quello che avviene nella ALU della CPU) e implementarlo tramite codice, ma non mi sembra che sia quello che tu vuoi fare...

Lupino.86
21-10-2005, 10:23
Appunto...non ha senso dire: voglio fare una moltiplicazione in binario... Una moltiplicazione è una moltiplicazione e basta...qualsiasi sia la sua base...

Devi considerare la natura binaria dei registri e della memoria solo quando vai a fare una operazione bit a bit... Per carità, puoi chiamare moltiplicazione binaria l'algoritmo che moltiplica due operandi binari (quello che avviene nella ALU della CPU) e implementarlo tramite codice, ma non mi sembra che sia quello che tu vuoi fare...

Come devo farti capire che ho capito benissimo cosa intendi dire?
Vallo a dire alla mia prof. e vedi che continuerà ad insistere sul calcolo binario dei numeri: è come se vuole vedere gli 0 e gli 1 che si moltiplicano!


Tu cosa mi consigli di fare? :help:
Acquisisco, moltiplico e stampo sempre in decimale?

Lupino.86
21-10-2005, 10:25
nn so che compilatore/IDE usi... ma è probabile che qualunque serio ti permetta di disassemblare il codice e quindi di averlo tradotto in assembly :D

vs lo fa ad esempio, ma probabilmente anche molti altri

Che cosa è un IDE?
Il compilatore che usiamo è il TASM.


VS è il nime del programma che traduce da C ad Assembler?
Cmq c'è differenza tra Assembly e Assembler: il primo è per Linux!!!

repne scasb
21-10-2005, 12:10
Cmq ti giuro che nn ho MAi visto certe istruzioni....... potreti spiegarmele oppure devo trovarmi una guida?


Sono normali istruzioni assembly x86, del tutto standard predisposte per l'assemblaggio mediante TurboAssembler della Borland (ancora oggi utilizzato per scopi didattici). Prima di sviluppare in assembly x86, devi necessariamente conoscere l'assembly x86, altrimenti qualsiasi sorgente ti apparira' del tutto incomprensibile. Qui: http://www.giobe2000.it/Tutorial/index.htm per iniziare a capire le base della programmazione assembly x86.


Questo programma converte solo da decimale a binario oppure fa anche la moltiplicazione binaria e stampa il risultato convertito in decimale?


1) Il software accetta due input da tastiera decimali a 9 cifre.
2) Converte le stringhe decimali in interi a 32-bit.
3) Moltiplica i due interi a 32-bit e ottiene un intero a 64-bit.
4) Visualizza a video l'intero a 64-bit in formato decimale.

Prova l'eseguibile nella shell del tuo sistema operativo cosi' ti apparira' piu' chiaramente cosa e' in grado di fare.

Lupino.86
21-10-2005, 12:40
Sono normali istruzioni assembly x86, del tutto standard predisposte per l'assemblaggio mediante TurboAssembler della Borland (ancora oggi utilizzato per scopi didattici).

A scuola usiamo proprio quello :)

Prima di sviluppare in assembly x86, devi necessariamente conoscere l'assembly x86, altrimenti qualsiasi sorgente ti apparira' del tutto incomprensibile. Qui: http://www.giobe2000.it/Tutorial/index.htm per iniziare a capire le base della programmazione assembly x86.

Conosco le strette istruzioni dell'Assembler, ma nn mi chiedere di sapere tanto!


Prova l'eseguibile nella shell del tuo sistema operativo cosi' ti apparira' piu' chiaramente cosa e' in grado di fare.

Ho provato l'eseguibile (grazie ancora): mi chiede l'Input ma si chiude prima di stampare a video......perchè? :doh:

repne scasb
21-10-2005, 12:48
Ho provato l'eseguibile (grazie ancora): mi chiede l'Input ma si chiude prima di stampare a video......perchè?

Vedo, che sempre meno persone utilizzano le shell messe a disposizione del proprio sistema operativo. Ti allego una nuova versione che attende la pressione di un tasto prima di terminare l'esecuzione.

Lupino.86
21-10-2005, 14:59
Vedo, che sempre meno persone utilizzano le shell messe a disposizione del proprio sistema operativo.

[QUOTE]Devo prenderla come <<"Sei un ignorante?">>

Ti allego una nuova versione che attende la pressione di un tasto prima di terminare l'esecuzione.

Grazie ancora, però è meglio se il risultato andrebbe scritto a capo e non sulla stessa riga del secondo input :fagiano: .....nn ti sto chiedendo m ica di farlo nè di abusare della tua pazienza e disponiblità!


Ora mi devo studiare solo il 96% delle istruzioni che nn conosco :muro: .... non posso certo consegnare un simile programma :D

repne scasb
21-10-2005, 15:07
Grazie ancora, però è meglio se il risultato andrebbe scritto a capo e non sulla stessa riga del secondo input


E' Windows XP che ha un idiosincrasia nei confronti dell'INT 21h-Func 9h. Se eseguissi il software due volte ti accorgeresti che la seconda volta che lo esegui sarebbe in grado di funzionare correttamente.

Lupino.86
21-10-2005, 15:23
E' Windows XP che ha un idiosincrasia nei confronti dell'INT 21h-Func 9h. Se eseguissi il software due volte ti accorgeresti che la seconda volta che lo esegui sarebbe in grado di funzionare correttamente.

mi spiace ma devo smentirti...... :Prrr:
Anche avviando 5 volte il programma, il risultato viene sempre scritto sulla stessa riga del secondo input

repne scasb
21-10-2005, 15:30
mi spiace ma devo smentirti...... :Prrr:
Anche avviando 5 volte il programma, il risultato viene sempre scritto sulla stessa riga del secondo input

1) Click con il tasto sinistro del mouse su "Start" (in basso a sinistra sul tuo video.
2) Click con il tasto sinistro del mouse su Esegui.
3) Digita il comando CMD e quindi il tasto INVIO.
4) Se MUL.EXE si trova nella directory D:\Programmi\Prove digita:
4a) Digita D: quindi il tasto INVIO.
4b) Digita CD \Programmi\Prove quindi il tasto INVIO.
5) Digita MUL.EXE quindi il tasto INVIO <<<<<----- Questa prima volta non funzionera'.
6) Riesegui MUL.EE quindi il tasto INVIO <<<<<----- Questa volta funzionera'.
7) Digita EXIT quindi il tasto INVIO per chiudere la shell.

Lupino.86
21-10-2005, 15:39
Azzo è vero! :eek:

Ma chi sei?
un mago? :D oppuro lo zio Bill? :D :D :D :D

Goldrake_xyz
21-10-2005, 16:25
A proposito di base, sarebbe utile ricordare che la conversione
da binario a esadecimale e viceversa è una conversione diretta.
Mentre così non è per la conversione decimale binario ...

Cioè invece di scrivere 11011001 in assembler si usa scrivere
la cifra esadecimale C9, infatti una cifra esadecimale corrisponde
a 4bit (nibble)

Appropos i gruppi di bit si dividono così :

4 bit = nibble
8 bit = byte
16 bit = world
32 bit = dworld
64 bit = qword
80 bit = ten byte (usato nel coprocessore math)

P.S. prima di mettere mano all' asm sarebbe utile acquistare
un libro ASM 8086 Tipo quello della Jackson dove sono elencate
tutte le istruzioni e il loro funzionamento ... ;)
Per poi passare alle istruzioni 386 estese a 32 bit, dopo si possono
studiare anche le istruzioni dei pentuim/amd 64 bit ...:sofico:
(una guida di riferimento delle istruzioni a 64 bit stà sul sito intel)
e anche uno sguardo alle istruzioni Floating point non sarebbe male,
ma li la questione si fà complessa x la presenza di numeri in
esponente e mantissa (binari !) normalizzati ... :rolleyes:

Ciao :D

Lupino.86
21-10-2005, 16:50
Cmq. per fare la conversione si possono usare anche altri metodi, che sono forse anche migliori ... :rolleyes:
Su google si trova tutto ! :O

Ciao :D

Peccano che io su Gooooogle nn abbia trovato nulla di utile, se non taaanta confusione :muro:

Quali metodi sarebbero migliori? :(

Goldrake_xyz
21-10-2005, 18:23
Purtroppo bisonga usare Google e cercare per diverse ore, soprattutto
sui siti americani, ovviamente in inglese :( .
Alla fine qualche buon programma si trova ;)

Io ad esempio, ai miei tempi - quando non c'era internet - mi sono
rotto la testa nel cercare di scrivere un' algoritmo che convertisse
i numeri esponente e mantissa normalizzati da decimale a binario
e viceversa.
In pratica tutti i linguaggi di programmazione la implementano,
quando si acquisice una variabile di tipo float o double float
e quando si stampa il risultato in decimale con virgola ... :mc:

Ciao :)

^TiGeRShArK^
21-10-2005, 18:57
ai tempi li mio prof ci aveva fatto implementare la moltiplicazione binaria in assembly SPARC nel senso che non potevamo usare l'operazione ma dovevamo agire direttamente sui bit (ora non mi ricordo il procedimento completo, ma per moltiplicazioni per potenze di due basta shiftare a sinistra di un numero di bit pari alla potenza di due... per gli altri numeri c'era una soluzione simile ma lievemente complicata che ora mi sfugge)...
quindi presumo che sia questo che viene inteso come moltiplicazione binaria... o no?:confused:

Lupino.86
21-10-2005, 19:36
ai tempi li mio prof ci aveva fatto implementare la moltiplicazione binaria in assembly SPARC nel senso che non potevamo usare l'operazione ma dovevamo agire direttamente sui bit (ora non mi ricordo il procedimento completo, ma per moltiplicazioni per potenze di due basta shiftare a sinistra di un numero di bit pari alla potenza di due... per gli altri numeri c'era una soluzione simile ma lievemente complicata che ora mi sfugge)...
quindi presumo che sia questo che viene inteso come moltiplicazione binaria... o no?:confused:

Io intendo dire proprio questo per moltiplicazione binaria ..... ma stando a quanto dice cionci:

Rifletti su quanto hai detto...non esiste una moltiplicazione binaria, intera o esadeciamale... Una moltiplicazione è una moltiplicazione e basta... La base in cui esprimi operatori e risultato non contano... :mbe: :mbe: :mbe: :mbe: :mbe: :mbe: :mbe:

repne scasb
21-10-2005, 20:00
ai tempi li mio prof ci aveva fatto implementare la moltiplicazione binaria in assembly SPARC nel senso che non potevamo usare l'operazione ma dovevamo agire direttamente sui bit (ora non mi ricordo il procedimento completo, ma per moltiplicazioni per potenze di due basta shiftare a sinistra di un numero di bit pari alla potenza di due... per gli altri numeri c'era una soluzione simile ma lievemente complicata che ora mi sfugge)...
quindi presumo che sia questo che viene inteso come moltiplicazione binaria... o no?:confused:

Per assembly x8 potrebbe essere questa?


; Moltiplicazione senza MUL/IMUL
; _val1,_val2 = Operandi
; _result = Risultato moltiplicazione

mov ax,word ptr [_val1]
movzx ebx,word ptr [_val2]
mov cx,1h
xor edx,edx
loop_mul:
test ax,cx
je no_add_mul
add edx,ebx
no_add_mul:
add ebx,ebx
add cx,cx
jne loop_mul
mov dword ptr [_result],edx

cj++
21-10-2005, 22:02
Che cosa è un IDE?
Il compilatore che usiamo è il TASM.
VS è il nime del programma che traduce da C ad Assembler?
Cmq c'è differenza tra Assembly e Assembler: il primo è per Linux!!!

Io ho sempre saputo che Assembly è il nome del linguaggio ed assembler lo strumento, in ogni caso... ci capiamo lo stesso ;)

VS (un IDE) è visual studio di Microsoft. Nn so gli altri IDE ma questo ti consente di disassemblare qualunque codice C/C++ al volo e di averne quindi una versione Assembly (o assembler come preferisci).

In questo senso ti dicevo... potresti scriverlo in C e fartelo tradurre da un qualunque IDE (che lo faccia).

Era solo un'idea cmq.

Lupino.86
21-10-2005, 22:20
La stessa idea mi è subito venuta appena la prof. ha finito di dettare la traccia, ma non sapendo come tradurre da C+ ad Assemplber 8lo so benissimo che ilC usa internamente l'assembler) ho acantonato l'idea.



Tu mi dici che con il Visual Studio potrei avere un sorgente in Assempler senza errori o incomprensioni software?

cj++
22-10-2005, 01:24
Probabilmente qualnque ambiente di sviluppo C lo fa, senza necessità di utilizzare strumenti cosi costosi.

Sicuramente è corretto... se no nn funzionerebbe ;)

Se nn riesci direttamente in assembly, potresti usarlo come utlima risorsa o cmq per confrontare quello che scrivi tu con quello scritto dalla macchina.

cionci
22-10-2005, 08:46
Io intendo dire proprio questo per moltiplicazione binaria ..... ma stando a quanto dice cionci:
:mbe: :mbe: :mbe: :mbe: :mbe: :mbe: :mbe:
Io anche detto che per moltiplicazione binaria puoi intendere l'algoritmo che usa la ALU per moltiplicare due numeri...leggi sopra... Se devi implementare quell'algoritmo senza usare l'istruzione IMUL finalmente abbiamo capito cosa devi fare...

cionci
22-10-2005, 08:48
Probabilmente qualnque ambiente di sviluppo C lo fa, senza necessità di utilizzare strumenti cosi costosi.
Se lui deve realizzare un algoritmo di moltiplicazione in Assembly dubito che realizzarlo ad alto livello e poi confrontarlo gli sia molto facile...anche perchè la differenza fra il suo algoritmo programmato direttamente in assembly e quello scritto ad alto livello e poi tradotto in assembly sarebbe abissale...
Conta che l'io ci sarebbero le chiamate a funzione...e quindi sarebbe ancora meno confrontabile...

Lupino.86
22-10-2005, 15:30
Io anche detto che per moltiplicazione binaria puoi intendere l'algoritmo che usa la ALU per moltiplicare due numeri...leggi sopra... Se devi implementare quell'algoritmo senza usare l'istruzione IMUL finalmente abbiamo capito cosa devi fare...

Non posso darti nessuna sicurezza perchè la prof non ha obbligato l'uso di nessuna istruzione, cioè non mi ha detto di usare per forza l'istruzione ZZZ..... posso usare anche l'istruzione YYY, l'importante è che il risultato è giusto :D e che la traccia venga rispettata

cionci
22-10-2005, 15:36
Allora non ho ancora capito cosa deve fare il codice... Creare l'algoritmo di moltiplicazione binaria (in tal caso non devi usare l'istruzione MUL visto che applica già l'algoritmo sui due registri) o fare la moltiplicazione fra due numeri (con l'istruzione MUL) ?!?!? :D
Chiarisciti con lei e poi ne riparliamo...

Lupino.86
22-10-2005, 15:48
Probabilmente qualnque ambiente di sviluppo C lo fa, senza necessità di utilizzare strumenti cosi costosi.

Farlo in C è facilissimo, lo so benissimo....... il problema è che la prof. ESIGE l'assembler :doh:

Lupino.86
22-10-2005, 22:59
Allora non ho ancora capito cosa deve fare il codice... Creare l'algoritmo di moltiplicazione binaria (in tal caso non devi usare l'istruzione MUL visto che applica già l'algoritmo sui due registri) o fare la moltiplicazione fra due numeri (con l'istruzione MUL) ?!?!? :D
Chiarisciti con lei e poi ne riparliamo...
Forse nn nn mi sono ancora spiegato bene: la moltiplicazione deve essere eseguita a livello binario cioè con numeri binari come nell'esempuio sottostante:

5 = 00000101 * ---> primo INPUT
2 = 00000010 = ---> secondo INPUT
_________
10 = 00000110 ----> stampo 10 come risultato

Cioè il programma deve convertire in binario i due operandi, moltiplicare con i numeri binari (sempre a livello binario) e stampare a video il numero decimale a sua volta convertito da binario a decimale

^TiGeRShArK^
22-10-2005, 23:45
Io intendo dire proprio questo per moltiplicazione binaria ..... ma stando a quanto dice cionci:
:mbe: :mbe: :mbe: :mbe: :mbe: :mbe: :mbe:
se usi l'operatore MUL ha ragione cionci....
infatti noi abbiamo dovuto implementare l'operatore MUL ..
se poi devi fare pure tu quello allora è stato cionci a nn avere capito un kakkio km al solito! :Prrr:

(Ora s'inkazza e mi banna! :D)

^TiGeRShArK^
23-10-2005, 00:48
Per assembly x8 potrebbe essere questa?


; Moltiplicazione senza MUL/IMUL
; _val1,_val2 = Operandi
; _result = Risultato moltiplicazione

mov ax,word ptr [_val1]
movzx ebx,word ptr [_val2]
mov cx,1h
xor edx,edx
loop_mul:
test ax,cx
je no_add_mul
add edx,ebx
no_add_mul:
add ebx,ebx
add cx,cx
jne loop_mul
mov dword ptr [_result],edx


l'assembly x86 purtroppo non l'ho mai studiato ... ho solo fatto qualke kazzatina con assembly x SPARC e x 68000 all'univ..
cmq provo a interpretare quello ke hai scritto e dimmi se ho interpretato bene....
mov ax,word ptr [_val1]
sposta nel registro ax il primo operando
movzx ebx,word ptr [_val2]
la movzx non l'ho mai vista... :mbe: ... meno male ke c'è santo google :D.. ho visto ke sposta in ebx il secondo operando riempiendolo di zeri a sinistra...(sempre se nn ho capito male ... :Prrr: )
mov cx,1h
mette nel registro cx il valore 1h (nell'assembly x86 era possibile assegnare un valore in maniera immediata in questo modo? nn lo sapevo proprio..pensavo lo facessero solo i 68000 kn uno dei loro TANTI modi di indirizzamento.. :mbe: )
xor edx,edx
??? e questa? :confused:azzera il contenuto di edx ??? :mbe:
loop_mul confronta ax e cx.... se sono uguali va in no_add_mul (quindi esce dal ciclo)
loop_mul:
test ax,cx
je no_add_mul
add edx,ebx
somma i registri edx e ebx mettendo il risultato nel primo....(al primo ciclo copia il contenuto di ebx in edx dato ke edx è 0 se nn ho capito male...)

no_add_mul:
add ebx,ebx
somma ebx con se stesso...
add cx,cx
somma cx con se stesso... (non ci sto capendo più un kakkio.. non doveva essere add cx, 1h??? :mbe: )
jne loop_mul
ritorna all'inizio del ciclo... non mi kiedere in base a cosa fa il confronto che non ho la minima idea..... forse sempre ax e cx????
mov dword ptr [_result],edx
mette il risultato in edx....



ora.. se non ho capito male praticamente stai facendo la somma ax volte di ebx... praticamente per fare 12 X 10 sommi 12 volte 10 a se stesso...
io quando avevo implementato l'operazione avevo usato un'altra tecnica...
ad esempio...
per moltiplicare un numero per le potenze di due shiftavamo il numero a sinistra di un numero di bit pari alla potenza di due per cui veniva moltiplicato....
praticamente...
3=011 2=010 3*2=6=110 --> ottenuto shiftando a sinistra 011 di un bit
3=011 4=010 3*4=12=1100 --> ottenuto shiftando a sinistra 011 di due bit
5=0101 4=0010 5*4=20=10100 -->ottenuto shiftando a sinistra 0101 di due bit
e così via...
per moltiplicare numeri ke non siano potenze di due avevamo trovato un metodo abbastanza simile.... sola ke ora km ora mi sfugge... :muro:
e questo è sicuramente + efficiente ke sommare il num per sè stesso x n volte...
ma scommetto ke ovviamente lo sapevi già e hai scritto quel codice poco efficiente solo per vedere se qualcuno si prendeva la briga di controllare..:mbe:
se è ks visto ke c 6 ricordami km si procedeva x moltiplicare numeri qualsiasi ke non siano potenze di due ks intanto io faccio riposare un pò i miei neuroni stanki ;)

repne scasb
23-10-2005, 09:07
mov ax,word ptr [_val1]
sposta nel registro ax il primo operando


Ok


movzx ebx,word ptr [_val2]
la movzx non l'ho mai vista... :mbe: ... meno male ke c'è santo google :D.. ho visto ke sposta in ebx il secondo operando riempiendolo di zeri a sinistra...(sempre se nn ho capito male ...


Ok


mov cx,1h
mette nel registro cx il valore 1h (nell'assembly x86 era possibile assegnare un valore in maniera immediata in questo modo? nn lo sapevo proprio..pensavo lo facessero solo i 68000 kn uno dei loro TANTI modi di indirizzamento..


Ok


xor edx,edx
??? e questa? :confused:azzera il contenuto di edx ??? :mbe:


Si, azzera edx.


loop_mul confronta ax e cx.... se sono uguali va in no_add_mul (quindi esce dal ciclo)[CUT....]


No. test ax,cx e' diverso da cmp ax,cx; ossia e' un confronto bit a bit.


ora.. se non ho capito male praticamente stai facendo la somma ax volte di ebx... praticamente per fare 12 X 10 sommi 12 volte 10 a se stesso...


Mica sono matta. per fare 1*1.000.000.000 sommerebbe 1 un miliardo di volte!

supponi di voler moltiplicare 21.167 * 18.529. In notazione binaria avremo:

101001010101111 * (21167)
100100001100001 = (18529)
-------------------

noterai ce 18529 ha settati a 1 solo i bit 14,11,6,5,0, da cui si evince che:

18529=2^14+2^11+2^6+2^5+2^0, da cui:

21167 * 18529= 21167*(2^14+2^11+2^6+2^5+2^0) da cui:

21167 *18529= 21167*2^14 + 21167*2^11 + 21167*2^6 +21167*2^5+21167*2^0 da cui:

21167 * 18529= 21167 shift a sinistra di 14 + 21167 shift a sinistra di 11 + 21167 shift a sinistra di 6 + 21167 shift a sinistra di 5 + 21167 shift a sinistra di 0 da cui:

21167 * 18529 = 346800128 + 43350016 + 1354688 + 677344 + 21167 = 392203343

L'algoritmo in assembly x86 fa esattamente questo (chiaramente per qualsiasi valore degli operando). Spero sia chiaro.

cionci
23-10-2005, 10:05
Forse nn nn mi sono ancora spiegato bene: la moltiplicazione deve essere eseguita a livello binario cioè con numeri binari come nell'esempuio sottostante:

5 = 00000101 * ---> primo INPUT
2 = 00000010 = ---> secondo INPUT
_________
10 = 00000110 ----> stampo 10 come risultato

Cioè il programma deve convertire in binario i due operandi, moltiplicare con i numeri binari (sempre a livello binario) e stampare a video il numero decimale a sua volta convertito da binario a decimale
Allora DEVI usare l'operatore MUL...ma come ti ripeto NON AVVIENE NESSUNA CONVERSIONE IN BINARIO !!! O meglio, avviene ma implicita nella lettura del carattere da tastiera... Quindi il tuo programma non dovrà effettuare nessuna conversione da decimale a binario e da binario a decimale... I contenuti dei registri li devi trattare (in questo caso) come semplici numeri naturali...

^TiGeRShArK^
23-10-2005, 11:05
L'algoritmo in assembly x86 fa esattamente questo (chiaramente per qualsiasi valore degli operando). Spero sia chiaro.
ok... l'algoritmo è perfettmente chiaro.
l'implementazione in assembly mi devo mettere con calma per capirla....
ci provo pomeriggio :D

Lupino.86
23-10-2005, 12:38
Allora DEVI usare l'operatore MUL...ma come ti ripeto NON AVVIENE NESSUNA CONVERSIONE IN BINARIO !!! O meglio, avviene ma implicita nella lettura del carattere da tastiera... Quindi il tuo programma non dovrà effettuare nessuna conversione da decimale a binario e da binario a decimale... I contenuti dei registri li devi trattare (in questo caso) come semplici numeri naturali...

E questo l'ho capito!
ma per usare i numeri binari, che istruzione devo usare?
Come andrebeb strutturato il codice??? :help:

Lupino.86
23-10-2005, 12:40
ok... l'algoritmo è perfettmente chiaro.
l'implementazione in assembly mi devo mettere con calma per capirla....
ci provo pomeriggio :D

Anche tu hai lo stesso mio problema? :D

^TiGeRShArK^
23-10-2005, 14:29
no no... io sono semplicemente masochista! :O

era da un pò ke non toccavo l'assembly e volevo cercare di ricordarmi qualkosa :Prrr:

Lupino.86
23-10-2005, 15:13
no no... io sono semplicemente masochista! :O

era da un pò ke non toccavo l'assembly e volevo cercare di ricordarmi qualkosa :Prrr:

Mi piace a tua mentalità!