2010-03-05 12 views
8

Sto provando a creare un programma compilato con GCC e utilizzando elementi intrinseci Qt e SSE. Sembra che quando una delle mie funzioni viene chiamata da Qt, l'allineamento dello stack non viene mantenuto. Ecco un breve esempio per illustrare quello che voglio dire:Qt, GCC, SSE e allineamento stack

#include <cstdio> 
#include <emmintrin.h> 
#include <QtGui/QApplication.h> 
#include <QtGui/QWidget.h> 


class Widget: public QWidget { 
public: 
    void paintEvent(QPaintEvent *) { 
     __m128 a; 
     printf("a: 0x%08x\n", ((void *) &a)); 
    } 
}; 


int main(int argc, char** argv) 
{ 
    QApplication application(argc, argv); 
    Widget w; 
    w.paintEvent(NULL); // Called from here, my function behaves correctly 
    w.show(); 
    w.update(); 
    // Qt will call Widget::paintEvent and my __m128 will not be 
    // aligned on 16 bytes as it should 
    application.processEvents(); 

    return 0; 
} 

ecco l'output:

a: 0x0023ff40 // OK, that's aligned on 16 bytes 
a: 0x0023d14c // Not aligned! 

Configurazione:

  • Intel Core2
  • WinXP, SP3
  • GCC 4.4 (Mingw incluso nel Qt SDK 2010.01)

ho provato a compilare il programma di esempio con le stesse opzioni come quelli che ho visto nel makefile Qt:

-O2 -Wall -frtti -fexceptions -mthreads 

, opzioni di collegamento:

-enable-stdcall-fixup -Wl,-enable-auto-import -Wl,-enable-runtime-pseudo-reloc -Wl,-s -mthreads 

Ora io non so in cui indicazioni per cercare Eventuali suggerimenti sarebbero apprezzati. Grazie!

Fabien

risposta

9

È possibile utilizzare l'opzione -mstackrealign di farlo senza l'aggiunta di attributi al codice sorgente:

-mstackrealign riallineare la pila in entrata. Su Intel x86, l'opzione -mstackrealign genererà un prologo ed un epilogo alternativi che riallinea lo stack di runtime se necessario. Questo supporta la combinazione di codici legacy che mantengono uno stack allineato a 4 byte con codici moderni che mantengono uno stack da 16 byte per la compatibilità SSE. Vedi anche l'attributo force_align_arg_pointer, applicabile alle singole funzioni.

(da the GCC docs)

+1

Grazie! Secondo http://eigen.tuxfamily.org/dox/WrongStackAlignment.html, sembra che sia meglio per le prestazioni utilizzare l'attributo force_align_arg_pointer. L'utilizzo di -mincoming-stack-boundary = 2 potrebbe essere un'altra soluzione (su Windows), in modo che "GCC sappia che è necessario prestare particolare attenzione per onorare l'allineamento a 16 byte". – Fabien

4
__attribute__((force_align_arg_pointer)) void paintEvent(QPaintEvent *); 

ha reso il lavoro! Qualcuno ha una soluzione migliore?

+0

Che cosa succede se si tenta di aggiungere '-mms-bitfields' alle opzioni del compilatore? –

Problemi correlati