I don't understand why this code print me the char I've insert back and the alphabet string if nobody told him to do it...
The mov lettere+(counter-1),al
instruction does not do what you want.
MASM will add the (offset)addresses of lettere (0) and counter (41), and then subtract 1, yielding the address 40 where the instruction then overwrites an important $ string terminator. The next time that your program tries to print a newline caporiga, the DOS.PrintString function 09h will continue printing characters until it finds the $ that ends your alphabet string.
lea dx,counter
mov ah,02h
int 21h
This is another error. The DOS.PrintCharacter function 02h expects to find a character in the DL
register, but this lea dx,counter
instruction clearly loads an address.
mov dl, counter
add dl, '0'
mov ah, 02h
int 21h
The correct code first retrieves the count [1,10] from memory and then adds '0' (48) in order to convert into a printable character. This will of course fail when your count is 10. Look in Displaying numbers with DOS to learn how to overcome this problem.
One possible solution:
...
xor BX, BX ; Reset counter
insertLoop:
inc BX ; Increment counter
lea dx, [BX + 48] ; -> DL = "1", "2", ...
mov ah, 02h ; Won't work when counter is 10
int 21h
lea dx, frase2
mov ah, 09h
int 21h
mov ah, 01h
int 21h
mov [lettere + BX - 1], al
lea dx, caporiga
mov ah, 09h
int 21h
cmp BX, 9
jb insertLoop
...