Skip to content

Instantly share code, notes, and snippets.

@jeff123wang
Created April 6, 2022 15:44
Show Gist options
  • Save jeff123wang/3dd36a50684e72093f9e95c43a44dcb6 to your computer and use it in GitHub Desktop.
Save jeff123wang/3dd36a50684e72093f9e95c43a44dcb6 to your computer and use it in GitHub Desktop.
' https://stackoverflow.com/questions/64729347/getting-a-udt-from-a-longptr-in-vba
' There are three ways to assign UDT.
' 1. Simply use = assgiment
' 2. use copymemory.
' 3. Allocate memory as a swap space, transfer the value.
' 4. in VB, you can't dereference a UDT pointer directly like in C "->"
' 5. You need to use copymemory to a UDT variable. Then use "." to reference that variable.
Type IDT
id As Long
SomeOther As Long
End Type
Public Const HEAP_NO_SERIALIZE = &H1
Public Const HEAP_ZERO_MEMORY = &H8
Declare PtrSafe Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (Destination As Any, Source As Any, ByVal Length As LongPtr)
Declare PtrSafe Function HeapAlloc Lib "kernel32" Alias "HeapAlloc" (ByVal hHeap As LongPtr, ByVal dwFlags As Long, ByVal dwBytes As LongPtr) As LongPtr
Declare PtrSafe Function GetProcessHeap Lib "kernel32" Alias "GetProcessHeap" () As LongPtr
Type IDT
id As Long
SomeOther As Long
End Type
Public Const HEAP_NO_SERIALIZE = &H1
Public Const HEAP_ZERO_MEMORY = &H8
Declare PtrSafe Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (Destination As Any, Source As Any, ByVal Length As LongPtr)
Declare PtrSafe Function HeapAlloc Lib "kernel32" (ByVal hHeap As LongPtr, ByVal dwFlags As Long, ByVal dwBytes As LongPtr) As LongPtr
Declare PtrSafe Function GetProcessHeap Lib "kernel32" () As LongPtr
Sub main()
Dim SourceIDT As IDT
Dim HeapIDT As LongPtr ' swap variable
Dim TestIDT As IDT
SourceIDT.id = 1234
Debug.Print "SourceIDT.id = " & SourceIDT.id ' returns 1234
' you actually no need to use headalloc. UDT name is a pointer.
' Simple assignment method also works.
' This over complicated the problem
HeapIDT = HeapAlloc(GetProcessHeap(), HEAP_NO_SERIALIZE Or HEAP_ZERO_MEMORY, LenB(SourceIDT))
CopyMemory ByVal HeapIDT, SourceIDT, LenB(SourceIDT)
CopyMemory TestIDT, ByVal HeapIDT, LenB(SourceIDT)
Debug.Print "TestIDT.id = " & TestIDT.id ' expected 1234, but getting 0
' to do: free
End Sub
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment