News:

MASM32 SDK Description, downloads and other helpful links
MASM32.com New Forum Link
masmforum WebSite

Sorting Problem

Started by p30arena, April 12, 2012, 05:07:19 PM

Previous topic - Next topic

p30arena

Hi!!!
I don't know why but, when I use 'j' instead of 'cnt' the app crashes  ::)
at first I used 'cnt', 'i' and 'j', but I couldn't run the app so I used 'cnt' and 'dnt'
could u plz help me solve the problem??? :red

.386P
.MODEL flat,stdcall
option casemap:none

include \masm32\include\windows.inc
include \masm32\include\kernel32.inc
include \masm32\include\user32.inc
include \masm32\include\masm32.inc
include \masm32\include\oleaut32.inc
include \masm32\macros\macros.asm

includelib \masm32\lib\kernel32.lib
includelib \masm32\lib\user32.lib
includelib \masm32\lib\masm32.lib
includelib \masm32\lib\oleaut32.lib
.DATA
    msg db  "Hello, Windows 8!!!",0
    buff    DWORD   100 dup(?)
    list    DWORD   7,2,6,4,5,3,1
    lsz     =       ($-list)/4
    cnt     DWORD   0
    dnt     DWORD   0
.CODE
MAIN PROC
    ;invoke nrQsortA, ADDR list, lsz
    call SORT
    mov cnt,0
start:
    mov     ecx, cnt
    invoke  dwtoa, [list+ecx*4], ADDR buff
    invoke  MessageBoxA,0,ADDR buff,ADDR msg,MB_OK
    inc     cnt
    cmp     cnt,lsz
    jne start
    invoke  ExitProcess,0
MAIN ENDP
SORT PROC
    fori:
    push    dnt+1
    pop     cnt
    forj:
    ;--------------------------
    mov esi, dnt
    mov eax, [list+esi*4]
    mov esi, cnt
    mov ebx, [list+esi*4]
    cmp eax, ebx
    jg  continue
    xchg eax,ebx
    mov esi, dnt
    mov [list+esi*4], eax
    mov esi, cnt
    mov [list+esi*4], ebx
    ;--------------------------
    continue:
    inc cnt
    cmp cnt,lsz
    jl forj
    inc dnt
    cmp dnt,lsz
    jl fori
    ret
   
SORT ENDP
END MAIN

dedndave

seems to work ok...
.386P
.MODEL flat,stdcall
option casemap:none

include \masm32\include\windows.inc
include \masm32\include\kernel32.inc
include \masm32\include\user32.inc
include \masm32\include\masm32.inc
include \masm32\include\oleaut32.inc
include \masm32\macros\macros.asm

includelib \masm32\lib\kernel32.lib
includelib \masm32\lib\user32.lib
includelib \masm32\lib\masm32.lib
includelib \masm32\lib\oleaut32.lib
.DATA
    msg db  "Hello, Windows 8!!!",0
    buff    DWORD   100 dup(?)
    list    DWORD   7,2,6,4,5,3,1
    lsz     =       ($-list)/4
    j       DWORD   0
    dnt     DWORD   0
.CODE
MAIN PROC
    ;invoke nrQsortA, ADDR list, lsz
    call SORT
    mov j,0
start:
    mov     ecx, j
    invoke  dwtoa, [list+ecx*4], ADDR buff
    invoke  MessageBoxA,0,ADDR buff,ADDR msg,MB_OK
    inc     j
    cmp     j,lsz
    jne start
    invoke  ExitProcess,0
MAIN ENDP
SORT PROC
    fori:
    push    dnt+1
    pop     j
    forj:
    ;--------------------------
    mov esi, dnt
    mov eax, [list+esi*4]
    mov esi, j
    mov ebx, [list+esi*4]
    cmp eax, ebx
    jg  continue
    xchg eax,ebx
    mov esi, dnt
    mov [list+esi*4], eax
    mov esi, j
    mov [list+esi*4], ebx
    ;--------------------------
    continue:
    inc j
    cmp j,lsz
    jl forj
    inc dnt
    cmp dnt,lsz
    jl fori
    ret
   
SORT ENDP
END MAIN

p30arena

yes its ok when I work with 2 DWORDs but when it reaches 3 , like i,j,cnt that weird crash happens ::)

qWord

Quote from: p30arena on April 12, 2012, 05:07:19 PM    fori:
    push    dnt+1
    pop     cnt
 

this is interpreted as:
push DWORD ptr ((OFFSET dnt) +1 )
pop cnt

what you propably want is:
mov eax,dnt
add eax,1
mov cnt,eax
FPU in a trice: SmplMath
It's that simple!

jj2007

There are a number of problems, and I won't have the time to go through it, so this is just a hint:

   push    dnt+1  ; you are pushing the content of address cnt PLUS ONE. That is likely to be garbage
What you want is
  mov eax, dnt
  inc eax
  push eax


Furthermore, your app does not start at start: but rather at MAIN, since the code ends with END MAIN.

And, by the way: Welcome to the Forum :thumbu

p30arena

Thanks Guys Problem Solved!
I'm studying Assembly from the book "Assembly Language for x86 Processors"
you recommend a better reference ?

Here's the correct code : :U

.386P
.MODEL flat,stdcall
option casemap:none

include \masm32\include\windows.inc
include \masm32\include\kernel32.inc
include \masm32\include\user32.inc
include \masm32\include\masm32.inc
include \masm32\include\oleaut32.inc
include \masm32\macros\macros.asm

includelib \masm32\lib\kernel32.lib
includelib \masm32\lib\user32.lib
includelib \masm32\lib\masm32.lib
includelib \masm32\lib\oleaut32.lib
.DATA
    msg db  "Hello, Windows 8!!!",0
    buff    DWORD   100 dup(?)
    list    DWORD   7,2,6,4,5,3,1
    lsz     =       ($-list)/4
    cnt     DWORD   0
    i       DWORD   0
    j       DWORD   0
.CODE
MAIN PROC
    ;invoke nrQsortA, ADDR list, lsz
    call SORT
    mov cnt,0
start:
    mov     ecx, cnt
    invoke  dwtoa, [list+ecx*4], ADDR buff
    invoke  MessageBoxA,0,ADDR buff,ADDR msg,MB_OK
    inc     cnt
    cmp     cnt,lsz
    jne start
    invoke  ExitProcess,0
MAIN ENDP
SORT PROC
    fori:
    mov eax,i
    inc eax
    mov j,eax
    forj:
    ;--------------------------
    mov esi, i
    mov eax, [list+esi*4]
    mov esi, j
    mov ebx, [list+esi*4]
    cmp eax, ebx
    jg  continue
    xchg eax,ebx
    mov esi, i
    mov [list+esi*4], eax
    mov esi, j
    mov [list+esi*4], ebx
    ;--------------------------
    continue:
    inc j
    mov eax,lsz
    dec eax
    cmp j,eax
    jl forj
    inc i
    mov eax,lsz
    sub eax,2
    cmp i,eax
    jl fori
    ret
   
SORT ENDP
END MAIN

dedndave

welcome to the forum   :U

the best assembler reference is right here   :P

zemtex

Just a tip: Use as many instructions as you can, try to vary them as much as possible, forget about optimizations. When you get familiar with most instructions, you can then start to optimize your programs. It is better to learn all instructions first. That doesn't mean you can't start to optimize programs if you have the know-how and it is blatantly obvious that it can be done.
I have been puzzling with lego bricks all my life. I know how to do this. When Peter, at age 6 is competing with me, I find it extremely neccessary to show him that I can puzzle bricks better than him, because he is so damn talented that all that is called rational has gone haywire.

hutch--

Here is a simple correction for you, it changed the EBX and ESI registers to ECX and EDX. There is a reason for this, it is compliance to the Intel ABI, the rules of register preservation which Microsoft used with 32 bit Windows. If you want to use EBX ESI EDI in a proc, you preserve them then restore them at the end using PUSH  POP.

It is worth getting used to this quickly so you don't learn bad habits that stop your code from being reliable.
Download site for MASM32      New MASM Forum
https://masm32.com          https://masm32.com/board/index.php

p30arena

Quote from: hutch-- on April 13, 2012, 12:57:32 AM
Here is a simple correction for you, it changed the EBX and ESI registers to ECX and EDX. There is a reason for this, it is compliance to the Intel ABI, the rules of register preservation which Microsoft used with 32 bit Windows. If you want to use EBX ESI EDI in a proc, you preserve them then restore them at the end using PUSH  POP.

It is worth getting used to this quickly so you don't learn bad habits that stop your code from being reliable.

you mean this?

PUSH EBP,EBX,EDI,ESI
.
.                       ;my code
.
POP ESI,EDI,EBX,EBP

dedndave

well - you might want to use the routine to sort more than just one list
so, let's pass it the address of the list and the number of dwords to sort
the assembler will do some things for you to help and to make the code easier to read
it will set up a stack frame, using EBP, and preserve EBP for you
we don't normally use EBP as a general register inside the routine, but it can be done
instead, it is used to access the passed parameters and local variables
EBX, ESI, and EDI are your responsibility, in a way - if you use them, preserve them

we start by prototyping the routine (near the beginning of the program)
MySort  PROTO   :DWORD,:DWORD
this tells the assembler that 2 dword parameters are required in an INVOKE
you can be more precise about the type of parameters passed
but it makes little difference, as the assembler really doesn't know one dword type from another   :P
MySort  PROTO   :LPVOID,:UINT

in the PROC line, you can tell the assembler to preserve registers and to type the passed parameters
MySort  PROC USES EBX ESI EDI lpList:LPVOID,uQuantity:UINT

        LOCAL   TempVar1:DWORD
        LOCAL   TempVar2:DWORD

        mov     esi,lpList
        mov     ecx,uQuantity
        xor     edx,edx
        mov     TempVar1,edx
        mov     TempVar2,edx
;
;
;
        ret

MySort  ENDP


to call the function...
        INVOKE  MySort,offset MyList,lengthof MyList

for more information about how the assembler handles the stack frame...
http://www.masm32.com/board/index.php?topic=15307.msg124847#msg124847

http://www.masm32.com/board/index.php?topic=14381.msg114921#msg114921

you can also read the documentation in the MASM reference manual....

http://www.4shared.com/file/39MdNf_v/MASMProgGuide.html

hutch--

p30arena,

Not exactly, in MASM notation using a PROC you would do this if you were going to use EBX ESI and EDI.


    push ebx
    push esi
    push edi

  ; your code here

    pop edi
    pop esi
    pop ebx


If you are writing a procedure without a stack frame you must also take note of what you do with EBP and ESP.
Download site for MASM32      New MASM Forum
https://masm32.com          https://masm32.com/board/index.php


p30arena

Thank you very much for your help "dedndave" and "hutch--" and other nice guys that helped me and i didn't mention  :bg
i jumped to the code when i started reading the book  :lol, i think i should jump back to the beginning, i have missed a lot of info  ::) :bg