News:

Masm32 SDK description, downloads and other helpful links
Message to All Guests

Main Menu

h2incx

Started by hutch--, September 09, 2016, 04:26:45 PM

Previous topic - Next topic

hutch--

I bothered to have a quick play with h2incx and while the output is a tangled mess, it may be useful for folks who want to use the Watcom forks if someone wanted to do enough work on them. If you can identify the structures, the data types appear to have been converted correctly and it would not take all that much work to convert them to intelligible assembler structures that can be read. Here is one as a test piece.

  IMAGE_OPTIONAL_HEADER64 STRUCT QWORD
    Magic                           dw ?
    MajorLinkerVersion              db ?
    MinorLinkerVersion              db ?
    SizeOfCode                      dd ?
    SizeOfInitializedData           dd ?
    SizeOfUninitializedData         dd ?
    AddressOfEntryPoint             dd ?
    BaseOfCode                      dd ?
    ImageBase                       dq ?
    SectionAlignment                dd ?
    FileAlignment                   dd ?
    MajorOperatingSystemVersion     dw ?
    MinorOperatingSystemVersion     dw ?
    MajorImageVersion               dw ?
    MinorImageVersion               dw ?
    MajorSubsystemVersion           dw ?
    MinorSubsystemVersion           dw ?
    Win32VersionValue               dd ?
    SizeOfImage                     dd ?
    SizeOfHeaders                   dd ?
    CheckSum                        dd ?
    Subsystem                       dw ?
    DllCharacteristics              dw ?
    SizeOfStackReserve              dq ?
    SizeOfStackCommit               dq ?
    SizeOfHeapReserve               dq ?
    SizeOfHeapCommit                dq ?
    LoaderFlags                     dd ?
    NumberOfRvaAndSizes             dd ?
    DataDirectory                   IMAGE_DATA_DIRECTORY IMAGE_NUMBEROF_DIRECTORY_ENTRIES dup <>
  IMAGE_OPTIONAL_HEADER64 ENDS

TouEnMasm

This structure is DWORD align not QWORD
extract from Winnt.sdk
Quote
;---- DEFALIGNMASM = DWORD ----------
IMAGE_OPTIONAL_HEADER64   STRUCT DEFALIGNMASM
   Magic WORD ?
   MajorLinkerVersion BYTE ?
   MinorLinkerVersion BYTE ?
   SizeOfCode DWORD ?
   SizeOfInitializedData DWORD ?
   SizeOfUninitializedData DWORD ?
   AddressOfEntryPoint DWORD ?
   BaseOfCode DWORD ?
   ImageBase REAL8 ?
   SectionAlignment DWORD ?
   FileAlignment DWORD ?
   MajorOperatingSystemVersion WORD ?
   MinorOperatingSystemVersion WORD ?
   MajorImageVersion WORD ?
   MinorImageVersion WORD ?
   MajorSubsystemVersion WORD ?
   MinorSubsystemVersion WORD ?
   Win32VersionValue DWORD ?
   SizeOfImage DWORD ?
   SizeOfHeaders DWORD ?
   CheckSum DWORD ?
   Subsystem WORD ?
   DllCharacteristics WORD ?
   SizeOfStackReserve REAL8 ?
   SizeOfStackCommit REAL8 ?
   SizeOfHeapReserve REAL8 ?
   SizeOfHeapCommit REAL8 ?
   LoaderFlags DWORD ?
   NumberOfRvaAndSizes DWORD ?
   DataDirectory IMAGE_DATA_DIRECTORY IMAGE_NUMBEROF_DIRECTORY_ENTRIES dup (<>)
IMAGE_OPTIONAL_HEADER64      ENDS

Fa is a musical note to play with CL

TWell

#2
Example was byte aligned as it is stucture in program image, there is no C alignment to handle.

How ml64 struct align actually works?
From here
QuoteThe first thing to notice scrolling this code is the structure:

MSG struct     
  hwnd              dq      ?
  message           dd      ?
  padding1          dd      ?      ; padding
  wParam            dq      ?
  lParam            dq      ?
  time              dd      ?
  pt                POINT   <>
  padding2          dd      ?      ; padding
MSG ends

It requires two paddings which the x86 declaration of the same structure didn't. The reason, in a few words, is that qword members should be aligned to qword boundaries (this for the first padding). The additional padding at the end of the structure follows the rule that: every structure should be aligned to its largest member. So, being its largest member a qword, the structure should be aligned to an 8-byte boundary.

nidud

#3
deleted

jj2007

Interesting, nidud :t

Another problem:MSG2 struct QWORD
  hwnd              dq      ? ; OxPT_DebugA -Zp8 ; same effect
  byte1             db      ?
  message           dd      ?
  ; byte2             db      ? ; when active, increases size by 8
  wParam            dq      ?
  lParam            dq      ?
  time              dd      ?
  pt                POINT   <>
MSG2 ends


wParam should be aligned 8, of course, so both versions should yield the same total size:
byte1+message=5  ; less than 8
byte1+message+byte2=6  ; less than 8

But it doesn't. What's the logic here?

nidud

#5
deleted

jj2007

Quote from: nidud on September 10, 2016, 03:15:59 AM
Think the logic here is that "message" is aligned 4

Right, that makes sense :t

rsala

Actually if you do not want to have problems with structures in WIN64 with ml64, align the structures to 16.

EC coder

jj2007

There is a part that I don't understand: option -Zp8 says structure alignment is 8 bytes, a QWORD. But even with this option set, a SMALL_RECT is 8 bytes long, i.e. none of the Top, Right, Bottom elements is QWORD-aligned:
SMALL_RECT STRUCT
  Left      WORD      ?
  Top       WORD      ?
  Right     WORD      ?
  Bottom    WORD      ?
SMALL_RECT ENDS


So what exactly does -Zp8?  ::)

Btw with ML64, the option seems to make it hang. I have to kill the process. HJWasm and AsmC work fine.

nidud

#9
deleted

jj2007

Yes. I found a clearer description in MSDN's Structure Alignment, Visual Studio 6.0 (my highlighting):
QuoteFor example, /Zp2 permits up to 1 byte of padding, /Zp4 permits up to 3 bytes of padding, and so on. The default pack size for Windows 3.x is 2, whereas the default for Win32 is 8. As a consequence:

    If you have specified a packing limit with /Zp or #pragma pack, you may not get the proper alignment (the default value) for Win32.

Question is why padding should be required in TWell's example if the default alignment is QWORD anyway*) :
Quote from: TWell on September 09, 2016, 06:42:37 PM
MSG struct     
  hwnd              dq      ?
  message           dd      ?
  padding1          dd      ?      ; padding  <<<<<< really needed? With align 8, wParam should start at a QWORD offset...
  wParam            dq      ?
  lParam            dq      ?
  time              dd      ?
  pt                POINT   <>
  padding2          dd      ?      ; padding
MSG ends

*) Tests confirm that ML64 uses DWORD alignment by default.

hutch--

Microsoft
---------

typedef struct tagMSG {
  HWND   hwnd;
  UINT   message;
  WPARAM wParam;
  LPARAM lParam;
  DWORD  time;
  POINT  pt;
} MSG, *PMSG, *LPMSG;

Vasily
------

IFDEF WIN32
   STRUCT_ALIGN   equ 4
ELSE
   STRUCT_ALIGN   equ 8
ENDIF

MSG STRUCT STRUCT_ALIGN
   hwnd      HWND ?
   message   DWORD ?
   wParam   WPARAM ?
   lParam   LPARAM ?
   time      DWORD ?
   pt      POINT<>
MSG ENDS

My own structure conversion tool.

  MSG STRUCT QWORD
    hwnd dq ?
    message dd ?
    wParam dq ?
    lParam dq ?
    time dd ?
    pt POINT <>
  MSG ENDS

My comments is that QWORD aligned structures for Win64 are safe and work well.

jj2007

Quote from: hutch-- on September 10, 2016, 06:49:18 AMMy comments is that QWORD aligned structures for Win64 are safe and work well.

One would indeed have to construct/find a case where -Zp8 would lead to wrong 32-bit code: M$ says default Win32 alignment is QWORD.

TWell

_WIN64 is standard for windows x64 headers, so why not use it?
ifdef rax
_WIN64 equ= 1
else
_WIN32 equ= 1
endif

ifdef _WIN64
echo _WIN64
else
echo _WIN32
endif
end


hutch--

I agree with Tim here, 8 byte alignment is the spec for Win 64, it works correctly with ML64, if anyone wants to try it the wrong way and fail, have PHUN !  :biggrin:

I started the topic to see if anyone wanted to use Japheth's h2incx to try and construct a working readable set of includes for the Watcom forks, I wonder why it changed to a debate about structures.