Author Topic: XOR Encryption NASM code  (Read 22212 times)

Offline Johnksilver

  • Jr. Member
  • *
  • Posts: 6
XOR Encryption NASM code
« on: July 24, 2013, 06:34:33 PM »
Hi there, how can I change this code below to a NASM code? My key to encrypt is k = 326 and I want to user type a number of lenght = 7. So I want encrypt this number with XOR property and then I want to show the encrypted number (cipher text), after I want to decrypt and show the decrypted number and see if the algorithm is correct.

Code: [Select]
KEY = 326 ; any value between 1-255
BUFMAX = 128 ; maximum buffer size
section .data
sPrompt BYTE "Enter the plain text: ",0
sEncrypt BYTE "Cipher text: ",0
sDecrypt BYTE "Decrypted: ",0
buffer BYTE BUFMAX+1 DUP(0)
bufSize DWORD ?
.code
main PROC
call InputTheString ; input the plain text
call TranslateBuffer ; encrypt the buffer
mov edx,OFFSET sEncrypt ; display encrypted message
call DisplayMessage
call TranslateBuffer ; decrypt the buffer
mov edx,OFFSET sDecrypt ; display decrypted message
call DisplayMessage
exit
main ENDP
;-----------------------------------------------------
InputTheString PROC
;
; Prompts user for a plaintext string. Saves the string
; and its length.
; Receives: nothing
; Returns: nothing
;-----------------------------------------------------
pushad
mov edx,OFFSET sPrompt ; display a prompt
call WriteString
mov ecx,BUFMAX ; maximum character count
mov edx,OFFSET buffer ; point to the buffer
call ReadString ; input the string
mov bufSize,eax ; save the length
call Crlf
popad
ret
InputTheString ENDP
;-----------------------------------------------------
DisplayMessage PROC
;
; Displays the encrypted or decrypted message.
; Receives: EDX points to the message
; Returns: nothing
;-----------------------------------------------------
pushad
call WriteString
mov edx,OFFSET buffer ; display the buffer
call WriteString
call Crlf
call Crlf
popad
ret
DisplayMessage ENDP
;-----------------------------------------------------
TranslateBuffer PROC
;
; Translates the string by exclusive-ORing each
; byte with the encryption key byte.
; Receives: nothing
; Returns: nothing
;-----------------------------------------------------
pushad
mov ecx,bufSize ; loop counter
mov esi,0 ; index 0 in buffer
L1:
xor buffer[esi],KEY ; translate a byte
inc esi ; point to next byte
loop L1
popad
ret
TranslateBuffer ENDP
END main
« Last Edit: July 24, 2013, 06:45:05 PM by Frank Kotler »

Offline Frank Kotler

  • NASM Developer
  • Hero Member
  • *****
  • Posts: 2667
  • Country: us
Re: XOR Encryption NASM code
« Reply #1 on: July 24, 2013, 07:23:24 PM »
I edited your message to put "code tags" around your code - just the word "code" in square brackets at the beginning of your code, and "/code" in square brackets at the end. Hope I didn't screw anything up.

We can, and probably will, show you how to translate your code to Nasm syntax. However, there are some "issues" to be worked out first. The worst one is probably that your proposed key exceeds a byte. As the comment says, "between 1 and 255". What do you actually want to do here?

The other issue is that you use some apparently external functions - "WriteString" and "ReadString". These look like they might be Kip Irvine's stuff, but it could be anything. Do you have this library (irvine32.lib or whatever)? Do you wish to link against it ("should" work, but I'm not certain) or do you want to include "WriteString" and "ReadString" in your Nasm code? There is an apparent "exit" macro that will have to be dealt with, too.

Outside of that, it's mostly a case of deleting the "Masm cruft", but there are some things that will have to be changed as well. I used to do a lot of this, and I think I mostly remember how it goes. But merely translating it to Nasm syntax is unlikely to give you working code.

What do you really want to do here? (especially with the key?) Why do you want to use Nasm for what is apparently Masm code?

Best,
Frank


Offline Johnksilver

  • Jr. Member
  • *
  • Posts: 6
Re: XOR Encryption NASM code
« Reply #2 on: July 24, 2013, 07:44:32 PM »
I want the key to be 326, that comment was from the before this existing code. But this key could be any number, it's just the key to encryption.

I want to include the WriteString and ReadString to the Nasm code.

I want a Nasm code to implement the XOR property applied to encryption and decryption. I found this Masm code and I want to translate it for Nasm.

Offline Frank Kotler

  • NASM Developer
  • Hero Member
  • *****
  • Posts: 2667
  • Country: us
Re: XOR Encryption NASM code
« Reply #3 on: July 24, 2013, 08:20:15 PM »
326 isn't going to fit in a byte, regardless of what you want. You could, I suppose, xor your plain text with a word, two bytes at a time. I guess it would work.

Including "WriteFile" and "ReadFile" in Nasm would require knowing what OS. Windows, I suppose?

Best,
Frank


Offline Johnksilver

  • Jr. Member
  • *
  • Posts: 6
Re: XOR Encryption NASM code
« Reply #4 on: July 24, 2013, 09:44:33 PM »
Windows Seven x86. Let me try to be more clear, I need to do this:

Logic XOR operation has an interesting property. If an integer X is XORed with Y and the result Z is XORed with Y again, the result produced is X:

Z = X xor Y (Z xor Y) = X

This “reversible” property of XOR provides an easy way to perform data encryption: a plain text message can be transformed into an unintelligible string called cipher text by XORing each of its characters with a character called a key. The cipher text can be stored or transmitted to a remote location and not able to be read by unauthorized persons who do not have the key. The intended viewer uses the key to decrypt the cipher text and produce the original plain text.

Write an assembly language program in NASM to do the following:

1. Ask user to enter an account number (7 digits in length),
2. encrypt the account number with the key= 326,
3. print the encrypted string, cipher text, on the screen,
4. decrypt the encrypted string with the same key
5. print the decrypted string on the screen to verify the algorithm correctness.

Can you help me??
« Last Edit: July 25, 2013, 02:11:35 AM by Johnksilver »

Offline Frank Kotler

  • NASM Developer
  • Hero Member
  • *****
  • Posts: 2667
  • Country: us
Re: XOR Encryption NASM code
« Reply #5 on: July 25, 2013, 05:05:32 PM »
Hi John,

Here's my attempt. I'm clueless in Windows, so that part's probably wrong. I could have made a mistake in the "translate to Nasm" part too. It assembles without complaint - that doesn't mean it runs correctly!

Code: [Select]
global main

; these "true names" may be wrong
; try 'em without the underscore and/or without @n
; if your linker can't find 'em
; may depend on linker
%define ExitProcess _ExitProcess@4
%define GetStdHandle _GetStdHandle@4
%define WriteFile _WriteFile@20
%define ReadFile _ReadFile@20

extern ExitProcess
extern GetStdHandle
extern WriteFile
extern ReadFile

; comment does not match code!
KEY equ 326 ; any value between 1-255

BUFMAX equ 128 ; maximum buffer size

section .data
    sPrompt db "Enter the plain text: ",0
    sEncrypt db "Cipher text: ",0
    sDecrypt db "Decrypted: ",0

; should probably be local to routine
    newline db 13, 10, 0

section .bss
    buffer resb BUFMAX+1
    bufSize resd 1

; maybe should be local to routines
; but we want 'em persistant
    hstdin resd 1
    hstdout resd 1

; should probably be local to routines
    byteswritten resd 1
    bytesread resd 1

section .text
main:
    call InputTheString ; input the plain text
    call TranslateBuffer ; encrypt the buffer
    mov edx, sEncrypt ; display encrypted message
    call DisplayMessage
    call TranslateBuffer ; decrypt the buffer
    mov edx, sDecrypt ; display decrypted message
    call DisplayMessage

    push 0
    call ExitProcess
;-----------------------------------------------------
InputTheString:
;
; Prompts user for a plaintext string. Saves the string
; and its length.
; Receives: nothing
; Returns: nothing
;-----------------------------------------------------
    pushad
    mov edx, sPrompt ; display a prompt
    call WriteString
    mov ecx, BUFMAX ; maximum character count
    mov edx, buffer ; point to the buffer
    call ReadString ; input the string
    mov [bufSize], eax ; save the length
    call Crlf
    popad
    ret
;-----------------------------------------------------
DisplayMessage:
;
; Displays the encrypted or decrypted message.
; Receives: EDX points to the message
; Returns: nothing
;-----------------------------------------------------
    pushad
    call WriteString
    mov edx, buffer ; display the buffer
    call WriteString
    call Crlf
    call Crlf
    popad
    ret
;-----------------------------------------------------
TranslateBuffer:
;
; Translates the string by exclusive-ORing each
; byte with the encryption key byte.
; Receives: nothing
; Returns: nothing
;-----------------------------------------------------
    pushad
    mov ecx, [bufSize] ; loop counter
    mov esi,0 ; index 0 in buffer
L1:

; this is shonky - should be byte!
    xor word [buffer + esi],KEY ; translate a byte

    inc esi ; point to next byte
    loop L1
    popad
    ret
;------------------------

;-------------------------
WriteString:
; expects: buffer in edx, zero-terminated
; returns: bytes written in eax

    add dword [hstdout], 0
    jnz .gothandle
    push -11
    call GetStdHandle
    mov [hstdout], eax
.gothandle:
    push 0 ; character size? ascii=0 unicode=1
    push byteswritten
    xor eax, eax
.getlen:
    cmp byte [edx + eax], 0
    jz .gotlen
    inc eax
    jmp .getlen
.gotlen:
    push eax
    push edx
    push dword [hstdout]
    call WriteFile
    ; check error?
    mov eax, [byteswritten]
    ret
;-----------------------------
;-------------------------
ReadString:
; expects: buffer in edx, ecx = max
; returns: bytes written in eax

    add dword [hstdin], 0
    jnz .gothandle
    push -10
    call GetStdHandle
    mov [hstdin], eax
.gothandle:
    push 0 ; character size? ascii=0 unicode=1
    push bytesread
    push ecx
    push edx
    push dword [hstdout]
    call ReadFile
    ; check error?
    mov eax, [bytesread]
; does Readfile return input zero-terminated?
; zero-terminate it to be sure
; pray ReadFile doesn't trash edx!
    mov byte [edx + eax + 1], 0
    ret
;-----------------------------

;----------------------------
Crlf:
    push edx
    mov edx, newline
    call WriteString
    pop edx
    ret
;--------------------------           

Since you mention in a PM that you have Linux available, I'll probably do a Linux version that I can actually test. Patience, Grasshopper! :)

Best,
Frank


Offline Johnksilver

  • Jr. Member
  • *
  • Posts: 6
Re: XOR Encryption NASM code
« Reply #6 on: July 25, 2013, 05:15:57 PM »
Hehehehe, thank you. I hope that everything goes right in the version for linux. Meanwhile I will analyze this version. Thank you for your help, I really appreciate it.

Offline Johnksilver

  • Jr. Member
  • *
  • Posts: 6
Re: XOR Encryption NASM code
« Reply #7 on: July 25, 2013, 09:00:45 PM »
I tried to run the .obj but I got the following error: in function main nasm error undefined reference to WinMain@16.

Did you have any success with linux code?

Thanks in advance!

Offline Frank Kotler

  • NASM Developer
  • Hero Member
  • *****
  • Posts: 2667
  • Country: us
Re: XOR Encryption NASM code
« Reply #8 on: July 25, 2013, 10:59:51 PM »
Yeah, seems to work. I take it that using a key larger than a byte was your instructor's idea?

Code: [Select]
; nasm -f elf32 myfile.asm
; ld -o myfile myfile.o -melf_i386

global _start

; comment does not match code!
KEY equ 326 ; any value between 1-255

BUFMAX equ 128 ; maximum buffer size

section .data
    sPrompt db "Enter the plain text: ",0
    sEncrypt db "Cipher text: ",0
    sDecrypt db "Decrypted: ",0

; should probably be local to routine
    newline db 10, 0

section .bss
    buffer resb BUFMAX+1
    bufSize resd 1


section .text
_start:
    call InputTheString ; input the plain text
    call TranslateBuffer ; encrypt the buffer
    mov edx, sEncrypt ; display encrypted message
    call DisplayMessage
    call TranslateBuffer ; decrypt the buffer
    mov edx, sDecrypt ; display decrypted message
    call DisplayMessage

    mov eax, 1
    xor ebx, ebx
    int 80h
;-----------------------------------------------------
InputTheString:
;
; Prompts user for a plaintext string. Saves the string
; and its length.
; Receives: nothing
; Returns: nothing
;-----------------------------------------------------
    pushad
    mov edx, sPrompt ; display a prompt
    call WriteString
    mov ecx, BUFMAX ; maximum character count
    mov edx, buffer ; point to the buffer
    call ReadString ; input the string
    mov [bufSize], eax ; save the length
    call Crlf
    popad
    ret
;-----------------------------------------------------
DisplayMessage:
;
; Displays the encrypted or decrypted message.
; Receives: EDX points to the message
; Returns: nothing
;-----------------------------------------------------
    pushad
    call WriteString
    mov edx, buffer ; display the buffer
    call WriteString
    call Crlf
    call Crlf
    popad
    ret
;-----------------------------------------------------
TranslateBuffer:
;
; Translates the string by exclusive-ORing each
; byte with the encryption key byte.
; Receives: nothing
; Returns: nothing
;-----------------------------------------------------
    pushad
    mov ecx, [bufSize] ; loop counter
    mov esi,0 ; index 0 in buffer
L1:

; this is shonky - should be byte!
    xor word [buffer + esi],KEY ; translate a byte

    inc esi ; point to next byte
    loop L1
    popad
    ret
;------------------------

;-------------------------
WriteString:
; expects: buffer in edx, zero-terminated
; returns: bytes written in eax

    mov ecx, edx
    xor edx, edx
.getlen:
    cmp byte [ecx + edx], 0
    jz .gotlen
    inc edx
    jmp .getlen
.gotlen:
    mov ebx, 1
    mov eax, 4
    int 80h
    ret
;-----------------------------
;-------------------------
ReadString:
; expects: buffer in edx, ecx = max
; returns: bytes written in eax
    xchg ecx, edx
    mov ebx, 1
    mov eax, 3
    int 80h
    mov byte [ecx + eax + 1], 0
    ret
;-----------------------------

;----------------------------
Crlf:
    push edx
    mov edx, newline
    call WriteString
    pop edx
    ret
;--------------------------           


Offline Johnksilver

  • Jr. Member
  • *
  • Posts: 6
Re: XOR Encryption NASM code
« Reply #9 on: July 25, 2013, 11:06:30 PM »
Yes, thats right. Very thanks. I will just try to make the win code works. I don't know how to thank you.

Offline Frank Kotler

  • NASM Developer
  • Hero Member
  • *****
  • Posts: 2667
  • Country: us
Re: XOR Encryption NASM code
« Reply #10 on: July 26, 2013, 02:59:41 PM »
Many people helped me when I was first learning this stuff (and still do!). I'm just trying to "pass it on". If you want to "thank" me, do the same when you get the opportunity! 'Til then, you're welcome!

The "undefined reference to WinMain@16" sounds like you need to tell the linker that the entrypoint is "main". "-e main" for ld, probably "/entry main" or "/entrypoint main" for other linkers? You might try:
Code: [Select]
%define main WinMain@16
Do it before "global main"! The error message, as you've posted it, seems not to have an underscore on it. The other "true names" may not want an underscore either. Read the error messages (if any) carefully - there's information in 'em!

I should have mentioned that the Windows version is intended to be assembled with "-f win32". "-f obj" would need slightly different source code (it "will" do 32-bit code, but isn't very good at it, IMO).

If you need help with linking (and perhaps the correct "true names"), mention what linker you're using, and what command line you gave it, along with any error messages. Like assemblers, linkers are all different.

I can only hope that my "ReadString" and "WriteString" functions are correct... "close" probably won't work! I hope someone more familiar with Windows will take a look at that.

As Betov (author of RosAsm) used to say, "Courage!"

Best,
Frank