Tentativo di leggere o scrivere memoria protetta. Questo è spesso un'indicazione che l'altra memoria è corrotta


144

Spero che qualcuno mi possa illuminare su cosa potrebbe causare questo errore:

Tentativo di leggere o scrivere memoria protetta. Questo è spesso un'indicazione che l'altra memoria è corrotta.

Non riesco davvero a postare il codice perché questo errore sembra essere lanciato in qualsiasi area casuale dell'applicazione. L'applicazione funzionerà ovunque dalle 12 alle 48 ore prima di lanciare l'errore. A volte si interrompe in un punto apparentemente casuale e genera l'errore sopra, altre volte l'intera applicazione si interrompe e viene visualizzato uno schermo con un errore che dice qualcosa sulla falsariga di "Si è verificato un errore fatale in ... Questo potrebbe essere un bug nel CLR o ... "qualcosa su PInvoke o altre informazioni non rilevanti. Quando ciò accade, tutti i thread mostrano terminato e non sono disponibili informazioni di debug.

In breve, questo è ciò che fa l'applicazione:

È un'applicazione server multi-thread scritta interamente in C #. I client si connettono al server tramite socket. Il server esegue un "ambiente" virtuale per i client in cui possono interagire tra loro e l'ambiente. Consuma un bel po 'di memoria ma non vedo perdite. In genere consuma circa 1,5 GB. Non credo che perde perché l'uso della memoria rimane relativamente costante per tutto il tempo in cui l'applicazione è in esecuzione. È un codice costantemente in esecuzione per mantenere l'ambiente anche se i client non stanno facendo nulla. Non utilizza software di terze parti o altre API. Le uniche risorse esterne utilizzate da questa applicazione sono le connessioni socket e le connessioni al database SQL. Funziona su un server a 64 bit. Ho provato a eseguire il debug di questo in VS2008 e VS2010 usando .net 2.0, 3.5 e 4.

Ho provato a disattivare le ottimizzazioni del compilatore e diverse hot-fix di Microsoft. Nulla sembra risolvere questo problema. Sarebbe apprezzato se qualcuno conoscesse possibili cause o un modo per identificare ciò che sta causando il problema.


si prega di inviare l'intero stack di chiamate ...
Mitch Wheat

possibile duplicato di Risoluzione
Hans Passant,

Circa la metà delle volte non riesco a ottenere lo stack di chiamate. Se genera l'errore irreversibile di esecuzione, non ci sono informazioni di debug. Le volte che si ferma effettivamente da qualche parte nel codice, nulla sembra anormale. Ho anche attraversato tutti i thread attivi e non ho visto nulla che potesse causare un conflitto. Suppongo che la corruzione della memoria sia avvenuta qualche tempo prima che generasse l'errore.
Qualcun altro il

Verificare la presenza di vecchi componenti COM e ActiveX scadenti in uso. Conosco anche SQLCE come questo in un ambiente multithread.
leppie

Non ci sono componenti COM o ActiveX.
Qualcun altro il

Risposte:


50

Ho appena affrontato questo problema in VS 2013 .NET 4.5 con una DLL MapInfo. Risulta, il problema era che ho cambiato la piattaforma per la compilazione da x86 a qualsiasi CPU e questo è stato sufficiente per innescare questo errore. Il cambio in x86 ha fatto il trucco. Potrebbe aiutare qualcuno.


1
come lo hai cambiato con x86. Sto solo affrontando lo stesso problema con questa istruzione CSingleLock lock(&m_csMember, TRUE);. Per maggiori dettagli, ecco il mio post
ABCmo

In VS 2012/2013, vai a Proprietà progetto-> Crea e modifica "Target piattaforma" in base alle tue esigenze. Anche se penso che ci sia un altro posto in cui puoi cambiarlo, ma non riesco a trovarlo, penso che entrambi i modi dovrebbero raggiungere lo stesso risultato.
Sergey,


1
Il tuo problema può essere causato da molte cose, sono stato davvero sorpreso di aver risolto il mio problema cambiando la piattaforma di compilazione. Potresti dire una fuga fortunata.
Sergey

Questa soluzione in combinazione con questa risposta l'ha risolto per me.
Zach Posten,

23

Ho anche affrontato questo problema con Visual Studio (VS) 2010. Ancora più interessante, avevo diversi progetti nella mia soluzione (applicazione console, applicazione WPF, applicazione Windows Form) ma non funzionava solo quando, stavo impostando il tipo "Applicazione console" del progetto come progetto di avvio della soluzione (anche per quelli che non avevano letteralmente codice o assiemi aggiuntivi a parte quelli predefiniti forniti con il modello di progetto stesso).

La successiva modifica mi ha finalmente aiutato a risolvere il problema: vai alle proprietà del progetto del progetto dell'applicazione console (in alternativa, seleziona il file di progetto in Esplora soluzioni e premi Alt+ Entercombinazione di tasti) -> Vai alla Debugscheda -> Scorri fino alla Enable Debuggerssezione nel riquadro a destra -> Controlla la Enable unmanaged code debuggingcasella di controllo come mostrato nell'istantanea di seguito -> Fare clic sul Floppypulsante nella barra degli strumenti per salvare le proprietà del progetto. La causa principale del perché è successo non mi è ancora noto. L'unica cosa che ho osservato è che c'erano molti aggiornamenti di Windows che erano stati installati sul mio computer la notte precedente e che costituivano principalmente aggiornamenti di Office e aggiornamenti del sistema operativo (più di una dozzina di articoli KB).

inserisci qui la descrizione dell'immagine

Aggiornamento : VS 2017 in poi il nome dell'impostazione è cambiato come mostrato nello screenshot qui sotto:

inserisci qui la descrizione dell'immagine


1
A partire da VS 2017 questo è stato rinominato " Abilita debug del codice nativo "
Chiramisu il

1
Grazie a @Chiramisu per fornire informazioni aggiornate e aiutare la comunità. Ho aggiornato la risposta per renderla adatta alle versioni più recenti di Visual Studio.
RBT

19

Alla fine lo abbiamo rintracciato con l'aiuto di WinDBG e SOS. Una violazione di accesso veniva generata da alcune DLL sconosciute. Si scopre che un software chiamato "Nvidia Network Manager" stava causando i problemi. Ho letto innumerevoli volte in che modo questo problema può essere causato da firewall o antivirus, nessuno dei quali sto usando, quindi ho respinto questa idea. Inoltre, supponevo che non fosse ambientale perché si verifica su più di 1 server utilizzando hardware diverso. Si scopre che tutte le macchine su cui ho provato questo eseguivano "NVidia Network Manager". Credo che si installi con il resto dei driver della scheda madre.

Spero che questo aiuti qualcuno perché questo problema ha tormentato la mia domanda per molto tempo.


1
nel mio caso quando leggevo frequentemente i dati dal dispositivo il suo errore di lancio, ho dovuto interrompere il thread per qualche tempo usando Thread.Sleep (1000) per la lettura successiva. e funziona perfettamente.
JRB

6
Pensavo che la cura fosse "disinstallare NVidia Network Manager"
paulm

79
La risposta più votata che non fornisce alcuna risposta logica.
Teoman Shipahi,

Dubito di avere qualcosa in relazione a NVIDIA nella mia scheda madre o nel mio software. Sto usando Visual Studio 2010. Il problema si verifica solo durante il debug del progetto da VS. Il suo output exe dalla cartella di debug funziona perfettamente.
RBT,

1
Sto accedendo ai thread del mio processo che causano il problema.
Muhammad Saqib,

13

Il problema potrebbe essere dovuto a DLL di piattaforme di build miste nel progetto. cioè costruisci il tuo progetto su qualsiasi CPU ma hai alcune DLL nel progetto già costruite per la piattaforma x86. Ciò causerà arresti casuali a causa della diversa mappatura della memoria dell'architettura a 32 e 64 bit. Se tutte le DLL sono create per una piattaforma, il problema può essere risolto.



8

Questo errore non dovrebbe verificarsi nel codice gestito. Questo potrebbe risolvere il problema:

Vai a Visual Studio Debugger per ignorare questa eccezione:

Tools menu ->Options -> Debugging -> General -> Uncheck this option "Suppress JIT optimization on module load"

Spero che possa essere d'aiuto.


3
Mi dispiace che non abbia funzionato per te. Questo errore viene generato per molte ragioni, pensavo, la soluzione che ho pubblicato potrebbe risolvere il problema per qualcun altro se il motivo è l'ottimizzazione JIT.
curiousBoy,

6

Mi sono imbattuto e ho trovato una risoluzione a questa eccezione oggi. Si stava verificando quando stavo cercando di eseguire il debug di un unit test (NUnit) che chiamava un metodo virtuale su una classe astratta.

Il problema sembra riguardare l'installazione di .NET 4.5.1.

Ho scaricato .NET 4.5.2 e installato (i miei progetti fanno ancora riferimento a .NET 4.5.1) e il problema è stato risolto.

Fonte di soluzione:

https://connect.microsoft.com/VisualStudio/feedback/details/819552/visual-studio-debugger-throws-accessviolationexception


5

Potrebbe essere hardware. Potrebbe essere qualcosa di complicato ... ma mi piacerebbe suggerire che da qualche parte il tuo codice di threading non sta proteggendo alcune raccolte (come un dizionario) con un blocco appropriato.

Quale sistema operativo e service pack stai eseguendo?


1
Esecuzione di XP 64 SP2. Questo è accaduto su più server però. Ho passato tutto così tante volte e non vedo nulla che non sia sicuro. Inoltre non verrei visualizzato un errore modificato nella raccolta anziché una viloation di accesso?
Qualcun altro il

5

Ho avuto questo problema di recente quando ho cambiato il server di sviluppo per un progetto. Stavo ottenendo questo errore sulla riga di codice in cui ho dichiarato una nuova variabile OracleConnection.

Dopo aver provato molte cose, inclusa l'installazione di hotfix, ho provato a cambiare i riferimenti Oracle.DataAccess e System.Data.OracleClient nel progetto e ha funzionato!

Quando un progetto viene spostato su una nuova macchina, ti suggerisco di rinnovare tutti i riferimenti aggiunti in quel progetto.


4

Hai provato a disattivare DEP (Data Execution Prevention) per la tua applicazione?


2
Non sono sicuro che sia una buona idea. Potrebbe ritardare l'incidente ma a costo di fare più danni. Penso che l'idea migliore, se hai intenzione di andare in crash, è di andare in crash presto :-)
paxdiablo,

1
Disattivare DEP non è saggio ma è un utile esercizio diagnostico.
vcsjones,

4

Ho affrontato lo stesso problema. Il mio codice era una DLL .NET (estensione AutoCAD) in esecuzione all'interno di AutoCAD 2012. Sto anche usando Oracle.DataAccess e il mio codice generava la stessa eccezione durante ExecuteNonQuery (). Per fortuna ho risolto questo problema modificando la versione .net di ODP che stavo usando (ovvero, 2.x di Oracle.DataAccess)


sto affrontando lo stesso problema - autocad .net dll - puoi approfondire quale fosse il problema e la soluzione?
BKSpurgeon,

3

Questo problema è quasi sempre semplice. Il codice non è valido Raramente sono gli strumenti, solo da un'analisi statistica. Milioni di persone indicibili usano Visual Studio ogni giorno e forse alcuni usano il tuo codice - quale bit di codice sta ottenendo i test migliori? Garantisco che, se questo fosse un problema con VS, probabilmente lo avremmo già trovato.

Ciò che significa l'affermazione è che, quando provi ad accedere alla memoria che non è tua, di solito è perché lo stai facendo con un puntatore danneggiato, che proviene da qualche altra parte. Ecco perché afferma l'indicazione.

Con il danneggiamento della memoria, il rilevamento dell'errore è raramente vicino alla causa principale dell'errore. E gli effetti sono esattamente ciò che descrivi, apparentemente casuale. Devi solo guardare i soliti colpevoli, cose come:

  • puntatori non inizializzati o altri valori.
  • scrivendo più su un buffer che sulla sua dimensione.
  • risorse condivise da thread che non sono protetti da mutex.

Lavorare all'indietro da un problema come questo per trovare la causa principale è incredibilmente difficile dato che potrebbe essere successo così tanto tra la creazione del problema e il rilevamento del problema.

Trovo principalmente che sia più facile dare un'occhiata a ciò che è corrotto (diciamo, un puntatore specifico) e quindi fare un'analisi statica manuale del codice per vedere cosa potrebbe averlo corrotto, controllando i soliti colpevoli come mostrato sopra. Tuttavia, anche questo non colpirà lunghe catene di problemi.

Non ho abbastanza familiarità con VS per sapere, ma potresti anche voler esaminare la possibilità di utilizzare uno strumento di tracciamento della memoria (come valgrind per Linux) per vedere se è in grado di individuare eventuali problemi ovvi.


3
È inoltre possibile ottenere un puntatore danneggiato dalla memoria insufficiente. Se ciò non accade su un server con memoria ECC, provare un'utilità di test della memoria a esecuzione prolungata per eliminare l'hardware come causa.
cdonner

12
So che non è un problema hardware perché succede su più server. Grazie per aver indicato che c'è qualcosa di brutto nel capitano del codice ovvio. Non sto incolpando Visual Studio. Come detto l'applicazione funziona bene per un periodo di tempo casuale. Non è facile da riprodurre e ho cercato di identificare il problema per settimane.
Qualcun altro il

5
Qualcun altro: difficilmente penso che il nominativo ti aiuterà molto.
Mitch Wheat,

2
Qualcun altro, ho aiutato il più possibile le informazioni limitate che hai fornito. Anche il miglior dottore al mondo non può fare molto con un paziente che afferma semplicemente "Mi sono fatto male" :-) Se desideri fornire informazioni più specifiche, allora forse possiamo aiutarti di più.
paxdiablo,

5
Cattiva risposta, ma approccio, speculazione spudorata, ipotesi ingiustificate, nessuna soluzione fornita ... Perché questa risposta è ancora valida? E quali 3 persone avrebbero potuto votare questa risposta?
ThunderGr

3

Il codice verificabile non dovrebbe essere in grado di corrompere la memoria, quindi c'è qualcosa di non sicuro in corso. Stai utilizzando un codice non sicuro ovunque, ad esempio nell'elaborazione del buffer? Inoltre, le informazioni su PInvoke potrebbero non essere irrilevanti, in quanto PInvoke comporta una transizione al codice non gestito e il marshalling associato.

La mia migliore raccomandazione è quella di collegarsi a un'istanza bloccata e utilizzare WinDBG e SOS per approfondire ciò che sta accadendo al momento del crash. Questo non è per i deboli di cuore, ma a questo punto potrebbe essere necessario sbloccare strumenti più potenti per determinare cosa, esattamente, sta andando storto.


Indica PInvoke come possibile causa nel messaggio di errore. Non esiste un codice non sicuro. Proverò WinDBG. Grazie.
Qualcun altro il

3

Ok, questo potrebbe essere piuttosto inutile e semplicemente aneddotico, ma ...

Questa eccezione è stata lanciata costantemente da alcune librerie Twain32 che stavamo usando nel mio progetto, ma sarebbe avvenuta solo nella mia macchina.

Ho provato molte soluzioni suggerite su Internet, inutilmente ... Fino a quando non ho scollegato il mio cellulare (era collegato tramite USB).

E ha funzionato.

Si scopre che le librerie Twain32 stavano cercando di elencare il mio telefono come dispositivo compatibile Twain e qualcosa che ha fatto in quel processo ha causato quell'eccezione.

Vai a capire...


3

Ho riscontrato questo errore quando si utilizza pinvoke su un metodo che utilizza un riferimento a StringBuilder . Avevo usato il costruttore predefinito che apparentemente alloca solo 16 byte. Windows ha tentato di inserire più di 16 byte nel buffer e ha causato un sovraccarico del buffer.

Invece di

StringBuilder windowText = new StringBuilder(); // Probable overflow of default capacity (16)

Utilizzare una capacità maggiore:

StringBuilder windowText = new StringBuilder(3000);

2

nel mio caso il file era aperto e quindi bloccato.

Lo stavo ottenendo quando cercavo di caricare un file Excel usando LinqToExcel che era stato aperto anche in Excel.

questo è tutto ciò che ho fatto

    var maps = from f in book.Worksheet<NavMapping>()
                select f;
    try {
        foreach (var m in maps)
            if (!string.IsNullOrEmpty(m.SSS_ID) && _mappings.ContainsKey(m.SSS_ID))
                _mappings.Add(m.SSS_ID, m.CDS_ID);
    } catch (AccessViolationException ex) {
        _logger.Error("mapping file error. most likely this file is locked or open. " + ex);
    }

2

Ho avuto lo stesso errore in un progetto con cui stavo lavorando in VB.NET. Il controllo di "Abilita framework applicativo" nella pagina delle proprietà l'ha risolto per me.


1

ho avuto anche questo problema. stavo eseguendo diverse soluzioni contemporaneamente usando Visual Studio, quando chiudevo altre soluzioni ed eseguivo solo la soluzione di destinazione, ha funzionato bene senza quell'errore.


1

Ho ricevuto questo errore in modo casuale in VS1017, quando ho provato a costruire un progetto che stava costruendo perfettamente bene il giorno prima. Il riavvio del PC ha risolto il problema (ho anche eseguito il seguente comando in anticipo, non sono sicuro che sia necessario: netsh winsock reset)


1
Questa è esattamente la mia situazione con VS 2017 - System.AccessViolationException: tentativo di leggere o scrivere memoria protetta. Questo è spesso un'indicazione che l'altra memoria è corrotta. Ho semplicemente riavviato il PC per risolvere questo problema senza fare altro.
Hong

0

La mia risposta dipende molto dal tuo scenario, ma abbiamo riscontrato un problema nel tentativo di aggiornare un'applicazione .NET per un client di età> 10 anni in modo che potessero farlo funzionare su Windows 8.1. La risposta di @ alhazen è stata un po 'nel campo da baseball corretto per me. L'applicazione si basava su una DLL di terze parti che il client non voleva pagare per l'aggiornamento (Pegasus / Accusoft ImagXpress). Abbiamo riottimizzato l'applicazione per .NET 4.5 ma ogni volta che è stata eseguita la seguente riga abbiamo ricevuto il AccessViolationException was unhandledmessaggio:

UnlockPICImagXpress.PS_Unlock (1908228217,373714400,1341834561,28447);

Per risolverlo, abbiamo dovuto aggiungere il seguente evento post-build al progetto:

call "$(DevEnvDir)..\tools\vsvars32.bat"
"C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\bin\amd64\editbin.exe" /NXCOMPAT:NO "$(TargetPath)"

Questo specifica esplicitamente l'eseguibile come incompatibile con Prevenzione esecuzione dati. Per maggiori dettagli vedi qui .


0

In alcuni casi, ciò può accadere quando:

obj = new obj();
...
obj.Dispose();  // <-----------------    Incorrect disposal causes it
obj.abc...

0

Nel mio caso ho dovuto fare riferimento a una libreria C / C ++ usando P / Invoke, ma ho dovuto assicurarmi che la memoria fosse allocata per la prima volta nell'array di output usando fixed:

[DllImport("my_c_func_lib.dll", CharSet = CharSet.Ansi)]
public static extern unsafe int my_c_func(double input1, double input2, double pinput3, double *outData);

    public unsafe double[] GetMyUnmanagedCodeValue(double input1, double input2, double input3)
    {
        double[] outData = new double[24];

        fixed (double* returnValue = outData)
        {
            my_c_func(input1, input2, pinput3, returnValue);
        }

        return outData;
    }

Per i dettagli, consultare: https://www.c-sharpcorner.com/article/pointers-in-C-Sharp/


0

Questo è successo a me quando stavo eseguendo il debug della mia applicazione WinForms C # in Visual Studio. La mia applicazione effettua chiamate a cose Win32 tramite DllImport, ad es

[DllImport("Secur32.dll", SetLastError = false)]
private static extern uint LsaEnumerateLogonSessions(out UInt64 LogonSessionCount, out IntPtr LogonSessionList);

L'esecuzione di Visual Studio "come amministratore" ha risolto il problema per me.


0

Ho avuto lo stesso messaggio di errore:

System.AccessViolationException: tentativo di leggere o scrivere memoria protetta. Questo è spesso un'indicazione che l'altra memoria è corrotta.

Nel mio caso, l'errore è scomparso dopo aver pulito e ricostruito la soluzione.


0

Nel mio caso, l'utilità FTDI FT Prog stava lanciando l'errore durante la scansione dei dispositivi USB. Scollegare le mie cuffie Bluetooth dal PC risolto il problema.


0

Ho ricevuto questo messaggio di errore sull'espressione lambda che utilizzava Linq per filtrare una raccolta di oggetti. Quando ho ispezionato la collezione ho notato che i suoi membri non erano popolati - nella Localsfinestra, espanderli mostrava solo "...". Alla fine il problema era nel metodo di repository che inizialmente popolava la collezione - Dapper stava cercando di mappare automaticamente una proprietà di un oggetto nidificato. Ho corretto la query Dapper per gestire il multi-mapping e questo ha risolto l'errore di memoria.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.