News:

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

What do you mean 'Immediate operand not allowed'

Started by Wez, January 07, 2008, 09:57:10 AM

Previous topic - Next topic

Wez

Hi, I'm trying to use a value from one table to reference a value in another table. This is the best I can come up with, but apparently you are not allowed to use an immediate operand (lpValue) where I have.
Can anyone tell me how your supposed to do this?

comment * «««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««

                             Build this with

                      >> Console Assemble & Link <<

; ««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««« *

;    .586
;    .model flat, stdcall
;    option casemap:none   ; case sensitive
   
; «««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««


    include \masm32\include\masm32rt.inc

    .data

t1 dd 2
t2 dd 7
t3 dd 1
t4 dd 8
t5 dd 3
t6 dd 5
t7 dd 6
t8 dd 4

table1 dd t1, t2, t3, t4, t5, t6, t7, t8

tt1 dd 80
tt2 dd 70
tt3 dd 60
tt4 dd 50
tt5 dd 40
tt6 dd 30
tt7 dd 20
tt8 dd 10

table2 dd tt1, tt2, tt3, tt4, tt5, tt6, tt7, tt8

    .code

; «««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««

;==============
; Local Macros
;==============

MyMacro MACRO MyVal
     LOCAL lpValue ; This is the operand causing the trouble
     lpValue = 0 ; I'm not sure if this is how you're supposed to define it, but it seems to work
             
     mov ebx, table1 + (MyVal - 1) * 4 ; Point to value in table1 (In this case, the 4th value)
        mov ebx, [ebx] ; Find value being pointed to (Should be 8)
        dec ebx ; Reduce it by 1
        mov lpValue, ebx ; Load pointer into lpValue

        mov eax, table2 + lpValue * 4 ; Point to value in table2 (Should be the 8th value)
        mov esi, [eax] ; Load value pointed at into esi (Should be 10)

        print str$(esi)
endm

; «««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««

start:

    MyMacro 4
    inkey
    exit

end start

Tedd

"t1", "t2", etc are labels not addresses, what you really mean is "OFFSET t1", "OFFSET t2", .... to give the addresses of those locations.
So, change 'table1' to "table1 dd OFFSET t1, OFFSET t2, OFFSET t3, ......" and the same for table2 :wink
No snowflake in an avalanche feels responsible.

Wez

Hi Tedd, I made those changes you suggested but it made no difference. It still comes up with 'Immediate operand not allowed'
Any other suggestions?
Also with the tables, is there a better way of doing things? I need to lookup values from the first table to be able to access values in 1 - 4 other tables, not just one as in the example code.

TIA
Wez

jdoe

Wez,

You can't move a register to a macro local.

mov lpValue, ebx ; Load pointer into lpValue


You can use a register instead. And I'm not sure about the way you set your tables.

Try this...

include \masm32\include\masm32rt.inc

.data

t1 equ 2
t2 equ 7
t3 equ 1
t4 equ 8
t5 equ 3
t6 equ 5
t7 equ 6
t8 equ 4

table1 dd t1, t2, t3, t4, t5, t6, t7, t8

tt1 equ 80
tt2 equ 70
tt3 equ 60
tt4 equ 50
tt5 equ 40
tt6 equ 30
tt7 equ 20
tt8 equ 10

table2 dd tt1, tt2, tt3, tt4, tt5, tt6, tt7, tt8

.code

MyMacro MACRO MyVal

        xor eax, eax

        mov ebx, [table1 + (MyVal - 1) * 4] ; Point to value in table1 (In this case, the 4th value)
        ;mov ebx, [ebx] ; Find value being pointed to (Should be 8)
        dec ebx ; Reduce it by 1
        mov eax, ebx ; Load pointer into lpValue

        mov esi, [table2 + eax * 4] ; Point to value in table2 (Should be the 8th value)
        ;mov esi, [eax] ; Load value pointed at into esi (Should be 10)

        print ustr$(esi)
        print chr$(13,10)

endm

start:

    MyMacro 4
    inkey
    exit

end start




ossama

as jdoe said, local macro variables are not used in run time but they are used only in compile time.

Wez

Awesome work, thanks for clearing that up for me, but I have a few more questions...

1. xor eax, eax      ; I see this quite often, is it faster / better than mov eax, 0?

2. print ustr$(esi)
    print chr$(13, 10)   ; Are these statements better than print str$(esi), 13, 10? Is there a full list of all these console statements and their meanings?

3. t1 equ 2
    t2 equ 7
    ...
    table1 dd t1, t2, ...

Is this how you're supposed to do tables? You said you weren't sure jdoe and I want to learn the right way if there is such a thing, I realise there are many ways to skin a cat but I just don't want to start any bad habits yet.

4. Is there a better way of doing tables? I want to be able to use statements like mov t10, 128 rather than mov ebx, [table1 + (10 - 1) * 4] > mov [ebx], 128

and...
5. Quite often I see @@, @B, and @F in different peoples code, I assumed @@ is a generic lable, @F means the next @@ lable forward and, @B means the next @@ lable back. Is this correct?


Once again thanks for the help.
Wez

ossama

Quote
1. xor eax, eax      ; I see this quite often, is it faster / better than mov eax, 0?
yes it is fast than mov eax,0

Quote
3. t1 equ 2
    t2 equ 7
    ...
    table1 dd t1, t2, ...

Is this how you're supposed to do tables? You said you weren't sure jdoe and I want to learn the right way if there is such a thing, I realise there are many ways to skin a cat but I just don't want to start any bad habits yet.

4. Is there a better way of doing tables? I want to be able to use statements like mov t10, 128 rather than mov ebx, [table1 + (10 - 1) * 4] > mov [ebx], 128
i am writing tables (or arrays) like this:

table1 dd 1,12,20,45,55,780


and if i wanted to get the 3rd value of the above table i use:

mov ecx,[table1+(3-1)*4]

or

lea eax,table1
add eax,(3-1)*4
mov ecx,[eax]


Quote
5. Quite often I see @@, @B, and @F in different peoples code, I assumed @@ is a generic lable, @F means the next @@ lable forward and, @B means the next @@ lable back. Is this correct?
yes it is correct.
my answers may be wrong,this is what i know
ragards OSSAMA

jdoe

Quote from: Wez on January 08, 2008, 09:30:51 PM
1. xor eax, eax      ; I see this quite often, is it faster / better than mov eax, 0?
2. print ustr$(esi)
    print chr$(13, 10)   ; Are these statements better than print str$(esi), 13, 10? Is there a full list of all these console statements and their meanings?
5. Quite often I see @@, @B, and @F in different peoples code, I assumed @@ is a generic lable, @F means the next @@ lable forward and, @B means the next @@ lable back. Is this correct?

Wez,

1) It's not better. In fact it is better in loops. Outside a loop, to make your code more readable "mov eax, 0" is just fine.
"xor eax, eax" is an optimization tips which is more suitable where speed makes a difference.

2) I'm not a big console program writer and masm32 macros user but for more informations you can always look at macros.asm in the macros folder of masm32

5) You're correct. Simple as that.

For tables, I'm not the right guy to give you good advices but the last post of ossama show how to read data in the table and the same can be done to write data in the table "mov [table1+(3-1)*4], ecx" or "mov dword ptr [table1+(3-1)*4], 128". For tables larger you can use multiple lines...

table1 dd 1,12,20,45,55,780
       dd 3,6,87,34,65,78
       dd 22,54,6,76,87,3



Wez

Excellent, thanks for the advice, I'll let you know how it all turns out.

Cheers
Wez