Die DLL an sich wird imho total einfach, es wird nur ein Speicherbereich von 1MB reserviert.
Der Aufruf der Funktion gibt einfach nur einen Pointer auf eben diesen Speicherbereich zurück.
In diesen Speicher kann nun jedes Programm beliebig Daten einschreiben bzw. auslesen. So die Theorie^^
Naja, vielleicht mache ich sogar 2 Funktionen, eine zum Schreiben, die andere zum Lesen. Usability ftw! Ich setz mich mal dran....
//EDIT
naja, fast hätte ich es mir gedacht, klappt so nicht.
Man kann nicht von "außerhalb" auf innerhalb der DLL reservierten Speicher zugreifen.
Hab eine dll erstellt
format PE GUI 4.0 DLL
entry DllEntryPoint
include 'win32ax.inc' ;includes
;einzubindende Librarys
section '.idata' import data readable writeable
library kernel,'KERNEL32.DLL',\
user,'USER32.DLL'
;************Hier die in der DLL verwendeten Funktionen für den Export eintragen
section '.edata' export data readable writable
export 'GETPOINTER.DLL',\ ;Dateiname, Zeilentrenner ist ,\
GetPointer,'GetPointer' ;Funktion
;weitere Sektionen je nach Anforderung der Funktionen
section '.data' data readable writeable
_mem dd 10000 dup 0 ;10 Kb Speicher
;section für die Funktionen
section '.code' code readable executable
;DllEntryPoint wird beim Laden der DLL aufgerufen
;um "bombensicheres" Errorhandling zu haben, Funktion anpassen!
proc DllEntryPoint hinstDLL,fdwReason,lpvReserved
mov eax,TRUE ;hart aber herzlich^^
ret
endp
;******************Ab hier fangen die Benutzer-Funktionen an **********
proc GetPointer
;ab hier folgt der Code, wie er z.B. von AssembleIt verarbeitet wird
use32
mov eax,_mem ;Startadresse variable
ret
endp
section '.reloc' fixups data discardable
welche auch einwandfrei funktioniert, sie gibt den Pointer auf die Variable _mem zurück.
Allerdings kann man per dllstructcreate(byte[1000],$pointer) nicht auf diesen Speicher zugreifen.
Umgekehrt funktionierts aber, man könnte der DLL einen Wert übergeben welcher im Speicher der DLL abgelegt wird, die Frage ist, ob von einem 2. Script dieser Speicher gelesen werden kann!
$gui = GUICreate("")
$label = GUICtrlCreateLabel("", 10, 10, 100, 30)
GUISetState()
$struct = DllStructCreate("char[100]")
$ptr = Int(DllStructGetPtr($struct))
$dll = DllOpen("getpointer.dll")
$string = "AutoIt"
$i = 0
$t = TimerInit()
While 1
$msg = GUIGetMsg()
If $msg = -3 Then ExitLoop
If TimerDiff($t) > 1000 Then
$t = TimerInit()
$i = $i + 1
ConsoleWrite('@@ Debug(' & @ScriptLineNumber & ') : $i = ' & $i & @CRLF & '>Error code: ' & @error & @CRLF) ;### Debug Console
$string="AutoIt " & $i
$ret = DllCall($dll, "dword", "VarIn", "str", $string, "int", StringLen($string))
$ret = DllCall($dll, "dword", "VarOut", "ptr", $ptr, "int", DllStructGetSize($struct))
GUICtrlSetData($label, DllStructGetData($struct, 1))
EndIf
WEnd
DLL dazu
; DLL creation example
;
;1) Funktion erstellen in der section .text
; proc Funktionsname
; AssemblerCode....wie er in AutoIt lauffähig ist... hierhinkopieren
; endp
;
;2) In die section .edata den Funktionsnamen eintragen:
;export 'DLLNAME.DLL',\ ;Name der DLL-Datei
;Funktionsname1,'Funktionsname1',\ ;Funktionsnamen
;Funktionsname2,'Funktionsname2'
;
;3) *.asm-datei mit wfasm.exe oder fasm.exe compilieren (in FASMW.EXE laden und CTRL+F9 drücken)
;
;Aufruf aus AutoIt mit
;$ret=dllcall("dllname.dll","RückgabeTYP","Funktionsname","TYP",$parameter1)
format PE GUI 4.0 DLL
entry DllEntryPoint
include 'win32ax.inc' ;includes
;************Hier die in der DLL verwendeten Funktionen für den Export eintragen
section '.edata' export data readable
export 'GETPOINTER.DLL',\ ;Dateiname, Zeilentrenner ist ,\
VarIn,'VarIn',\ ;Funktion
VarOut,'VarOut' ;Funktion
;weitere Sektionen je nach Anforderung der Funktionen
section '.data' data readable writable
_mem dd 10000 dup 0 ;10 Kb Speicher
;section für die Funktionen
section '.code' code readable executable
;DllEntryPoint wird beim Laden der DLL aufgerufen
;um "bombensicheres" Errorhandling zu haben, Funktion anpassen!
proc DllEntryPoint hinstDLL,fdwReason,lpvReserved
mov eax,TRUE ;hart aber herzlich^^
ret
endp
;******************Ab hier fangen die Benutzer-Funktionen an **********
proc VarIn
;ab hier folgt der Code, wie er z.B. von AssembleIt verarbeitet wird
use32
mov esi,[esp+4] ;Startadresse variable
mov ecx,[esp+8] ;länge
mov eax,ecx
mov edi,_mem ;DLL Speicher
rep movsb ;alle bytes von quelle nach ziel kopieren
ret 8
endp
proc VarOut
mov edi,[esp+4] ;Startadresse variable
mov ecx,[esp+8] ;länge
mov esi,_mem ;DLL Speicher
mov eax,edi
rep movsb ;alle bytes von quelle nach ziel kopieren
ret 8
endp
section '.reloc' fixups data discardable
Alles anzeigen
In einem Script( compiliert) gestartet, funktioniert das einwandfrei. Man kann dieses Script laufen lassen und ein weiteres starten, in dem die Zeile mit dem VarIN-Call auskommentiert ist.
Leider wird, wenn man die DLL aus einem weiteren Script anspricht, der Speicher nicht Global angesprochen...werde da wohl nochmal etwas nachhaken müssen!
Funzt nicht...Speicher innerhalb der DLL wird geschützt. Um da ranzukommen, verwendet man die Methode per _WinAPI_ReadProcessMemory(), das geht aber einfacher, s.o.