Speicher Verständis



  • Hallo

    Habe da mal ne frage bez. Speicher.
    Wenn ich jetzt Bereich: 0x00510000 - 0x00511000 (RegionSize:4096) habe, habe ich dann 4*4096bytes (16384bytes) Speicher? Weil eine Adresse ja 4byte Speicher belegt auf 32bit systemen.



  • Ich weiß zwar nicht was das mit Standard C zu tun haben soll, aber du hast wohl eher 4096 (0x1000) Byte Speicher. Eine Adresse belegt vielleicht 4 Byte, aber das ändert ja nichts daran, dass jedes Byte einzeln adressiert ist.



  • Aber dann würde ich mit diesem Code am Ende über den Speicher hinaus lesen oder?

    void ScanMem(HANDLE hproc ,DWORD start ,DWORD end)
    {
    
    	DWORD read = 0;
    	int buffer = 0;
    
    	printf("wird gescannt...\n");
    
        for(start; start < end ;start++) {
    
            ReadProcessMemory(hproc ,(void *) start ,&buffer ,sizeof(int) ,&read);
            if(buffer == 0x65) {
                printf("Wert an 0x%.8lx gefunden!", start);
    				getchar();
                  return;
            }
        }
    }
    


  • dirk01 schrieb:

    Hallo

    Habe da mal ne frage bez. Speicher.
    Wenn ich jetzt Bereich: 0x00510000 - 0x00511000 (RegionSize:4096) habe, habe ich dann 4*4096bytes (16384bytes) Speicher? Weil eine Adresse ja 4byte Speicher belegt auf 32bit systemen.

    Das hängt damit zusammen, ob deine Maschine byte-adressierbar (also 8 bit) ist. Besteht ein Speicherwort aus 32 Bits, dann bestehen 4096 Adressen aus 32*4096 Speicherbits.



  • Kommt darauf an, wie du die Funktion aufrufst. Wenn [start;end) dir gehört, dann nicht.



  • Ja das weis ich auch danke... möchte eben nur wissen ob es beim obigen konstrukt ein überlauf gibt - bei einer maschine die byte adressierbar ist.



  • void GetMemMinMax(DWORD pid)
    {
    	HANDLE hprocess = NULL;
    	MEMORY_BASIC_INFORMATION mbi;
    	unsigned long adress = 0x00400000; // Start memory address
    	unsigned long start;
    	unsigned long end;
    
    	hprocess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, pid);
    	if(hprocess == NULL) {
    		printf("OpenProcess(), error %i\n",GetLastError());
    		getchar();
    		return;
    	}
    
        do
        {
            VirtualQueryEx( hprocess ,(void *) adress ,&mbi ,sizeof(MEMORY_BASIC_INFORMATION) );
    
            if( ( (mbi.State == MEM_COMMIT) && (mbi.Protect == PAGE_READWRITE) ) && (mbi.Type == MEM_PRIVATE)) {
    			start = (unsigned int) mbi.BaseAddress;
    			end = (unsigned int) mbi.BaseAddress + mbi.RegionSize;
    
    			printf("Bereich: 0x%.8lx - 0x%.8lx  Size:%li ",start ,end ,end-start);
    
    			// Scan memory
    			ScanMem(hprocess ,start ,end);
            }
    
            adress += mbi.RegionSize;
    
        } 
    	while(adress < 0x80000000);
    
    	CloseHandle(hprocess);
    
    	return;
    }
    
    void ScanMem(HANDLE hproc ,DWORD start ,DWORD end)
    {
    
    	DWORD read = 0;
    	int buffer = 0;
    
    	printf("wird gescannt...\n");
    
        for(start; start < end ;start++) {
    
            ReadProcessMemory(hproc ,(void *) start ,&buffer ,sizeof(int) ,&read);
            if(buffer == 0x65) {
                printf("Wert an 0x%.8lx gefunden!", start);
    				getchar();
                  return;
            }
        }
    }
    


  • Nimm dann gleich einen entsprechenden Zeiger, dann paßt es automatisch:

    int *p = (int*)start;
    int *pEnd = (int *)end;
    for(; p < pEnd ; p++)
    {
        ReadProcessMemory(hproc, p ,&buffer, sizeof(int), &read);
    
    }
    

    So liest du "(end - start) / sizeof(int)" Werte aus.



  • Sieht in Ordnung aus, allerdings solltest du "read" auch überprüfen, wenn du dir die Information schon holst. Also if (read == sizeof(int) && buffer == 0x65).

    Edit: Warte mal, du übergibst da DWORD statt DWORD*? 😮
    Wenn du jede Kombination checken willst, dann nimm zumindest char*. Aber caste doch keine Pointer in Integer um. oO



  • Und wenn ich einen String habe?



  • Sinnvollerweise holst du dir eh den ganzen Block (oder zumindest große Teile) auf einmal und durchsuchst die dann.



  • @cooky451 Dein edit versteh ich nicht. Könntest Du mir das näher erklären?



  • void scanMemeory(HANDLE hproc, const char* start, const char* end)
    {
      DWORD read;
      int buffer;
    
      printf("wird gescannt...\n");
    
      for(; start < end; ++start)
      {
        if (ReadProcessMemory(hproc, start, &buffer, sizeof(buffer), &read))
        {
          if(read == sizeof(buffer) && buffer == 0x65)
          {
            printf("Wert an 0x%.8lx gefunden!", start);
            getchar();
            return;
          }
        }
        else // GetLastError()
        {
        }
      }
    }
    

    Das meinte ich. Allerdings ist jeder ReadProcessMemory() Aufruf teuer, und hier macht man sogar unnötig viele Aufrufe, weil man alles vier mal liest. Besser wäre es, den ganzen Speicher am Stück zu kopieren und dann zu durchsuchen. Wenn der Block zu groß ist, einen Fehler melden oder aber aufteilen - wobei man dann aufpassen muss, dass man nicht plötzlich etwas übersieht, das sich in zwei Blöcken befindet.



  • Danke Dir cooky451
    👍



  • Dieser Thread wurde von Moderator/in rüdiger aus dem Forum C (C89 und C99) in das Forum WinAPI verschoben.

    Im Zweifelsfall bitte auch folgende Hinweise beachten:
    C/C++ Forum :: FAQ - Sonstiges :: Wohin mit meiner Frage?

    Dieses Posting wurde automatisch erzeugt.



  • cooky451 schrieb:

    if (ReadProcessMemory(hproc, start, &buffer, sizeof(buffer), &read))
        {
          if(read == sizeof(buffer) && buffer == 0x65)
          {
    

    Die Chance, den Bytewert zu finden, dürfte bei <= 50% für sizeof(int)==2*1 und bei <= 25% für sizeof(int)=4*1 liegen. Bei Suchwerten oberhalb 0x7F gibts auch noch Vorzeichenprobleme.



  • Was meinst Du damit genau? Funktioniert jedenfals so wie ich möchte. Das es False/Positive Ergebnisse gibt ist mir klar!


Log in to reply