The MASM Forum

Miscellaneous => Irvine Book Questions. => Topic started by: ProtoflareX on February 28, 2016, 09:52:25 AM

Title: x86 assembly language newbie requesting help on a project.
Post by: ProtoflareX on February 28, 2016, 09:52:25 AM
Hello, masm32 forum users. I am taking an x86 assembly language course this semester and am struggling to grasp it as well as I was able to grasp Java. As a result of this, I am having quite a bit of trouble completing a project that my professor assigned recently (which is embarassing, because it is supposed to be a novice level course). To make matters worse, I cannot actually test code myself since I get an "A1000 error" each time I attempt to do a console build all. I was wondering if some of the forum users here could assist me with the project and provide useful hints / tips that will allow me to more easily work through it. I have posted picture of the project requirements as well as my current progress (which is barely anything) below. Oh, and I will be using the MASM32 editor in order to write the code.

Project requirements: http://puu.sh/nmguK/40e9e448d6.png

Current Progress: http://puu.sh/nnMI1/27ae69be6e.png

I am currently attempting to complete the task described in the first bullet point. Since I cannot test my code, I would like to know if I have completed that task, or if I have made any mistakes (which is highly likely).

Title: Re: x86 assembly language newbie requesting help on a project.
Post by: jj2007 on February 28, 2016, 10:02:07 AM
Error A1000 means probably that a file is missing. But you forgot to tell us which one.
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: ProtoflareX on February 28, 2016, 10:10:53 AM
This is the exact message: http://puu.sh/nnOg4/84e5bd0245.png

The thing is, I just checked that directory and the file is definitely there, as shown in this picture: http://puu.sh/nnOdS/8cf4a1c712.png
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: GoneFishing on February 28, 2016, 10:49:49 AM
Does Project1 file have .asm extension ?
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: ProtoflareX on February 28, 2016, 10:55:51 AM
Quote from: GoneFishing on February 28, 2016, 10:49:49 AM
Does Project1 file have .asm extension ?

I added the esm extension after reading your comment. I also facepalmed very hard when it worked. That was so obvious, but I still didn't realize. Oh well, thank you for helping me fix that, that would have been a major problem throughout the entire semester. Hopefully someone can help me with the requirements now.
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: hutch-- on February 28, 2016, 12:46:19 PM
Just note that we have a firm "No Homework" rule in this forum, members will help you but only if you do your own work. Ask other people to do your work for you and you will be shown the door.  :badgrin:
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: jj2007 on February 28, 2016, 01:00:34 PM
Quote from: ProtoflareX on February 28, 2016, 10:55:51 AMThat was so obvious

Don't worry, that happened to me, too. It is a bad habit of certain editors to save files without ending ;-)
Now go ahead and attack your agenda, step by step. We'll help you to correct errors in your code. How much time is left? Is your teacher Kip Irvine, or do you have another reason to use his library? Here, almost everybody uses Masm32...
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: ProtoflareX on February 29, 2016, 05:26:14 AM
I've continued to work on the project since my last response. I haven't made much progress, but that's besides the point. I am currently experiencing an issue in which I get error A2006 "undefined symbol : prompt" when I attempt a console build all. The line of code containing the prompt is similar to an example that I saw in my textbook, so I'm not sure what's causing the error. I have linked pictures of my current code and the error below. Would anyone happen to know why this is occurring?

Code: http://puu.sh/noIv3/43f1c653b3.png

Error: http://puu.sh/noIGx/94ab7ed071.png
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: GoneFishing on February 29, 2016, 06:08:10 AM
Probably assembler wants symbol prompt to be defined
Give to ML what he  wants
add  this to .data:
prompt BYTE "Hello I'm prompt",0
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: ProtoflareX on February 29, 2016, 06:27:44 AM
Quote from: GoneFishing on February 29, 2016, 06:08:10 AM
Probably assembler wants symbol prompt to be defined
Give to ML what he  wants
add  this to .data:
prompt BYTE "Hello I'm prompt",0

Ah, I see. It worked, thank you.
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: dedndave on February 29, 2016, 09:39:44 AM
you probably want something like "Enter a string" as a prompt

you have some other problems, though...

first, you probably want more than a single byte for an input buffer
in fact, the ReadString function needs a buffer that will accomodate the null terminator so, at least 2 bytes are needed
i suggest you use 256 characters for the buffer

theStringArray BYTE 256 dup(?)

also, the ReadString function needs 2 registers to be set...
ReadString inputs:
EDX = offset of the input buffer
ECX = maximum characters to input (including terminal null)


so, you probably want something like
    mov     edx,offset theStringArray
    mov     ecx,sizeof theStringArray
    call    ReadString
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: ProtoflareX on February 29, 2016, 10:41:39 AM
Quote from: dedndave on February 29, 2016, 09:39:44 AM
you probably want something like "Enter a string" as a prompt

you have some other problems, though...

first, you probably want more than a single byte for an input buffer
in fact, the ReadString function needs a buffer that will accomodate the null terminator so, at least 2 bytes are needed
i suggest you use 256 characters for the buffer

theStringArray BYTE 256 dup(?)

also, the ReadString function needs 2 registers to be set...
ReadString inputs:
EDX = offset of the input buffer
ECX = maximum characters to input (including terminal null)


so, you probably want something like
    mov     edx,offset theStringArray
    mov     ecx,sizeof theStringArray
    call    ReadString


After making changes based on your comment, my current code looks like what is linked in the picture below. However, when I do a console build all, I do not receive an input prompt. Would you happen to know the reason for this?

Current code: http://puu.sh/np4w9/e8c34a000c.png

Result of "console build all": http://puu.sh/np4GL/8e454a282f.png
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: dedndave on February 29, 2016, 12:56:43 PM
i sure do
you moved the ReadString call from the PROC, and placed it at the beginning of the program

it isn't very convenient that you post images of the code text
copy and paste the text into the reply window, then highlight it, then click on the # icon above the reply window
that way, we can copy and paste without having to do a lot of typing

originally, a partial looked like this

.code
main PROC
mov edx,offset theStringArray
call requestInput
EXIT
main ENDP

requestInput PROC

mov edx,offset prompt
call WriteString
call ReadString
ret
requestInput ENDP
END main


i suggested this modification
    mov     edx,offset theStringArray
    mov     ecx,sizeof theStringArray
    call    ReadString


you totally butchered my intent - lol

try this code...

    .CODE

main PROC

    mov     edx,offset theStringArray
    mov     ecx,sizeof theStringArray
    call    requestInput
    exit

main ENDP

requestInput PROC

    push    edx
    push    ecx
    mov     edx,offset prompt
    call    WriteString
    pop     ecx
    pop     edx
    call    ReadString
    ret

requestInput ENDP

    END     main
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: ProtoflareX on February 29, 2016, 01:06:16 PM
The result of your code is linked below. I'm going to assume that isn't the desired result. It feels absolutely awful to be incapable of discerning the problem myself. Also, I'll listen to your suggestion about pasting my code in the future.

Result of your code: http://puu.sh/npcSu/e9fc74f1bd.png
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: dedndave on February 29, 2016, 01:09:31 PM
that looks ok - did you try to run the program ?

Kip Irvine's library isn't very modular
so, everything gets pulled in, resulting in larger than needed EXE's
so, 9 KB might be ok
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: ProtoflareX on March 01, 2016, 06:39:34 AM
Quote from: dedndave on February 29, 2016, 01:09:31 PM
that looks ok - did you try to run the program ?

Kip Irvine's library isn't very modular
so, everything gets pulled in, resulting in larger than needed EXE's
so, 9 KB might be ok

Your code did work successfully, dedndave; I just made foolish mistake that caused me to think it didn't. Anyway, I am now attempting to solve the requirement in bullet point 2, which says: "Your program must have a procedure that accepts the address of a string and returns through EAX the length of the string". If I am correct, after the code below has finished executing, the address of the String typed in by the user is stored in EDX, right? If that is correct, then does that mean that I need to write a procedure that "USES" EDX in order to fulfill the requirement in the second bullet?

INCLUDE c:\irvine\irvine32.inc
INCLUDELIB c:\irvine\irvine32.lib
INCLUDELIB c:\masm32\lib\user32.lib
INCLUDELIB c:\masm32\lib\kernel32.lib

.data
theStringArray BYTE 256 dup(?)             
prompt BYTE "Please input a String",0

.CODE

main PROC

    mov     edx,offset theStringArray
    mov     ecx,sizeof theStringArray
    call    requestInput
    exit

main ENDP

requestInput PROC

    push    edx
    push    ecx
    mov     edx,offset prompt
    call    WriteString
    pop     ecx
    pop     edx
    call    ReadString
    ret

requestInput ENDP


getStringLength PROC USES edx

    ;temporarily empty

getStringLength ENDP

END     main
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: jj2007 on March 01, 2016, 02:11:57 PM
Quote from: ProtoflareX on March 01, 2016, 06:39:34 AMdoes that mean that I need to write a procedure that "USES" EDX

Logic is OK. I can't guarantee, though, that the address is in edx because I don't have the Irvine library.

One instruction you will need is cmp byte ptr [edx], 0

\Masm32\help\opcodes.chm has details on cmp.
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: dedndave on March 02, 2016, 01:13:22 AM
Kip Irvine's library has a function called Get_length
it isn't the greatest code in the world, but the library source does show you how it works
it is invoked with an argument - not quite what the assignment asks for

as for EDX, i think WriteString preserves all registers, so EDX will remain unaltered
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: ProtoflareX on March 02, 2016, 02:33:15 AM
Quote from: dedndave on March 02, 2016, 01:13:22 AM
Kip Irvine's library has a function called Get_length
it isn't the greatest code in the world, but the library source does show you how it works
it is invoked with an argument - not quite what the assignment asks for

as for EDX, i think WriteString preserves all registers, so EDX will remain unaltered

In the time since my last post, I found out that Irvine's library also has an StrLength function that I'm pretty sure is exactly what the second bullet requires. It is pasted below. I think my current goal is to see if it is possible to alter the StrLength function in order to accomplish the third bullet's task which is: "Your program must have a procedure that accepts the address of a string and returns through EAX the amount of "words" the string contains. For the purposes of this project, consider a "word" to be any non-whitespace characters that are bounded by whitespace, or by the beginning or ending of the string".

StrLength PROC
;
; OBSOLETE???
; Returns the length of a null-terminated string.
; Receives: EDX points to the string.
; Returns: EAX = string length.
; Last update: 6/9/05
;---------------------------------------------------------
    push edx
    mov eax,0             ; holds character count

L1: cmp BYTE PTR [edx],0   ; end of string?
    je L2                  ; yes: quit
    inc edx                  ; no: point to next
    inc eax                  ; add 1 to count
    jmp L1

L2: pop edx
    ret
StrLength ENDP
Title: Re: x86 assembly language newbie requesting help on a project.
Post by: ProtoflareX on March 03, 2016, 01:25:02 PM
Currently, I have bullets 1-4 completed, but I'm stuck once again on bullet 5, which says the following: "Your program must have a main procedure that calls the input method, calls the other three methods
mentioned above, and reports the findings of those three methods. See the Sample Run" (I put a link to a picture of the Sample Run below). There isn't anything difficult about calling functions, but I have no idea how to display output, or put values from registers into the output message for that matter. Can anybody provide hints / tips on how to do this?

Picture of Sample Run: http://puu.sh/nsOat/92e5fe92c1.png

Current code below:

INCLUDE c:\irvine\irvine32.inc
INCLUDELIB c:\irvine\irvine32.lib
INCLUDELIB c:\masm32\lib\user32.lib
INCLUDELIB c:\masm32\lib\kernel32.lib

.data
theStringArray BYTE 256 dup(?)             
prompt BYTE "Please enter a String: ",0

.CODE

main PROC

    mov     edx,offset theStringArray
    mov     ecx,sizeof theStringArray
    call    requestInput
    call    getStringLength           
    call    getNumWords             
    call    getNumVowels             
    exit

main ENDP

requestInput PROC

    push    edx
    push    ecx
    mov     edx,offset prompt
    call      WriteString
    pop     ecx
    pop     edx
    call      ReadString
    ret

requestInput ENDP


getStringLength PROC

    push edx
    mov eax,0               

L1: cmp BYTE PTR [edx],0      
    je L2                
    inc edx                  
    inc eax                  
    jmp L1

L2: pop edx
    ret

getStringLength ENDP


getNumWords PROC

    push    edx
    mov eax,0                 

L1: cmp BYTE PTR [edx],0       
      je L3                  
      cmp BYTE PTR [edx]," "     
      je       L2
      inc     edx                   
      jmp    L1                   

L2: inc edx                
      inc eax                
      jmp L1

L3: pop edx
      ret

getNumWords ENDP


getNumVowels PROC

    push edx
    mov eax,0                 

L1: cmp BYTE PTR [edx],0      
      je L3                  
      cmp BYTE PTR [edx],"a"
      je       L2
      cmp BYTE PTR [edx],"A"
      je       L2
      cmp BYTE PTR [edx],"e"
      je       L2
      cmp BYTE PTR [edx],"E"
      je       L2
      cmp BYTE PTR [edx],"i"
      je       L2
      cmp BYTE PTR [edx],"I"
      je       L2
      cmp BYTE PTR [edx],"o"
      je       L2
      cmp BYTE PTR [edx],"O"
      je       L2
      cmp BYTE PTR [edx],"u"
      je       L2
      cmp BYTE PTR [edx],"U"
      je       L2
      inc edx                  ; no: point to next
      jmp L1

L2: inc edx                  
      inc eax                  
      jmp L1

L3: pop edx
      ret

getNumVowels ENDP

END     main