The MASM Forum

General => The Workshop => Topic started by: Rob260z on July 26, 2017, 06:18:35 PM

Title: Introduction + Silly Question :)
Post by: Rob260z on July 26, 2017, 06:18:35 PM
Hi All :)

Well , in order to prove I'm not a bot, I thought I should introduce myself. My name is Robert and I have returned to Assembly programming after nearly 15 years. Looking for a bit of an intellectual challenge , plus I absolutely love the pure nature of Assembly.

Last time I did any programming I was using Boralnd Turbo Assembler. After a bit of a look around I have decided to settle on MASM.


Well , I'm going to start with a simple question. What am I doing wrong in the example below. I know I'm going to kick myself when I get the answer , but it's got me stumped. This approach works fine in NASM , but I obviously don't understand exactly how MASM pointers/referencing/stack works. Despite finding examples that appear to do the same thing.

A simple test function. I'm writing the modified string to a text file using WIN32 WriteFile. The issue appears to be the use of the INC instruction. With or without the INC instruction successfully writes to the file , but with the INC instruction the program crashes immediately after writing the file ( succsessfully ). Am I somehow corrupting the stack ?

        Str_DataLogText db "..........",13,10

     mov EBX , offset Str_DataLogText
   inc EBX          ;??????????????????????????????????????????????
   mov EDX , 49d
   mov byte ptr [ EBX ] , DL

        push 0
        push offset Var_DataLogBytesWritten
        push 12d
       push offset Str_DataLogText
       push Hdl_DataLogFile
       call WriteFile

     

      cheers ,
      Rob
Title: Re: Introduction + Silly Question :)
Post by: jj2007 on July 26, 2017, 06:42:35 PM
Hi Robert,
First things first: Welcome to the Forum :icon14:

Your code works fine. It took me ten minutes of my precious time, though, to set up the missing headers, insert the variables etc - be prepared that this is the last time that I help you unless you decide to post complete code with detailed comments in future.

include \masm32\include\masm32rt.inc ; obligatory in this forum, for practical reasons!

.data
Str_DataLogText db "..........",13,10
Var_DataLogBytesWritten dd ?
Hdl_DataLogFile dd ?
.code
start:
mov EBX , offset Str_DataLogText
   inc EBX          ;??????????????????????????????????????????????
   mov EDX , 49d
   mov byte ptr [ EBX ] , DL
mov Hdl_DataLogFile, fopen("tmp.txt")
        push 0
        push offset Var_DataLogBytesWritten
        push 12d
       push offset Str_DataLogText
       push Hdl_DataLogFile
       call WriteFile

       fclose Hdl_DataLogFile
  exit

end start


You should also get used to the invoke macro. The old habit of pushing parameters around is error-prone, especially if a function needs a dozen parameters, like e.g. CreateWindowEx.

So your code crashes. Weird, mine doesn't  8)

It could remain forever a mystery, but there is a solution: In case of little programs that crash, it is a good habit to zip the exe and attach it here, so that we can launch Olly (http://www.ollydbg.de/version2.html) and analyse the problem. For example, without a crystal ball we won't know which parameters you used for the unknown API call that you used to open the file.
Title: Re: Introduction + Silly Question :)
Post by: Rob260z on July 26, 2017, 06:49:32 PM
Hi jj2007 :)

Thank you for your time , very much appreciated.

Sorry , but I appear to have wasted it ( your time ). I was just typing a new comment when you replied.

I'm very embarrassed , but I forgot to put a RET instruction at the end of the procedure **** hangs head in shame ****

I would have posted the total code but its already around 300 lines. Too much for a forum post ?

Regarding the use of invoke.....I still feel dirty using it , lol. I'm a bit of a purist :)
Title: Re: Introduction + Silly Question :)
Post by: Rob260z on July 26, 2017, 07:00:28 PM
In future I'll create self-contained , executable code before posting up any example code. This way I would have actually realised what the problem was.
Title: Re: Introduction + Silly Question :)
Post by: jj2007 on July 26, 2017, 07:38:07 PM
Quote from: Rob260z on July 26, 2017, 06:49:32 PMI would have posted the total code but its already around 300 lines. Too much for a forum post ?

No problem, you have 32k if I remember well. If it's more, zip the source and attach it. The limit is 524,288 bytes then.

Quote from: Rob260z on July 26, 2017, 06:49:32 PMRegarding the use of invoke.....I still feel dirty using it , lol. I'm a bit of a purist :)

As a purist, if you code in C, do you still use the original Kernighan & Ritchie compiler?
Title: Re: Introduction + Silly Question :)
Post by: sinsi on July 26, 2017, 08:20:22 PM
Quote from: jj2007 on July 26, 2017, 07:38:07 PM
Quote from: Rob260z on July 26, 2017, 06:49:32 PMRegarding the use of invoke.....I still feel dirty using it , lol. I'm a bit of a purist :)
As a purist, if you code in C, do you still use the original Kernighan & Ritchie compiler?
Don't listen to him Rob, some of us don't need our hands held  :biggrin:
Title: Re: Introduction + Silly Question :)
Post by: jj2007 on July 26, 2017, 09:22:52 PM
Quote from: sinsi on July 26, 2017, 08:20:22 PMDon't listen to him Rob, some of us don't need our hands held  :biggrin:

That's true! As a rule, if your IQ is well above 140 and your code never exceeds, say, a thousand lines, you can comfortably push your paras without the invoke macro. I've done the pushpushpop thing myself when I started assembler programming.
Title: Re: Introduction + Silly Question :)
Post by: hutch-- on July 26, 2017, 09:23:45 PM
Depends on how much typing you want to do, push/call notation works fine but its a bit cluttery with large amounts of API and similar HLL code. This is where "invoke" notation does the job better and makes your code more readable. The real action in 32 bit and later assembler is in writing algorithms and here pure mnemonic code is the way to go.
Title: Re: Introduction + Silly Question :)
Post by: Rob260z on July 27, 2017, 12:34:45 AM
With all due respect....and I honestly mean that. People usually use that term just before their about to patronize someone. But I've been lurking on here for a long time , and I understand that the people I'm talking to know much more about this subject than i'll ever know. Which is why I'm here !

But...honestly...what about pushing parameters to a procedure/function requires a high IQ ? . I find it a much easier syntax to read.

Maybe I dislike the C syntax.

Not here to pick a fight , just looking to learn from people far more knowledgeable than myself. A pretty easy task :)
Title: Re: Introduction + Silly Question :)
Post by: felipe on July 27, 2017, 12:47:08 AM
Quote from: Rob260z on July 26, 2017, 06:18:35 PM
Last time I did any programming I was using Boralnd Turbo Assembler.
So, you were a guy writing computer viruses!   :icon_mrgreen:
:lol: Just a joke.

Welcome to the forum.  :t
Title: Re: Introduction + Silly Question :)
Post by: hutch-- on July 27, 2017, 01:37:28 AM
Rob,

You will find the comment was offered in humour, not as an insult. There are those among us who can still code in HEX so don't feel you are left out of it coding external function calls with push/call notation. MASM can write very low level code if you know how to write it but it IS a MACRO assembler which is fully controlled by the assembler programmer so its more a case of packaging code you write yourself into a macro if it suits your purpose.

Many of the old fellas (me included) used to write code that looked like a Codeview debug screen but with the advent of Windows where you have no choice other to call system functions (Windows API calls), there are so many system defined equates that you would go NUTZ doing them as hex numbers as you would have to look them up in C notation in those truly horrible C header files.

Title: Re: Introduction + Silly Question :)
Post by: aw27 on July 27, 2017, 01:41:54 AM
Quote from: Rob260z on July 26, 2017, 06:49:32 PM
but I forgot to put a RET instruction
A lil problem, is like leaving home without putting the house keys in the pocket.  ;)
Title: Re: Introduction + Silly Question :)
Post by: jj2007 on July 27, 2017, 04:38:29 AM
Quote from: Rob260z on July 27, 2017, 12:34:45 AMBut...honestly...what about pushing parameters to a procedure/function requires a high IQ ? . I find it a much easier syntax to read

The ironic IQ remark was not addressed to you, really. As to the syntax, as Hutch wrote already, if your programs get longer, you will be drowned by really complicated API calls, but invoke checks if the parameters have the correct type, and if you haven't by accident added one push eax too much. Pushing by hand is really error-prone, you end up chasing bugs all the time. And yes, it's an old fight between those who accept that Masm is a macro assembler, and those who don't. My impression is that the purists are not very productive, but that's only an impression 8)
Title: Re: Introduction + Silly Question :)
Post by: coder on July 27, 2017, 05:16:24 AM
invoke and stuff are high-level macros. They may not be well-suited for beginners like Rob who wants to learn instructions and make parallel references to the Manuals, the debugger output and examples floating around the internet. invoke hides too many things crucial to understanding how instructions really work - the true fun of x86 assembly programming. But once he truly appreciates what's going on behind the scene, he can use invoke and other high-level stuff as he pleases. Rob is not a purist. He misused the terminology. He's an x86 Instruction Set learner.

Just my 2 cents. Welcome to forum, Rob. There are many bad guys in here, led by Hutch. You and I are the good guys  :dazzled:










Title: Re: Introduction + Silly Question :)
Post by: aw27 on July 27, 2017, 05:19:36 AM
Actually INVOKE is not a macro in Masm, it has been a directive, for the last 25 years or so. Then Microsoft transferred all MASM developers to the C# department leaving there just an old guy to change the version number and rebuild from time to time (probably with the assistance from some people from this forum ).
When it was time to compile MASM for 64-bit they could not make INVOKE and the Comparition directives to work, so they left these behind saying rough and hard to use is indeed a feature - some people in this forum agree with that 100%.
Title: Re: Introduction + Silly Question :)
Post by: coder on July 27, 2017, 05:59:28 AM
Quote from: aw27 on July 27, 2017, 05:19:36 AM
Actually INVOKE is not a macro in Masm, it has been a directive, for the last 25 years or so. Then Microsoft transferred all MASM developers to the C# department leaving there just an old guy to change the version number and rebuild from time to time (probably with the assistance from some people from this forum ).
When it was time to compile MASM for 64-bit they could not make INVOKE and the Comparition directives to work, so they left these behind saying rough and hard to use is indeed a feature - some people in this forum agree with that 100%.
You didn't just make that story up, did you?

I am not against high-level stuff. They have their own advantages especially in code readability. They fit very well in complex Win APIs environment. But some people just want to learn instructions without such API burden. I don't remember who, but someone told me that you should just throw away your AMD/Intel manuals once you're using MASM because it is highly likely that in a MASM source code, you could find only 20-30 percent 'instructions' while the rest are high-level statements, macros and directives. Look at this example:

.data
s1 db 'abcdefgh',0
s2 db 'abcd',0
.code
start:
.for (ebx = offset s1, edx = func(strlen,ebx) ¦ edx >= sizeof(s2) ¦ edx--)
    mov byte ptr [ebx+edx-1],0
.endfor
invoke printf,cstr(<"s1: %s",10,"s2: %s",10>),ebx,addr s2
output:
s1: abcdefgh
s2: abcd
...
mov ebx,offset s1
.for (edx = func(strlen,ebx) ¦ edx >= sizeof(s2) ¦ edx--)
output:
s1: abcd
s2: abcd


There's only one instruction in there, that is MOV instruction, out of the entire code. The rest are high-level stuff. This is not healthy for beginners wishing to learn X86 instruction sets (which is the heart of assembly programming anyway).
Title: Re: Introduction + Silly Question :)
Post by: felipe on July 27, 2017, 08:09:40 AM
Quote from: coder on July 27, 2017, 05:16:24 AM
invoke hides too many things crucial to understanding how instructions really work - the true fun of x86 assembly programming.
I understand this coder, but i really think that if were out there more O.Ses, probably it would be more fun to make programs than to understand just the basics of the architecture.  :greensml:

Quote from: coder on July 27, 2017, 05:16:24 AM
There are many bad guys in here, led by Hutch. You and I are the good guys  :dazzled:
:lol:
Title: Re: Introduction + Silly Question :)
Post by: jj2007 on July 27, 2017, 08:18:57 AM
Quote from: coder on July 27, 2017, 05:59:28 AMhigh-level stuff ... is not healthy for beginners wishing to learn X86 instruction sets (which is the heart of assembly programming anyway).

include \masm32\include\masm32rt.inc

.code
start:

  mov eax, 20
  lea ecx, [eax+4*eax]

  inkey str$(ecx), " is the result"
  exit

end start


Do you learn something when you see the two lines in the middle?
Will you learn something when you build and run this code?

Yes.

Will you learn better when somebody convinces you that you should not use this inkey and str$() high level stuff...?
Title: Re: Introduction + Silly Question :)
Post by: Rob260z on July 27, 2017, 08:23:41 AM
Cheers for the welcome folks :)

Sorry jj2007 , I shouldn't have taken offence , that was petty of me. It was 1am in the morning when I posted that. Busy trying to juggle my interest in Assembly ( wife would say obsession ) and my boring everyday work commitments :)

Coders example piece of code ! , ewwwwwww...yuck....lol. I must say it's this aspect of MASM that I initially wrestled with. But I realised that I don't have to use it , if I don't wish.

You are correct Coder , purist was the wrong terminology. It's the low level control that Assembly offers, that I really enjoy. It's about as close to having direct control of the CPU as I'm ever going to get.  But with that said , I'm also happy to use the WIN32 api. Why reinvent the wheel. It's all about compromise at the end of the day , the fine balance between it being fun or a grind.

Anyway, I should get back to double checking my RET's.........

Cheers,
Rob
Title: Re: Introduction + Silly Question :)
Post by: hutch-- on July 28, 2017, 10:18:41 AM
I have split this topic as I think Rob's original question has been answered and placed the following discussion in another thread so it is dealt with as discussion, not advice to the original poster.