Torna al Thread

enum AccessRights { PROCESS_VM_READ = 0x0010, PROCESS_VM_WRITE = 0x0020, PROCESS_VM_OPERATION = 0x0008 } [DllImport("kernel32.dll")] static extern IntPtr OpenProcess(AccessRights dwDesiredAcces, bool bInheritHandle, int dwProcessId); [DllImport("kernel32.dll")] static extern bool CloseHandle(IntPtr hObject); [DllImport("kernel32.dll")] static extern bool ReadProcessMemory(IntPtr hProcess, IntPtr lpBaseAddress, IntPtr lpBuffer, int nSize, out int lpNumberOfBytesRead); [DllImport("kernel32.dll")] static extern bool WriteProcessMemory(IntPtr hProcess, IntPtr lpBaseAddress, IntPtr lpBuffer, int nSize, out int lpNumberOfBytesWritten); //Questa struttura deve essere identica a quella //dichiarata nell'altra applicazione struct SharedData { public int v1; public bool v2; public char v3; public Point v4; } IntPtr processHandle; IntPtr sharedMemPtr; IntPtr mustRefreshPtr; IntPtr newDataPtr; IntPtr sharedData; int dataSize; SharedData data; //Questa funzione ottiene gli indirizzi e le informazioni dal registro di sistema void InitRead() { //Apre la chiave di registro RegistryKey swKey = Registry.LocalMachine.OpenSubKey("Software"); RegistryKey infoKey = swKey.OpenSubKey("SharedMemTest"); //Ottiene l'ID del processo da cui leggere i dati int processId = (int)infoKey.GetValue("ProcessID"); //Apre il processo con diritti di lettura e scrittura this.processHandle = OpenProcess(AccessRights.PROCESS_VM_READ | AccessRights.PROCESS_VM_WRITE | AccessRights.PROCESS_VM_OPERATION, false, processId); //Ottiene l'indirizzo della memoria condivisa sharedMemPtr = (IntPtr)(int)infoKey.GetValue("MemPtr"); //Ottiene l'indirizzo del bool da impostare per richiedere l'aggiornamento mustRefreshPtr = (IntPtr)(int)infoKey.GetValue("MustRefreshPtr"); //Ottiene l'indirizzo della memoria da impostare per l'aggiornamento dei dati newDataPtr = (IntPtr)(int)infoKey.GetValue("NewDataPtr"); //Chiude le chiavi di registro infoKey.Close(); swKey.Close(); //Ottiene la dimensione della memoria da leggere this.dataSize = Marshal.SizeOf(typeof(SharedData)); //Alloca la memoria in cui leggere i dati estranei this.sharedData = Marshal.AllocHGlobal(dataSize); } //Questa funzione legge i dati condivisi void Read() { int readBytes; //Legge la memoria condivisa del processo ReadProcessMemory(processHandle, sharedMemPtr, this.sharedData, this.dataSize, out readBytes); //Converte la memoria non gestita nella struttura gestita this.data = (SharedData)Marshal.PtrToStructure(this.sharedData, typeof(SharedData)); } void Write(SharedData newData) { int written; //Imposta nel ptr da scrivere i nuovi dati Marshal.StructureToPtr(newData, this.sharedData, false); //Scrive nella memoria condivisa i nuovi dati WriteProcessMemory(processHandle, this.newDataPtr, this.sharedData, this.dataSize, out written); //Imposta nel ptr da scrivere true, per indicare al processo di aggiornare i dati Marshal.StructureToPtr(true, this.sharedData, false); //Scrive nella memoria condivisa il true WriteProcessMemory(processHandle, this.mustRefreshPtr, sharedData, sizeof(bool), out written); //A questo punto la prossima volta che il processo esterno dovrà elaborare i dati //saprà di dover aggiornare i dati dalla memoria condivisa, dove abbiamo copiato //i nuovi valori } void EndRead() { //Chiude l'handle del processo CloseHandle(this.processHandle); //Dealloca la memoria non gestita Marshal.FreeHGlobal(sharedData); }
Copyright © dotNetHell.it 2002-2024
Running on Windows Server 2008 R2 Standard, SQL Server 2012 & ASP.NET 3.5