In che modo l'aggiunta di dati a un segmento nella memoria flash può rovinare i tempi di un programma?

StackOverflow https://stackoverflow.com/questions/129911

Domanda

Ho un'app integrata in tempo reale con il ciclo principale a 10KHz. Funziona su una TI TMS320C configurata per l'avvio da flash. Di recente ho aggiunto un array inizializzato a un file sorgente, e all'improvviso i tempi sono sbagliati (in un modo troppo complesso per spiegare bene - essenzialmente una scrittura seriale della porta non si completa più in tempo.)

Le cose su questo che mi sconcertano:

  • Sto nemmeno accedendo ai nuovi dati , sto solo dichiarando un array inizializzato.
  • Dipende dalle dimensioni - il problema si presenta solo se l'array è & 40 parole.
  • So che non sto traboccando di segmenti di dati nella mappa dei collegamenti.
  • Non esiste la memorizzazione nella cache dei dati, quindi non è dovuto all'interruzione della coerenza della cache.

Qualche idea su come il semplice aumento delle dimensioni del segmento .cinit in flash possa influire sui tempi del tuo codice?

Informazioni aggiuntive:
Ho considerato che forse il codice era stato spostato, ma è ben separato dai dati. Ho verificato attraverso la mappa di memoria che tutti i segmenti di codice hanno gli stessi indirizzi prima e dopo il bug. Ho anche verificato che nessuno dei segmenti è pieno: gli unici indirizzi che cambiano nella mappa sono pochi nella sezione .cinit. Quella sezione contiene valori di dati usati per inizializzare le variabili in ram (come il mio array). Non dovrebbe mai essere accessibile dopo che è stato chiamato main ().

È stato utile?

Soluzione 5

Dopo più di un giorno a fissare tracce e generato assemblaggi, penso di averlo capito. Il problema della causa principale si è rivelato essere un problema di progettazione che ha causato anomalie solo se l'ISR che ha dato il via alla scrittura della porta seriale si è scontrato con una priorità più alta. Il tempismo ha appena scoperto che ci sono volute solo l'aggiunta di alcune istruzioni extra a un loop per far collidere i due interrupt.

Quindi la domanda diventa: in che modo l'archiviazione, ma non l'accesso, di dati aggiuntivi nella memoria flash provoca l'esecuzione di ulteriori istruzioni?

Sembra che la risposta sia correlata, ma non è la stessa, ai suggerimenti di Frosty e Frederico. Il nuovo array sposta alcune variabili esistenti, ma non oltre i confini della pagina o verso regioni più lente (su questa scheda, i tempi di accesso dovrebbero essere gli stessi per tutte le regioni). Ma cambia gli offset di alcune strutture a cui si accede frequentemente, il che fa sì che l'ottimizzatore emetta sequenze di istruzioni leggermente diverse per accedervi. Un allineamento dei dati può causare uno stallo della pipeline di un ciclo, mentre l'altro no. E quelle poche istruzioni hanno spostato i tempi abbastanza per esporre il problema di fondo.

Altri suggerimenti

I miei sospetti indicherebbero un cambiamento nell'allineamento tra i tuoi dati / codice e il supporto / memoria sottostante. L'aggiunta ai tuoi dati cambierebbe le posizioni della memoria nel tuo heap (a seconda del modello di memoria) e potrebbe mettere il tuo codice oltre un limite di "pagina" sul dispositivo flash causando latenza che prima non c'era.

Forse il nuovo array allocato staticamente trasferisce i dati esistenti in aree di memoria più lente, causando un rallentamento degli accessi a tali dati?

Il problema si ripresenta se l'array è l'ultima cosa nel suo spazio di indirizzamento? Altrimenti, guardando nella tua mappa, prova a spostare la dichiarazione dell'array in modo che, una ad una, le cose posizionate dopo di essa vengano mischiate per essere prima di essa. In questo modo è possibile individuare l'oggetto rilevante e iniziare a capire perché lo spostamento provoca il ritardo.

Mi rischierei e affermerei che non hai un problema di prestazioni qui, piuttosto un qualche tipo di corruzione della memoria che sintomi come un problema di prestazioni. Aggiunta di un array al file eseguibile modificando l'immagine della memoria. Quindi la mia ipotesi sarà che tu abbia una corruzione della memoria per lo più innocua (ovvero la sovrascrittura di una parte della memoria non utilizzata) e lo spostamento della memoria di oltre 40 byte causano un grave problema alla corruzione della memoria. Qual è una vera domanda

L'inizializzazione potrebbe sovrascrivere un altro pezzo di codice adiacente? Esistono strutture o variabili che utilizzano l'array, che ora sono più grandi e potrebbero causare uno stackoverflow?

Potrebbe trattarsi anche di un conflitto bancario o di pagina. Forse hai due routine che sono chiamate abbastanza spesso (gestori di interruzione o giù di lì) che sono state sulla stessa pagina e ora sono divise in due pagine.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top