Zeiger auf Gültigkeit testen (C / C ++)

70

Gibt es eine Möglichkeit, (natürlich programmatisch) zu bestimmen, ob ein gegebener Zeiger "gültig" ist? Die Suche nach NULL ist einfach, aber was ist mit 0x00001234? Wenn versucht wird, diese Art von Zeiger zu dereferenzieren, tritt eine Ausnahme / ein Absturz auf.

Eine plattformübergreifende Methode wird bevorzugt, aber plattformspezifisch (für Windows und Linux) ist auch in Ordnung.

Zur Klärung aktualisieren: Das Problem ist nicht mit veralteten / freigegebenen / nicht initialisierten Zeigern; Stattdessen implementiere ich eine API, die Zeiger vom Aufrufer übernimmt (wie ein Zeiger auf eine Zeichenkette, eine Dateikennung usw.). Der Aufrufer kann einen ungültigen Wert als Zeiger senden (aus Versehen oder aus Versehen). Wie verhindere ich einen Absturz?

    
noamtm 15.02.2009, 15:45
quelle

27 Antworten

65
  

Zur Klärung aktualisieren: Das Problem liegt nicht bei veralteten, freigegebenen oder nicht initialisierten Zeigern. Stattdessen implementiere ich eine API, die Zeiger vom Aufrufer übernimmt (wie ein Zeiger auf eine Zeichenkette, eine Dateikennung usw.). Der Aufrufer kann einen ungültigen Wert als Zeiger senden (aus Versehen oder aus Versehen). Wie verhindere ich einen Absturz?

Sie können diese Überprüfung nicht durchführen. Es gibt einfach keine Möglichkeit zu überprüfen, ob ein Zeiger "gültig" ist. Sie müssen darauf vertrauen, dass Menschen, die eine Funktion verwenden, die einen Zeiger verwendet, wissen, was sie tun. Wenn sie Ihnen 0x4211 als Zeigerwert übergeben, müssen Sie darauf vertrauen, dass sie auf Adresse 0x4211 zeigt. Und wenn sie "versehentlich" ein Objekt treffen, dann würden Sie selbst dann, wenn Sie eine unheimliche Operationssystemfunktion (IsValidPtr oder was auch immer) verwenden würden, in einen Fehler schlüpfen und nicht schnell versagen.

Beginnen Sie mit Null-Zeigern, um diese Art von Dingen zu signalisieren, und teilen Sie dem Benutzer Ihrer Bibliothek mit, dass sie Zeiger nicht verwenden sollten, wenn sie dazu neigen, ungültige Zeiger versehentlich zu passieren:)

    
Johannes Schaub - litb 15.02.2009, 16:11
quelle
28

Das Verhindern eines Absturzes, der durch das Senden eines ungültigen Zeigers durch den Aufrufer verursacht wird, ist ein guter Weg, um stille Fehler zu finden, die schwer zu finden sind.

Ist es nicht besser für den Programmierer, der Ihre API verwendet, um eine klare Nachricht zu erhalten, dass sein Code gefälscht ist, indem er ihn abstürzt, anstatt ihn zu verstecken?

    
Nailer 15.02.2009 16:05
quelle
26

Unter Win32 / 64 gibt es eine Möglichkeit, dies zu tun. Versuch, den Zeiger zu lesen und die resultierende SEH-Ausnahme abzufangen, die bei einem Fehler ausgelöst wird. Wenn es nicht wirft, dann ist es ein gültiger Zeiger.

Das Problem bei dieser Methode besteht jedoch darin, dass sie nur zurückgibt, ob Sie Daten aus dem Zeiger lesen können oder nicht. Es gibt keine Garantie für die Sicherheit des Typs oder eine Anzahl anderer Invarianten. Im Allgemeinen ist diese Methode gut für wenig anderes als zu sagen "Ja, ich kann diesen bestimmten Ort in Erinnerung zu einer Zeit lesen, die jetzt vergangen ist".

Kurz gesagt, tu das nicht;)

Raymond Chen hat einen Blogbeitrag zu diesem Thema: Ссылка

    
JaredPar 15.02.2009 15:55
quelle
20

Hier sind drei einfache Möglichkeiten für ein C-Programm unter Linux, introvertiert zu werden über den Status des Speichers, in dem es läuft, und warum die Frage in einigen Kontexten entsprechende ausgeklügelte Antworten hat.

  1. Nach dem Aufruf von getpagesize () und Runden des Mauszeigers auf eine Seite Grenze, Sie können mincore () aufrufen, um herauszufinden, ob eine Seite gültig ist und wenn es zufällig Teil des Prozess-Arbeitssatzes ist. Beachten Sie, dass dies erforderlich ist einige Kernel-Ressourcen, so sollten Sie es Benchmark und bestimmen, ob Diese Funktion aufzurufen, ist in Ihrer API wirklich angemessen. Wenn deine api wird Interrupts behandeln oder von seriellen Ports lesen in Erinnerung, es ist angemessen, dies zu nennen, um unvorhersehbare zu vermeiden Verhalten.
  2. Nachdem stat () aufgerufen wurde, um festzustellen, ob ein Verzeichnis / proc / self verfügbar ist, können Sie / proc / self / maps öffnen und durchlesen Informationen über die Region finden, in der sich ein Zeiger befindet. Untersuchen Sie die Manpage für proc, die Prozessinformations-Pseudodatei System. Offensichtlich ist das relativ teuer, aber Sie könnten sein in der Lage, das Ergebnis der Analyse in ein Array zwischenzuspeichern Sie können effizient mit einer binären Suche suchen. Beachten Sie auch die / proc / self / smaps. Wenn Ihre API dann für High-Performance-Computing ist Das Programm wird über das / proc / self / numa wissen wollen dokumentiert unter der man-Seite für numa, den nicht einheitlichen Speicher Architektur.
  3. Der Aufruf get_meppolicy (MPOL_F_ADDR) ist für Hochleistungs-Computing-API-Arbeiten geeignet, bei denen mehrere Threads von Ausführung und Sie verwalten Ihre Arbeit, um Affinität für nicht einheitlichen Speicher zu haben wie es sich auf die CPU-Kerne und Socket-Ressourcen bezieht. Eine solche api wird Ihnen natürlich auch sagen, ob ein Zeiger gültig ist.

Unter Microsoft Windows gibt es die Funktion QueryWorkingSetEx, die unter der Process Status API (auch in der NUMA API) dokumentiert ist. Als logische Konsequenz der anspruchsvollen NUMA-API-Programmierung ermöglicht Ihnen diese Funktion auch einfache "Testzeiger für Validität (C / C ++)", so dass es unwahrscheinlich ist, dass sie für mindestens 15 Jahre veraltet sind.

    
George Carrette 12.05.2015 17:22
quelle
15

AFAIK gibt es keinen Weg. Sie sollten versuchen, diese Situation zu vermeiden, indem Sie nach dem Freigeben von Speicher immer Zeiger auf NULL setzen.

    
Ferdinand Beyer 15.02.2009 15:48
quelle
7

Sehen Sie sich dies und diese Frage. Sehen Sie sich auch die Smart Pointer an.

    
tunnuz 15.02.2009 15:51
quelle
6

Erstens sehe ich keinen Sinn darin, sich vor dem Anrufer zu schützen, der absichtlich versucht, einen Absturz zu verursachen. Sie könnten dies leicht tun, indem sie versuchen, über einen ungültigen Zeiger selbst darauf zuzugreifen. Es gibt viele andere Möglichkeiten - sie könnten nur Ihr Gedächtnis oder den Stapel überschreiben. Wenn Sie vor solchen Dingen schützen müssen, müssen Sie in einem separaten Prozess mit Sockets oder einem anderen IPC für die Kommunikation ausgeführt werden.

Wir schreiben ziemlich viel Software, die es Partnern / Kunden / Benutzern ermöglicht, die Funktionalität zu erweitern. Zwangsläufig wird uns jeder Fehler gemeldet, daher ist es hilfreich, wenn Sie einfach zeigen können, dass das Problem im Plug-In-Code liegt. Darüber hinaus gibt es Sicherheitsbedenken und einige Benutzer sind vertrauenswürdiger als andere.

Wir verwenden eine Reihe verschiedener Methoden, abhängig von den Anforderungen an Leistung / Durchsatz und Vertrauenswürdigkeit. Am meisten bevorzugt:

  • separate Prozesse mit Sockets (oft Daten als Text übergeben).

  • separate Prozesse mit gemeinsam genutztem Speicher (wenn große Datenmengen passieren).

  • gleicher Prozess separate Threads über Nachrichtenwarteschlange (wenn häufige Kurznachrichten).

  • Derselbe Prozess trennt alle Threads, die aus einem Speicherpool zugewiesen wurden.

  • gleicher Prozess über direkten Prozeduraufruf - alle übergebenen Daten, die aus einem Speicherpool zugewiesen wurden.

Wir versuchen, niemals auf das zurückzugreifen, was Sie im Umgang mit Software von Drittanbietern tun wollen - vor allem, wenn wir die Plug-Ins / Bibliothek als Binärcode und nicht als Quellcode erhalten.

Die Verwendung eines Speicherpools ist in den meisten Fällen recht einfach und muss nicht ineffizient sein. Wenn Sie die Daten an erster Stelle zuweisen, ist es trivial, die Zeiger auf die Werte zu überprüfen, die Sie zugewiesen haben. Sie können auch die zugewiesene Länge speichern und "magische" Werte vor und nach den Daten hinzufügen, um nach gültigen Datentypen und Datenüberschreitungen zu suchen.

    
Dipstick 15.02.2009 18:03
quelle
6

Zur Antwort ein wenig in diesem Thread:

  

IsBadReadPtr (), IsBadWritePtr (), IsBadCodePtr (), IsBadStringPtr () für Windows.

Mein Rat ist, sich von ihnen fern zu halten, jemand hat diesen schon gepostet: Ссылка

Ein anderer Beitrag zum selben Thema und vom selben Autor (glaube ich) ist dieser: Ссылка ("IsBadXxxPtr sollte wirklich CrashProgramRandomly heißen").

Wenn die Benutzer Ihrer API fehlerhafte Daten senden, lassen Sie sie abstürzen. Wenn das Problem darin besteht, dass die übergebenen Daten erst später verwendet werden (und das Auffinden der Ursache erschwert wird), fügen Sie einen Debug-Modus hinzu, in dem die Strings usw. bei der Eingabe protokolliert werden. Wenn sie schlecht sind, wird es offensichtlich sein (und wahrscheinlich abstürzen). Wenn es zu oft passiert, kann es sich lohnen, das API aus dem Prozess zu entfernen und den API-Prozess anstelle des Hauptprozesses zum Absturz zu bringen.

    
Fredrik 15.02.2009 18:37
quelle
4

Ich habe viel Sympathie für Ihre Frage, da ich mich selbst in einer fast identischen Position befinde. Ich weiß zu schätzen, was viele der Antworten sagen, und sie sind korrekt - die Routine, die den Zeiger liefert sollte einen gültigen Zeiger bereitstellen. In meinem Fall ist es fast unvorstellbar, dass sie den Zeiger korrumpiert hätten - aber wenn sie verwaltet worden wären, wäre es meine Software, die abstürzt, und ME würde die Schuld dafür bekommen: - (

Meine Anforderung ist nicht, dass ich nach einem Segmentierungsfehler weitermache - das wäre gefährlich - ich möchte nur berichten, was mit dem Kunden passiert ist, bevor ich ihn beende, damit sie ihren Code reparieren können, anstatt mir die Schuld zu geben!

So habe ich es (unter Windows) gefunden: Ссылка

Um eine Zusammenfassung zu geben:

%Vor%

Nun erscheint , um sich so zu verhalten, wie ich es hoffe (es gibt die Fehlermeldung aus und beendet dann das Programm) - aber wenn jemand einen Fehler entdecken kann, lass es mich wissen!

    
Mike Sadler 12.04.2012 13:45
quelle
2

In C ++ gibt es keine Bestimmungen, um die Gültigkeit eines Zeigers als allgemeinen Fall zu testen. Man kann natürlich annehmen, dass NULL (0x00000000) schlecht ist, und verschiedene Compiler und Bibliotheken verwenden hier und da gerne "spezielle Werte", um das Debuggen zu vereinfachen (wenn ich z. B. einen Zeiger im visuellen Studio als 0xCECECECE sehe) Ich habe etwas falsch gemacht, aber die Wahrheit ist, dass, da ein Zeiger nur ein Index in den Speicher ist, es fast unmöglich ist, dies zu erkennen, indem man einfach auf den Zeiger schaut, wenn es der "richtige" Index ist.

Es gibt verschiedene Tricks, die Sie mit dynamic_cast und RTTI ausführen können, um sicherzustellen, dass das Objekt, auf das verwiesen wird, den von Ihnen gewünschten Typ aufweist, aber alle erfordern, dass Sie zuerst auf etwas Gültiges zeigen.

Wenn Sie sicherstellen wollen, dass Ihr Programm "ungültige" Zeiger erkennen kann, dann ist mein Ratschlag: Setzen Sie jeden deklarierten Zeiger sofort nach der Erzeugung auf NULL oder eine gültige Adresse und setzen Sie ihn sofort auf NULL, nachdem Sie den Speicher freigegeben haben verweist auf. Wenn Sie mit dieser Übung fleißig sind, brauchen Sie nur nach NULL zu suchen.

    
Toji 15.02.2009 15:57
quelle
2

Es gibt keine portable Möglichkeit, dies zu tun, und dies für bestimmte Plattformen zu tun, kann irgendwo zwischen schwer und unmöglich sein. In jedem Fall sollten Sie niemals Code schreiben, der von einer solchen Prüfung abhängt - lassen Sie die Zeiger nicht von vornherein ungültige Werte annehmen.

    
anon 15.02.2009 15:49
quelle
2

Es ist eine gute Technik, den Zeiger vor und nach der Verwendung auf NULL zu setzen. Dies ist in C ++ leicht zu bewerkstelligen, wenn Sie z. B. Zeiger innerhalb einer Klasse (eine Zeichenkette) verwalten:

%Vor%     
Tim Ring 15.02.2009 16:09
quelle
2

Es ist keine sehr gute Richtlinie, willkürliche Zeiger als Eingabeparameter in einer öffentlichen API zu akzeptieren. Es ist besser, "plain data" -Typen wie eine ganze Zahl, eine Zeichenfolge oder eine Struktur (ich meine eine klassische Struktur mit reinen Daten im Inneren natürlich; offiziell kann alles eine Struktur sein).

Warum? Nun, wie andere sagen, gibt es keinen Standardweg, um zu wissen, ob Sie einen gültigen Zeiger oder einen, der auf Junk verweist, erhalten haben.

Aber manchmal haben Sie nicht die Wahl - Ihre API muss einen Zeiger akzeptieren.

In diesen Fällen muss der Aufrufer einen guten Zeiger übergeben. NULL kann als Wert akzeptiert werden, aber nicht als Zeiger auf Junk.

Können Sie in irgendeiner Weise nachsehen? Nun, was ich in einem solchen Fall getan habe, war, eine Invariante für den Typ zu definieren, auf den der Zeiger zeigt, und es aufzurufen, wenn Sie es erhalten (im Debug-Modus). Zumindest wenn die Invariante fehlschlägt (oder abstürzt), wissen Sie, dass Ihnen ein schlechter Wert übergeben wurde.

%Vor%     
Daniel Daranas 16.02.2009 08:20
quelle
1

Wie andere bereits gesagt haben, können Sie einen ungültigen Zeiger nicht zuverlässig erkennen. Betrachten Sie einige der Formen, die ein ungültiger Zeiger annehmen könnte:

Sie könnten einen Nullzeiger haben. Das ist einer, nach dem Sie leicht suchen und etwas unternehmen können.

Sie könnten einen Zeiger auf einen Bereich außerhalb des gültigen Speichers haben. Was gültiger Speicher ist, hängt davon ab, wie die Laufzeitumgebung des Systems den Adressraum einrichtet. Auf Unix-Systemen ist es normalerweise ein virtueller Adressraum, der bei 0 beginnt und zu einer großen Anzahl von Megabyte geht. Auf eingebetteten Systemen könnte es ziemlich klein sein. Es darf auf jeden Fall nicht bei 0 beginnen. Wenn Ihre App zufällig im Supervisormodus oder einem ähnlichen Modus ausgeführt wird, verweist Ihr Zeiger möglicherweise auf eine echte Adresse, die möglicherweise nicht mit echtem Speicher gesichert ist.

Sie könnten einen Zeiger auf einen Bereich innerhalb Ihres gültigen Speichers haben, selbst innerhalb Ihres Datensegments, bss, stack oder heap, aber nicht auf ein gültiges Objekt zeigen. Eine Variante davon ist ein Zeiger, der auf ein gültiges Objekt zeigt, bevor dem Objekt etwas Schlimmes passiert ist. Schlechte Dinge in diesem Kontext sind die Freigabe, Speicherfehler oder Zeigerfehler.

Sie könnten einen ungültigen ungültigen Zeiger haben, z. B. einen Zeiger mit unzulässiger Ausrichtung für das Objekt, auf das verwiesen wird.

Das Problem wird noch schlimmer, wenn Sie Segment / Offset-basierte Architekturen und andere ungerade Pointer-Implementierungen in Betracht ziehen. Diese Art von Sache wird normalerweise durch gute Compiler und vernünftige Verwendung von Typen vor dem Entwickler verborgen, aber wenn Sie den Schleier durchbohren und versuchen wollen, das Betriebssystem und die Compiler-Entwickler auszutricksen, dann können Sie das, aber es gibt keinen generischen Weg um es zu tun, das alle Probleme behandeln wird, die Sie möglicherweise treffen.

Das Beste, was Sie tun können, ist, den Absturz zuzulassen und einige gute Diagnoseinformationen zu veröffentlichen.

    
John Grieggs 16.02.2009 08:48
quelle
1

Im Allgemeinen ist es unmöglich zu tun. Hier ist ein besonders unangenehmer Fall:

%Vor%

Auf vielen Plattformen wird Folgendes ausgegeben:

%Vor%

Sie zwingen das Laufzeitsystem, Speicherbits falsch zu interpretieren, aber in diesem Fall wird es nicht abstürzen, weil die Bits alle sinnvoll sind. Dies ist Teil des Designs der Sprache (siehe C-Stil Polymorphismus mit struct inaddr , inaddr_in , inaddr_in6 ), so dass Sie nicht zuverlässig gegen es auf jeder Plattform schützen können.

    
Tom 15.02.2009 16:24
quelle
1

Es ist unglaublich, wie viele irreführende Informationen Sie in den Artikeln oben lesen können ...

Und selbst in Microsoft MSDN-Dokumentation wird behauptet, dass IsBadPtr verboten ist. Naja - ich bevorzuge eine Anwendung, anstatt zu stürzen. Auch wenn das Arbeiten mit Begriffen fehlerhaft funktioniert (solange der Endbenutzer mit der Anwendung fortfahren kann).

Beim googeln habe ich kein brauchbares Beispiel für Windows gefunden - eine Lösung für 32-Bit-Apps gefunden,

Ссылка

Ich muss aber auch 64-Bit-Apps unterstützen, daher funktionierte diese Lösung nicht für mich.

Aber ich habe die Quellcodes des Weins geerntet und es geschafft, ähnliche Codes zu erstellen, die auch für 64-Bit-Apps funktionieren würden - Code wird hier angehängt:

%Vor%

Und folgender Code kann erkennen, ob der Zeiger gültig ist oder nicht, Sie müssen wahrscheinlich einige NULL-Prüfzeichen hinzufügen:

%Vor%

Dies ruft den Klassennamen vom Zeiger ab - ich denke, es sollte für Ihre Bedürfnisse ausreichen.

Eine Sache, die ich immer noch fürchte, ist die Leistung der Zeigerüberprüfung - in Code-Snipet oben gibt es bereits 3-4 API-Aufrufe gemacht - könnte für zeitkritische Anwendungen übertrieben sein.

Es wäre gut, wenn jemand den Overhead der Zeigerüberprüfung messen könnte, der beispielsweise mit C # / verwalteten C ++ - Aufrufen verglichen wird.

    
TarmoPikaro 11.03.2014 23:03
quelle
1

In der Tat könnte etwas unter bestimmten Umständen getan werden: Wenn Sie zum Beispiel prüfen möchten, ob eine String Pointer-Zeichenfolge gültig ist, kann syscall mit write (fd, buf, szie) Ihnen helfen, die Magie zu nutzen: fd sei eine Datei Deskriptor der temporären Datei, die Sie für test erstellen, und buf zeigt auf die zu testende Zeichenfolge. Wenn der Zeiger ungültig ist, würde write () -1 zurückgeben und errno auf EFAULT setzen, was anzeigt, dass buf außerhalb Ihres zugänglichen Adressraums ist.

    
Wenlin.Wu 25.03.2018 16:24
quelle
0

IsBadReadPtr (), IsBadWritePtr (), IsBadCodePtr (), IsBadStringPtr () für Windows.
Diese nehmen die Zeit proportional zur Länge des Blocks, also überprüfe ich für die Plausibilitätsprüfung einfach die Startadresse.

    
pngaz 15.02.2009 15:53
quelle
0

Ich habe gesehen, dass verschiedene Bibliotheken eine Methode verwenden, um nach nicht referenziertem Speicher und dergleichen zu suchen. Ich glaube, sie "überschreiben" einfach die Speicherzuweisungs- und Freigabe-Methoden (malloc / free), die eine Logik haben, die die Zeiger verfolgt. Ich nehme an, das ist für Ihren Anwendungsfall ein Overkill, aber es wäre eine Möglichkeit, das zu tun.

    
sebnow 15.02.2009 16:12
quelle
0

Technisch können Sie den Operator new (und delete ) überschreiben und Informationen über den gesamten zugewiesenen Speicher sammeln, damit Sie über eine Methode verfügen können, um zu überprüfen, ob der Heapspeicher gültig ist. aber:

  1. Sie müssen immer noch einen Weg finden, um zu überprüfen, ob der Zeiger auf stack () zugewiesen ist

  2. Sie müssen definieren, was "gültiger" Zeiger ist:

a) Speicher auf dieser Adresse ist    zugeordnet

b) Speicher an dieser Adresse    ist start Adresse des Objekts (z.    Adresse nicht in der Mitte von riesig    Array)

c) Speicher an dieser Adresse    ist start Adresse des Objekts von erwartet Typ

Untere Zeile : Der fragliche Ansatz ist keine C ++ - Methode. Sie müssen einige Regeln definieren, die sicherstellen, dass die Funktion gültige Zeiger erhält.

    
noonex 15.02.2009 16:26
quelle
0

Es gibt keine Möglichkeit, diese Überprüfung in C ++ durchzuführen. Was sollten Sie tun, wenn Ihnen ein anderer Code einen ungültigen Zeiger übergibt? Sie sollten abstürzen. Warum? Schauen Sie sich diesen Link an: Ссылка

    
zildjohn01 16.02.2009 01:02
quelle
0

Nachtrag zu der (den) Antwort (en):

Angenommen, Ihr Zeiger könnte nur drei Werte enthalten: 0, 1 und -1, wobei 1 einen gültigen Zeiger, -1 einen ungültigen und 0 einen anderen ungültigen Zeiger angibt. Wie hoch ist die Wahrscheinlichkeit, dass Ihr Zeiger NULL ist, wobei alle Werte gleich wahrscheinlich sind? 1/3. Nehmen Sie nun den gültigen Fall heraus, so dass Sie für jeden ungültigen Fall ein Verhältnis von 50:50 haben, um alle Fehler zu erfassen. Sieht gut aus oder? Skalieren Sie dies für einen 4-Byte-Zeiger. Es gibt 2 ^ 32 oder 4294967294 mögliche Werte. Von diesen ist nur EINER Wert korrekt, einer ist NULL, und Sie haben immer noch 4294967292 andere ungültige Fälle. Neu berechnen: Sie haben einen Test für 1 von (4294967292+ 1) ungültigen Fällen. Eine Wahrscheinlichkeit von 2.xe-10 oder 0 für die meisten praktischen Zwecke. Das ist die Sinnlosigkeit der NULL-Prüfung.

    
dirkgently 18.02.2009 20:01
quelle
0

Weißt du, ein neuer Treiber (zumindest unter Linux), der dazu in der Lage ist, wäre wahrscheinlich nicht so schwer zu schreiben.

Andererseits wäre es Unsinn, Ihre Programme so zu bauen. Es sei denn, Sie haben eine bestimmte spezifische und einmalige Verwendung für so etwas, ich würde es nicht empfehlen. Wenn Sie eine große Anwendung erstellen, die mit konstanten Zeiger-Gültigkeitsprüfungen geladen wird, wäre sie wahrscheinlich schrecklich langsam.

    
dicroce 09.03.2009 17:03
quelle
0

Dieser Artikel MEM10- C. Definieren und verwenden Sie eine Zeigerüberprüfungsfunktion , die besagt, dass es möglich ist, eine Überprüfung zu einem gewissen Grad durchzuführen, besonders unter Linux OS.

    
Marek Szanyi 11.04.2012 08:17
quelle
0
  

Sie sollten diese Methoden vermeiden, weil sie nicht funktionieren. blogs.msdn.com/oldnewthing/archive/2006/09/27/773741.aspx - JaredPar 15. Februar 09 um 16:02

Wenn sie nicht funktionieren - nächstes Windows Update wird es reparieren? Wenn sie nicht auf Konzeptebene funktionieren, wird die Funktion wahrscheinlich komplett aus Windows API entfernt.

MSDN-Dokumentation behaupten, dass sie verboten sind, und Grund dafür ist wahrscheinlich Fehler der weiteren Gestaltung der Anwendung (z. B. sollten Sie nicht in der Regel ungültige Zeiger essen - wenn Sie für das Design der gesamten Anwendung natürlich verantwortlich sind), und Leistung / Zeit der Zeigerüberprüfung.

Aber Sie sollten nicht behaupten, dass sie wegen eines Blogs nicht funktionieren. In meiner Testanwendung habe ich bestätigt, dass sie funktionieren.

    
TarmoPikaro 17.03.2014 05:59
quelle
0

Diese Links können hilfreich sein

_CrtIsValidPointer Überprüft, ob ein bestimmter Speicherbereich zum Lesen und Schreiben gültig ist (nur Debug-Version). Ссылка

_CrtCheckMemory Bestätigt die Integrität der im Debug-Heap reservierten Speicherblöcke (nur Debug-Version). Ссылка

    
Khachatur 12.04.2014 06:32
quelle
0

Das Folgende funktioniert in Windows (jemand hat es vorher vorgeschlagen):

statische Void-Kopie (void * Ziel, const void * Quelle, int Größe)  {      __Versuchen      {          CopyMemory (Ziel, Quelle, Größe);      }      __except (EXCEPTION_EXECUTE_HANDLER)      {          etwas (- was auch immer--);      }  }

Die Funktion muss statisch, standalone oder statisch einer Klasse sein. Kopieren Sie Daten im lokalen Puffer, um schreibgeschützt zu testen. Um beim Schreiben zu testen, ohne den Inhalt zu ändern, schreibe sie auf. Sie können nur die ersten / letzten Adressen testen. Wenn der Zeiger ungültig ist, wird die Kontrolle an 'doSomething' übergeben, und dann außerhalb der Klammern. Verwenden Sie einfach keine Destruktoren wie CString.

    
user2089173 01.09.2015 20:26
quelle

Tags und Links