News:

Masm32 SDK description, downloads and other helpful links
Message to All Guests
NB: Posting URL's See here: Posted URL Change

Main Menu

Trying to understand TYPEDEF with PTR and without PTR

Started by StillLearningMasm, September 10, 2023, 05:14:35 PM

Previous topic - Next topic

StillLearningMasm

HELP! I am having a big problem understanding the TYPEDEF instruction when PTR is used.

Here is a fragment of code:
aword TYPEDEF word
.code
mov ax,word ptr [bx]
mov ax,aword ptr [bx]
I understand when this code is assembled that both of the instructions create the same code.
And they do.

Now look at this code fragment:
aword TYPEDEF PTR word
.code
mov ax,word ptr [bx] ;results in this code: mov ax,[bx]
mov ax,aword [bx] ;why does the assembler create this code: mov ax,[bx+number]
                  ;What does that number represent?
                  ;Why is the code: mov ax,[bx] not created?
                  ;In the definition of aword I specified ptr.
                  ;I expected aword to be the same as ptr word.
                  ;It is not. Then what is it?
mov ax,aword ptr [bx] ;Why does the assembler create a error message for this instruction?
When this code is assembled is "word ptr" the same as "ptr word"?
I thought if I used PTR in the TYPEDEF instruction then I would not need it in any
instruction that would normally need PTR.

Can anybody explain this?

Sincerely,
StillLearningMasm

Biterider

Hi StillLearningMasm

Quote from: StillLearningMasm on September 10, 2023, 05:14:35 PMHELP! I am having a big problem understanding the TYPEDEF instruction when PTR is used.
Don't panic, it's really easy. It took me a while at the beginning too  :cool:

What you are defining with
aword TYPEDEF PTR word is a pointer type to a word. Depending on the target bitness, it requires 4 or 8 bytes.

The problem with
mov ax, aword [ebx] is that the ptr between aword and [ebx] (32 bit) is missing. As a result, the compiler interprets this as an additional offset and creates [ebx + nn], where nn is the size of aword.

The last one
mov ax, aword ptr [ebx]fetches a pointer from [ebx] that does not fit into ax

Biterider

StillLearningMasm

Biterider,
Thanks for responding.

In your first example
mov ax, aword [ebx]
you said:
Quotethe ptr between aword and [ebx] (32 bit) is missing.
It is not missing that is why PTR was in the TYPEDEF that I created.
Or so I thought. So, if I have to still have a PTR in the example instruction
then what is the benefit of using PTR in the TYPEDEF instruction?

Also then what is the TYPEDEF instruction I created equivalent to???
Now even more confused.

StillLearning

Biterider

Hi StillLearningMasm
OK, the thing is that PTR has different meanings depending on where you use it.  :icon_idea:

If you write "TYPEDEF PTR", you create a new type of pointer to something, while mov YourType PTR [xxx] simply asks the assembler to treat [xxx] as being of type YourType.

There are many situations in which you can use a typed pointer.
For example, when you pass a pointer to a routine. When you use a typed pointer, the debugger shows you the entire contents of what the pointer points to. Another use is type checking, which is very useful when checking your code.

Biterider

StillLearningMasm

Biterider,

Thank you for your response.

So when I created the aword type I thought it was the same as WORD PTR [xxx].
From my testing I see that it is not.

is this rule for TYPEDEF correct:
When creating a pointer using PTR in TYPEDEF you NEVER include the size in the TYPEDEF
because it is NOT the same as (SIZE) PTR [xxx].

You never answered this question:
what is the TYPEDEF instruction I created equivalent to?

From the example I supplied:
mov ax,aword [bx]
it seems to be this:
mov ax,[bx+2] ;the 2 is from the size of word being 2


StillLearningMasm

HSE

Quote from: StillLearningMasm on September 11, 2023, 07:14:32 AMFrom the example I supplied:
mov ax,aword [bx]
it seems to be this:
mov ax,[bx+2] ;the 2 is from the size of word being 2

You are building a 16 bits program, in wich pointer have a size of 2 bytes.

There is a section for 16 bits programming in wich people used to this old kind of programming could be more specific.  :thumbsup:
Equations in Assembly: SmplMath

jj2007

Quote from: StillLearningMasm on September 11, 2023, 07:14:32 AMis this rule for TYPEDEF correct:
When creating a pointer using PTR in TYPEDEF you NEVER include the size in the TYPEDEF
because it is NOT the same as (SIZE) PTR [xxx].

Doesn't make any difference.

  Print Chr$("*** testing a typedef problem ***", 13, 10)
  aword TYPEDEF PTR word
  mov bx, Chr$(11h, 22h, 33h, 44h)
  mov ax, aword [bx]
  Print "AX 1=", Hex$(ax)
  Print
  mov ax, aword ptr [bx]
  Print "AX 2=", Hex$(ax)
  Print
  mov ax, word ptr [bx]
  Print "AX 3=", Hex$(ax)

*** testing a typedef problem ***
AX 1=4433    ** reads [bx][2]
AX 2=2211    ** reads [bx]
AX 3=2211    ** reads [bx]

@Zedd: yes, this is certainly 16-bit code, so move it, please :thumbsup:

Caché GB

Hi StillLearningMasm

My two cents.

TYPEDEF is an Operator which lets you create user-defined types

For example In C++

typedef float real4;

Now you can use real4 where ever you use float in C++

  real4 myfloat = (1.5f * 2.0f);  // instead of : float myfloat = (1.5f * 2.0f);

In assembly

float TYPEDEF real4

Now you can use float where ever you use real4

    local  MyReal:float

      mov  eax, FL4(1.5)
      mov  MyReal, eax

If you have a stucture say

TheStruct Struct
  Val1  dd ?
  Val2  dd ?
  Val3  dd ?
TheStruct ends

In a funtion's local space you can write

    local  pMyStruct:ptr TheStruct

However in the .data / .data? sections you cannot write

.data?

    pMyStruct ptr TheStruct ?  ; <- error A2008: syntax error : ptr

But you can do this

lpTheStruct typedef ptr TheStruct

.data

    pMyStruct lpTheStruct NULL

Also in C++ you may have seen this in a stucture declaration

typedef struct TheStruct
    {
    DWORD Val1;
    DWORD Val2;
    BYTE  *pVal;  // <- this
    } TheStruct;

You cannot do this in assembly

TheStruct struct
  Val1  dd ?
  Val2  dd ?
  pVal  ptr byte ?  ; <- error A2008: syntax error : ptr
TheStruct ends

But you can do this

PBYTE typedef ptr byte

TheStruct Struct
  Val1  dd ?
  Val2  dd ?
  pVal  PBYTE ?    ; a pointer to a byte / pointer to a byte array
TheStruct ends

Hope this helps
Caché GB's 1 and 0-nly language:MASM

zedd151

Hi Cache GB, the OP, StillLearningMasm was asking about TYPEDEF and TYPEDEF PTR for 16 bit code.
He may find your examples useful though.

This thread has been moved to the 16 bit DOS Programming board.

StillLearningMasm

jj2007,
When I asked this question:
Quoteis this rule for TYPEDEF correct:
When creating a pointer using PTR in TYPEDEF you NEVER include the size in the TYPEDEF
because it is NOT the same as (SIZE) PTR [xxx].

Your response was:
QuoteDoesn't make any difference.

Is that becasuse it is a pointer so any specified size given (in this case word) is ignored?
So the rule would be:
QuoteWhen creating a pointer using PTR in TYPEDEF you NEVER include the size in the TYPEDEF
because it ignored. (but no error occurs if you do.)

StillLearningMasm


Biterider

Hi StillLearningMasm
Quote from: StillLearningMasm on September 11, 2023, 07:14:32 AMYou never answered this question:
what is the TYPEDEF instruction I created equivalent to?

From the example I supplied:
mov ax,aword [bx]
it seems to be this:
mov ax,[bx+2] ;the 2 is from the size of word being 2

mov ax,aword [bx]
is assembled like

mov ax, [bx + sizeof(aword)]
Since aword is a pointer, in 16 bit it has a size of 2.
Based on the destination register (ax), the assembler assumes that the read value is a word.

Biterider

jj2007

Quote from: StillLearningMasm on September 11, 2023, 05:17:51 PMjj2007,
When I asked this question:
Quoteis this rule for TYPEDEF correct:
When creating a pointer using PTR in TYPEDEF you NEVER include the size in the TYPEDEF
because it is NOT the same as (SIZE) PTR [xxx].

Your response was:
QuoteDoesn't make any difference.

Is that becasuse it is a pointer so any specified size given (in this case word) is ignored?
So the rule would be:
QuoteWhen creating a pointer using PTR in TYPEDEF you NEVER include the size in the TYPEDEF
because it ignored. (but no error occurs if you do.)

Exactly, aword TYPEDEF PTR qword (in 16-bit code!!) produces the same results :thumbsup:

StillLearningMasm

To Anybody,
Using the same TYPEDEF with PTR how do I get masm to create the same code in 32-bit?
aword TYPEDEF PTR word ;result is dword size
.code
.386
mov ax,word ptr [bx]

This code is not the same:
mov ax, aword ptr [bx]
What do you do to make it the same?

Thanks for your help.

StillLearningMasm

jj2007

  aword TYPEDEF PTR
  mov ebx, Chr$(11h, 22h, 33h, 44h, 55h, 66h, 77h, 88h)
  mov eax, aword [ebx] ; mov eax, [ebx+4]
  Print "AX 1=", Hex$(ax)
  Print
  mov eax, aword ptr [ebx]
  Print "AX 2=", Hex$(ax)
  Print
  mov ax, word ptr [ebx]
  Print "AX 3=", Hex$(ax)

AX 1=6655
AX 2=2211
AX 3=2211

Biterider

Hi StillLearningMasm
Quote from: StillLearningMasm on September 12, 2023, 08:42:13 AMCode Select Expand
aword TYPEDEF PTR word ;result is dword size
.code
.386
mov ax,word ptr [bx]
This code is not the same:
mov ax, aword ptr [bx]
What do you do to make it the same?
In 16 bits, both variants result in the same value in ax, but in 32/64 bits you will have a problem. Using "mov ax, aword ptr [ebx]" will not work because you are loading a pointer (to a word) into ax, but ax is too short to hold it. In 32 bit you need eax or rax in 64 bit mode.
mov eax, aword ptr [ebx]     ;32 bit
mov rax, aword ptr [rbx]     ;64 bit

Biterider