Jump to content

Pointer to a pointer


Recommended Posts

Local $oDict_A = ObjCreate( "Scripting.Dictionary" )

to make copy of $oDict_A object we do:
  > Local $oDict_B = $oDict_A
  > or can use Ptr($oDict_A) to make copy $oDict_A object.

Now Ptr($oDict_A) method work fine if used within same script.

 

Server.au3

__Server_script()
Func __Server_script()
    ConsoleWrite('__Server_script' & @crlf)
    Local $o_PID = WinGetProcess("AutoIt v3")
    Local $o_Buffer = 'ptr'
    Local $oDict_A = ObjCreate( "Scripting.Dictionary" )
    Local $o_Struct = DllStructCreate($o_Buffer)
    DllStructSetData($o_Struct, 1, $oDict_A)

    ConsoleWrite("DllStruct_Size ->     " & DllStructGetSize($o_Struct) & @CRLF)
    ConsoleWrite("DllStruct_Ptr ->  " & DllStructGetPtr($o_Struct) & @CRLF)
    ConsoleWrite("$oDict_A ptr ->   " & DllStructGetData($o_Struct, 1) & @tab & Ptr($oDict_A) & @CRLF)

    RunWait( @AutoItExe & " /AutoIt3ExecuteScript " & '"Client.au3" ' & $o_PID & " " & $o_Buffer & " " & DllStructGetPtr($o_Struct))

    $o_Struct = 0
    $oDict_A = 0
EndFunc

Client.au3

__Child_script(Number($CmdLine[1]), $CmdLine[2], $CmdLine[3])
Func __Child_script($o_PID, $o_Buffer, $o_Ptr)
    MsgBox( 0, "Client", "Client Started [ __Child_script() ]" )

    Local $hHandle = DllCall("kernel32.dll", 'int', 'OpenProcess', 'int', 0x1F0FFF, 'int', 1, 'int', $o_PID)
    If @error Then
        MsgBox( 0, "Client", "+++ Failed to open process memory for FULL_ACCESS. Error is " & @error )
        Exit
    EndIf

    Local $oResultA = __ReadMemory_Address($hHandle, $o_Ptr, $o_Buffer)
    If Not @error Then
        ;~ get exact =>  __Server_script() $oDict_A pointer
        ;~ but it will not work if try to do dereferencing.....
        ;~ need actual address of __Server_script() $oDict_A pointer
        MsgBox( 0, "Client", VarGetType($oResultA) & @tab & ($oResultA))
    EndIf

    DllCall("kernel32.dll", "int", "CloseHandle", "hwnd", $hHandle[0])
    MsgBox( 0, "Client", "Client.... End" )
EndFunc

; #FUNCTION# ========================================================================
; Name ..........: __ReadMemory_Address
; ===================================================================================
Func __ReadMemory_Address($hHandle, $o_Ptr, $o_Buffer = 'Dword')
    Local $sStruct = DllStructCreate($o_Buffer)     ; ptr   Dword
    DllCall("kernel32.dll", 'int', 'ReadProcessMemory', _
                            'int', $hHandle[0], _
                            'int', Number($o_Ptr), _
                            'ptr', DllStructGetPtr($sStruct), _
                            'int', DllStructGetSize($sStruct), _
                            'int', '')
    If @error Then
        MsgBox( 0, "@error", "+++ Failed to Read Process Memory. Error is " & @error )
        Return SetError(1)
    EndIf

    Local $vRet = DllStructGetData($sStruct, 1)
    If @error Then
        MsgBox( 0, "@error", "+++ Failed to Get data from $sStruct. Error is " & @error )
        Return SetError(1)
    EndIf

    $sStruct = 0
    Return $vRet
EndFunc

 

problem is how to get correct ptr address of $oDict_A from __Child_script()

ReadProcessMemory return exact pointer value of $oDict_A of __Server_script() which will not work if try to do dereferencing from __Child_script()

So any method to obtain the address pointing towards __Server_script() $oDict_A object.

Link to comment
Share on other sites

Quote

Quoting the E4A manual, section "Work Environment":

Although the base offset of a memory-mapped region is virtualised per process (and thus has a different virtual base address for each process that maps it), the relative offsets of individual allocations therein remain fixed. In combination with process IDs (PIDs), this allows for globally unique identification of each virtual memory allocation and defining an associated global mutex (an "in-use" flag), so numerous processes can negotiate writing to it in turn. (...)

 As soon as a first process has initialised its own virtual memory, other processes may gain direct read/write access to it by calling _HighMem_MapExternalMemory ( $PID ), with $PID being the process ID of the first process. (...)

Thereafter, the first process needs to communicate the relevant specs (allocated size) plus its relative offset to its own base address (as a 64-bit pointer-type variable). Other processes can then(...)  re-map this region into their PID-specific re-mapped workspace.

TLDR:

  • process A allocates virtual memory region A at base offset A_base, and creates structs/objects therein with address ptr
  • (ptr minus A_base) is the relative address rel_ptr of target struct/object within region A
  • process B needs to remap region A into its own virtual memory with base offset B_base
  • given A_base's (relative) virtual address within B_base, add rel_ptr to access A's shared struct/object from process B
  • for this to work, A needs to first parse to B  A_base's absolute address, the rel_ptr, and the struct/object size (and layout)
  • NB if both processes may write to the same region, you'll need a mutex to negotiate access and avoid race conditions

Check out my HighMem UDF, in particular the test example scripts and functions:

  • _HighMem_PID2BaseOffset( PID )
  • _HighMem_MapExternalMemory(PID)
  • _HighMem_OffsetAbsolute2Relative (offset,PID) / _HighMem_OffsetRelative2Absolute(offset,PID)
  • _HighMem_AllocateExternal(offset, size, unit)
Edited by RTFC
Link to comment
Share on other sites

Link to comment
Share on other sites

@RTFC 

HighMem UDF contains lot of coding so it's going to take time to study it.
it will be easier for me to understand the concept if you modified the above example :D.

 

@Nine

yes I know using ROT objects we can share object between processes (thanks to @LarsJ).
but I want to know how to Read Memory to get Server.au3 $oDict_A ptr address from Client.au3.

with help of RtlMoveMemory we can get object out of a pointer.
only tested with Scripting.Dictionary object so not sure about other com object.


 

Edited by jugador
Link to comment
Share on other sites

Very cute, jugador.:P

Luckily for you, the Highmem UDF comes with the simplest-possible example scripts that already do almost exactly what you request, except sharing a struct rather than an object. So edit those to create your object instead of my example struct, get its pointer, and Bob's your uncle.

Edited by RTFC
Link to comment
Share on other sites

Ok, I was able to copy scripting.dictionnary from one object to the other using RtlMoveMemory, but there is one major remaining challenge.  How to know the length of the object in terms of bytes ?  Lets just say you have 100 keys and items, there is no way that I know of to evaluate the size of the memory occupied by the object.

 

Link to comment
Share on other sites

@Nine I don't know any other language except Autoit.
so can you explain....
How pointer to object work in c or any other language?
while using C How we know the length of the object in terms of bytes ?

 

@Nine do You know how to use cheat engine?
Can we view __Server_script() $oDict_A object address and offset value using cheat engine?

If yes... can you show what modification needed in client script.

Link to comment
Share on other sites

You're overcomplicating matters, @jugador, It's really not that hard; see attached.:rolleyes:

HighMem4Objects.7z

Note: you don't need to know the object's size (which is hard; depending as it does on alignment/padding, v-tables, and inheritance) to get a reference to it elsewhere. I've included AutoItObject v.1.2.8.3 in the zip for convenience (from here), as the Server example script (A) uses it to un/register  the dictionary object.

Start HighMem_TestDict_A.au3 first and wait for the MsgBox to appear that tells you to start HighMem_TestDict_B.au3. If all goes well, both scripts then have access to the same dictionary object (but please use Highmem's mutex functions to avoid race conditions).

Note: you'll have to launch each script in a separate instance of Scite (you may have to edit the Scite Properties beforehand to set check.if.already.open=0).

Edited by RTFC
Link to comment
Share on other sites

@RTFC thanks for the code.
but frankly I am having hard time understanding what you did with the code(HighMem UDF).
I use @LarsJ Rot object Udf for server/client connectivity.


Now we do pass String using DllStructure to different script and use ReadProcessMemory to extract the string.
So my point creating this thread to know can we pass object pointer to different script using the same technique.


Quite evident that I don't process knowledge about all this :P.
So making wild guess that it possible to dereference object pointer using ReadProcessMemory while creating this thread.

Like @Manko use ReadProcessMemory in _WinAPI_GetCommandLineFromPID
https://www.autoitscript.com/forum/topic/88214-_winapi_getcommandlinefrompid-from-any-process/

or by using _MemInit + _MemWrite

 

May be none of the above method will work as pointer is not valid in another process. I don't know.

I think.... It's good to have different working method :D.

Anyway thanks for showing interest @RTFC & @Nine.
@Nine so if you don't want to help that's fine.

Edited by jugador
Link to comment
Share on other sites

20 hours ago, jugador said:

as pointer is not valid in another process

Pointers are perfectly valid in another process as long as the original referenced memory is mapped into that of the current process, and the pointer itself translated w.r.t. the current process's base memory pointer (as I explained before). Moreover, the provided test scripts show that not only can the 2nd process get a valid pointer to an object created elsewhere, but also (via ROT ID, if 1st process registered it with unique name) gain access to  the object itself, outside of the process that created it. Apparently you're under the mistaken assumption that HighMem is just for IPC; it's not; it's for managing large chunks of virtual memory in a multi-processing context.

Edited by RTFC
Link to comment
Share on other sites

  • 2 weeks later...

is this the correct way to get offset value of Scripting.Dictionary object 

Func __ExampleA()
    Local $o_PID = WinGetProcess("AutoIt v3")
    ConsoleWrite("PID-> " & $o_PID & @CRLF)

    Local $hWnd = WinGetHandle("AutoIt v3")
    ConsoleWrite("handle-> " & $hWnd & @CRLF)

    Local $oDict_A = ObjCreate( "Scripting.Dictionary" )
    Local $oDict_ptr = ptr($oDict_A)

    Local $o_BaseAddress = __GetBaseAddress($o_PID, 'autoit3.exe')
    Local $o_offset = $oDict_ptr - $o_BaseAddress
EndFunc

 

Edited by jugador
Link to comment
Share on other sites

#include <WinAPISys.au3>

Local $tmp=_WinAPI_GetSystemInfo()
Local $BaseAddress = Ptr($tmp[2])   ; "Lowest-Accessible Memory Address"

You didn't specify what __GetBaseAddress() actually does. With the above it should work (for the current PID).

(the Highmem UDF of course takes care of all this low-level stuff for you automatically...)

Edited by RTFC
Link to comment
Share on other sites

__GetBaseAddress get the current Module Base Address that is "AutoIt v3" in this case.

Result....

ptr(Scripting.Dictionary)   = 0x026BED08
__GetBaseAddress(AutoIt v3) = 0x00DF0000
_WinAPI_GetSystemInfo()[2]  = 0x00010000

1) ptr(Scripting.Dictionary) - __GetBaseAddress(AutoIt v3)  = 0x018CED08
2) ptr(Scripting.Dictionary) - _WinAPI_GetSystemInfo()[2]   = 0x026AED08

if this the correct procedure to get offset value then which one is more convenient to use type 1 or 2 ?

Link to comment
Share on other sites

That would depend entirely on what you wish to do with it afterwards, but try option 1 first. If you study _HighMem_MapExternalMemory(), you see that I pre-allocate a (uniquely, predictably) PID-named region in virtual memory first, which allows another process (if it knows the PID of the original process) to open it and remap it within their own (virtual) memory space. Anything allocated within that region is then also accessible to the other process; it just has to be remapped in the new context. Look into _WinAPI_CreateFileMapping, _WinAPI_OpenFileMapping, and _WinAPI_MapViewOfFile for more info (Note: these function names are confusing, because we're mapping virtual memory with it, not a file).

Link to comment
Share on other sites

@RTFC

As I want to access object pointer without using Rot object I disable this part of HighMem_TestDict_A.au3

; by def, a mutex name is unique
; $uniqueObjectName=_Highmem_GetMutexName( $pAddress3 )
; _AutoItObject_RegisterObject( Ptr( $oDict_A ), $uniqueObjectName )

HighMem_TestDict_B.au3 failed to convert $oResultA to object.

Code.....

HighMem_TestDict_A.au3

; Open HighMem_TestDict_A.au3 and HighMem_TestDict_B.au3 in
; two separate instances of Scite, and start script A, which will display a message box
; when you can start script B. Both will eventually terminate automatically.
; NB Changing memory allocation contents are written to console only.

; enable this line if you wish to allocate more than 1.5 GB of virtual memory (see _HighMem_StartUp() call below)
;#AutoIt3Wrapper_UseX64=Y

#NoTrayIcon
#include ".\HighMem.au3"
;#include ".\AutoitObject\AutoitObject.au3"
;_AutoItObject_StartUp()

Global $runningTimeInSec=20
Global $timeoutInMs=250 ; max 1/4 second for obtaining mutex
Global $inifile=StringTrimRight(@ScriptName,6) & ".ini"

Global $struct1SizeinBytes=512
Global $lastbyte1=$struct1SizeinBytes-1
Global $struct2SizeinBytes=1024
Global $lastbyte2=$struct2SizeinBytes-1
Global $tagValue=123    ; byte value (0-255)

; initialise _HighMem
$_HighMem_Testmode=False        ; F: enable actual changes in RAM; (T: dummy mode)
Global $_HighMem_Verbose=True   ; show initialisation error msgs
_HighMem_StartUp(1,"GB")    ; if this exceeds free virtual memory, then the max-available is allocated
If @error Then Exit(@error)

;_HighMem_ShowSpecs()

;____________________________________________________________________________________
; first we create two HighMem allocations and map a struct to each

ConsoleWrite("Allocating 1st struct of "&$struct1SizeInBytes&" bytes; please wait..." & @CRLF)
$pAddress1=_HighMem_Allocate($struct1SizeinBytes,"B")
If @error Then
    ConsoleWrite("Error: Allocation failed with error: " & @error & @CRLF)
    Exit(1) ;   on Exit, _HighMem_CleanUp() is automatically invoked
EndIf

Global $tBuffer1 = DllStructCreate('byte['&$struct1SizeinBytes&']',$pAddress1)
If @error Then
    ConsoleWrite("Error: struct creation failed with error: " & @error & @CRLF)
    Exit(1) ;   on Exit, _HighMem_CleanUp() is automatically invoked
EndIf

; test struct1 I/O
ConsoleWrite("Struct ptr: " & DllStructGetPtr($tBuffer1) & @CRLF)
ConsoleWrite("Struct size: " & DllStructGetSize($tBuffer1) & @CRLF)
ConsoleWrite("Setting last value: " & DllStructSetData($tBuffer1,1,$tagValue,$lastbyte1) & @CRLF)
ConsoleWrite("Getting last value: " & DllStructGetData($tBuffer1,1,$lastbyte1) & @CRLF)
; we're not using this one for shared I/O here, it's just to illustrate
; the second allocation's non-zero relative offset (to be parsed to script B)


; second struct size is different from first, and has non-zero relative offset
ConsoleWrite("Allocating 2nd struct of "&$struct2SizeInBytes&" bytes; please wait..." & @CRLF)
$pAddress2=_HighMem_Allocate($struct2SizeinBytes,"B")
If @error Then
    ConsoleWrite("Error: Allocation failed with error: " & @error & @CRLF)
    Exit(1) ;   on Exit, _HighMem_CleanUp() is automatically invoked
EndIf

Global $tBuffer2 = DllStructCreate('byte['&$struct2SizeInBytes&']',$pAddress2)
If @error Then
    ConsoleWrite("Error: struct creation failed with error: " & @error & @CRLF)
    Exit(1) ;   on Exit, _HighMem_CleanUp() is automatically invoked
EndIf

; test struct2 I/O
ConsoleWrite("Struct ptr: " & DllStructGetPtr($tBuffer2) & @CRLF)
ConsoleWrite("Struct size: " & DllStructGetSize($tBuffer2) & @CRLF)
ConsoleWrite("Setting last value: " & DllStructSetData($tBuffer2,1,$tagValue,$lastbyte2) & @CRLF)
ConsoleWrite("Getting last value: " & DllStructGetData($tBuffer2,1,$lastbyte2) & @CRLF)

;###########################################################################
; dictionary test

    Global $struct3SizeinBytes=8
    $pAddress3=_HighMem_Allocate($struct3SizeinBytes,"B")
    If @error Then
        ConsoleWrite("Error: Allocation failed with error: " & @error & @CRLF)
        Exit(1) ;   on Exit, _HighMem_CleanUp() is automatically invoked
    EndIf

    Global $tBuffer3 = DllStructCreate('ptr',$pAddress3)
    If @error Then
        ConsoleWrite("Error: struct creation failed with error: " & @error & @CRLF)
        Exit(1) ;   on Exit, _HighMem_CleanUp() is automatically invoked
    EndIf

    Local $oDict_A = ObjCreate( "Scripting.Dictionary" )
    DllStructSetData($tBuffer3, 1, Ptr($oDict_A))

    ; by def, a mutex name is unique
;   $uniqueObjectName=_Highmem_GetMutexName( $pAddress3 )
;   _AutoItObject_RegisterObject( Ptr( $oDict_A ), $uniqueObjectName )

    ConsoleWrite(VarGetType($oDict_A) & @TAB &  "IsObj = " & IsObj($oDict_A) & @CRLF)
    ConsoleWrite("DllStruct_Size -> " & DllStructGetSize($tBuffer3) & @CRLF)
    ConsoleWrite("DllStruct_Ptr ->  " & DllStructGetPtr($tBuffer3) & @CRLF)
    ConsoleWrite("oDict_A ORIGINAL ptr ->   " & Ptr($oDict_A) & @TAB & "(PID = " & @AutoItPID & ")" & @CRLF)

;###########################################################################

;_HighMem_ShowAllocations(1)    ; 1: sorted by offset (Ptr)
;____________________________________________________________________________________

; Now we need to tell script B about these allocations
Global $relativeOffset1=_HighMem_OffsetAbsolute2Relative($pAddress1)
Global $relativeOffset2=_HighMem_OffsetAbsolute2Relative($pAddress2)
Global $relativeOffset3=_HighMem_OffsetAbsolute2Relative($pAddress3)

; simple way to convey allocation specs to 2nd process
IniWrite($inifile,"PID","PID",@AutoItPID)

IniWrite($inifile,"ALLOC1","sizeInBytes",$struct1SizeinBytes)
IniWrite($inifile,"ALLOC1","relativeOffset",$relativeOffset1)

IniWrite($inifile,"ALLOC2","sizeInBytes",$struct2SizeinBytes)
IniWrite($inifile,"ALLOC2","relativeOffset",$relativeOffset2)

IniWrite($inifile,"ALLOC3","sizeInBytes",$struct3SizeinBytes)
IniWrite($inifile,"ALLOC3","relativeOffset",$relativeOffset3)

MsgBox(64,@ScriptName,"You can start the B-script now.",3)

Local $tstart=TimerInit()
While FileExists($inifile) And TimerDiff($tstart)/1000<$runningTimeInSec
    Sleep(500)
WEnd
if FileExists($inifile) Then FileDelete($inifile)

_HighMem_CleanUp()

;_AutoItObject_UnregisterObject($uniqueObjectName)
;_AutoItObject_Shutdown()

 

HighMem_TestDict_B.au3

; Open HighMem_TestDict_A.au3 and HighMem_TestDict_B.au3 in
; two separate instances of Scite, and start script A, which will display a message box
; when you can start script B. Both will eventually terminate automatically.
; NB Changing memory allocation contents are written to console only.

; enable this line if you wish to allocate more than 1.5 GB of virtual memory (see _HighMem_StartUp() call below)
;#AutoIt3Wrapper_UseX64=Y

#NoTrayIcon
#include ".\HighMem.au3"

Global $runningTimeInSec=20
Global $timeoutInMs=250 ; max 1/4 second for obtaining mutex
Global $inifile=StringTrimRight(@ScriptName,6) & ".ini"

Global $tagValue=234    ; byte value (0-255)

;____________________________________________________________________________________
If Not FileExists($inifile) Then
    msgbox(16,@ScriptName,"Please start the A-script first, and wait until it has finished intialising before starting this B-script")
    Exit
EndIf

; first read the .ini data from the A-script
; NB .ini contents are strings, so convert back to (64-bit) Ptr
Global $pid1=int(IniRead($inifile,"PID","PID",-1))

Global $struct1SizeinBytes=Int(IniRead($inifile,"ALLOC1","sizeInBytes",0))
Global $relativeOffset1=Ptr(IniRead($inifile,"ALLOC1","relativeOffset",0))

Global $struct2SizeinBytes=Int(IniRead($inifile,"ALLOC2","sizeInBytes",0))
Global $relativeOffset2=Ptr(IniRead($inifile,"ALLOC2","relativeOffset",0))
Global $lastbyte2=$struct2SizeinBytes-1

Global $struct3SizeinBytes=Int(IniRead($inifile,"ALLOC3","sizeInBytes",0))
Global $relativeOffset3=Ptr(IniRead($inifile,"ALLOC3","relativeOffset",0))

;____________________________________________________________________________________
; initialise _HighMem
$_HighMem_Testmode=False        ; F: enable actual changes in RAM; (T: dummy mode)
Global $_HighMem_Verbose=True   ; show initialisation error msgs
_HighMem_StartUp(1,"GB")    ; if this exceeds free virtual memory, then the max-available is allocated
If @error Then Exit(@error)

; B-script creates its own mapping of A-script's shared memory,
; with a DIFFERENT ABSOLUTE BASE-OFFSET !!
_HighMem_MapExternalMemory($pid1)

;###########################################################################
; dictionary test

    $pAddress3=_HighMem_AllocateExternal($pid1,$relativeOffset3,$struct3SizeinBytes,"B")
    If @error Then
        ConsoleWrite("Error: Allocation 3 failed with error: " & @error & @CRLF)
        Exit(1) ;   on Exit, _HighMem_CleanUp() is automatically invoked
    EndIf

    ; map a struct to script A's third allocation
    Global $tBuffer3 = DllStructCreate('ptr',$pAddress3)
    If @error Then
        ConsoleWrite("Error: struct 3 creation failed with error: " & @error & @CRLF)
        Exit(1) ;   on Exit, _HighMem_CleanUp() is automatically invoked
    EndIf
    Local $ptr_original = DllStructGetData($tBuffer3,1)

    Local $oResultA = _HighMem_OffsetRelative2Absolute($ptr_original)
    If Not @error Then
        Local $out = VarGetType($oResultA) & @CR & _
        "DllStruct_Size -> " & DllStructGetSize($tBuffer3) & @CR & _
        "DllStruct_Ptr ->  " & DllStructGetPtr($tBuffer3) & @CR & _
        "oDict_A LOCAL ptr ->    = " & $oResultA  & @TAB & "(PID = " & @AutoItPID & ")" & @CR & _
        "oDict_A ORIGINAL ptr ->    = " & $ptr_original & @TAB & "(PID = " & $pid1 & ")"

        ConsoleWrite($out & @CRLF)
;        MsgBox( 0, "Client", $out, 20 )
    EndIf

;   $uniqueObjectName=_Highmem_GetMutexName( $pAddress3 )
;   $oDict_A = ObjGet("","Scripting.Dictionary",$uniqueObjectName)
;   ConsoleWrite("ObjGet returns error: " & @error & @TAB & "IsObj = " & IsObj($oDict_A) & @CRLF & @CRLF)

    ;~ ==================
    Local $oDict_A = Null
    $oDict_A = __ConvertPtrToIDispatch($oResultA)
    If IsObj($oDict_A) Then MsgBox( 0, "", "IsObj = " & IsObj($oDict_A))
    $oDict_A = 0
    ;~ ==================

    Sleep(6000)
;###########################################################################

_HighMem_UnMapExternalMemory($pid1) ; releases all allocations therein as well
_HighMem_CleanUp()
FileDelete($inifile)    ; signals first process that we're done here


Func __ConvertPtrToIDispatch($pIDispatch)
    ; @monoceres
    ; In the end we still want the autoit object. This function converts a raw pointer to an autoit object
    ; This would have been 10000x easier if autoit had supported the idispatch* type in dllstructs...
    Local $aCall = DllCall("kernel32.dll", "none", "RtlMoveMemory", _
            "idispatch*", 0, _
            "ptr*", $pIDispatch, _
            "dword", 4)

    If @error Then
        Return SetError(1, 0, 0)
    EndIf
    Return $aCall[1]
EndFunc

 

Edited by jugador
Link to comment
Share on other sites

If you don't register the object in some way, then how do you expect other processes to find it?:blink: That's exactly what a ROT is for. There may be other ways to achieve this, but I wouldn't know how, nor do I see the point of pursuing this question (you keep moving the goal posts...:(). So far I've provided you with:

  • a fully functional UDF for sharing any amount of available virtual memory (and all data therein) between processes
  • two dedicated example scripts written just for you, that solve your issue of sharing dictionary objects
  • pointers to specific WinAPI functions for setting up your own memory-mapping environment instead of my oven-ready solution, should you so desire

If that still isn't good enough for you, then you'll have to dig much deeper into the low-level ways the OS kernel manages objects. But you'll have to take that journey without further assistance from me. Best of luck.

Link to comment
Share on other sites

@RTFC

I was expecting....  code to access object pointer type reply not this :P.

I thought you knew it that this thread is about dereferencing object pointer.

now suddenly you alleged

4 hours ago, RTFC said:

 (you keep moving the goal posts...:(). 

when did i do that :huh:
In Op post I clearly mention

On 5/9/2023 at 4:48 PM, jugador said:

problem is how to get correct ptr address of $oDict_A 

 

and as far as Rot object concern, again I clearly mention 2 time in my post that I use @LarsJ ROT objects UDF

On 5/9/2023 at 9:54 PM, jugador said:

@Nine

yes I know using ROT objects we can share object between processes (thanks to @LarsJ).
but I want to know how to Read Memory to get Server.au3 $oDict_A ptr address from Client.au3.

 

On 5/12/2023 at 5:31 PM, jugador said:

@RTFC thanks for the code.
but frankly I am having hard time understanding what you did with the code(HighMem UDF).
I use @LarsJ Rot object Udf for server/client connectivity.

So You  see its not about Rot object ;)  and I am not the one "moving the goal posts", it's you who not reading my post properly.

thanks for writing those two dedicated example scripts for me but it didn't solve my query/ problem.
If my request/ question is that hard for the MVPs to answer then I seriously need Best of luck.

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...