Frage

Ich arbeite an Auto Vektorisierung mit GCC. Ich bin nicht in der Lage intrinsics zu verwenden oder Attribute Kundenanforderung durch. (Ich kann nicht von Benutzereingaben erhalten zu Vektorisierung unterstützen)

Wenn die Ausrichtungsinformation des Arrays, die unbekannt vektorisiert werden kann, ist, ruft GCC einen Durchlauf für ‚loop Versions‘. Schleifenversionierung wird ausgeführt, wenn Schleife Vektorisierung auf Bäumen durchgeführt wird. Wenn eine Schleife identifiziert werden vektorisierbar und die Einschränkung für die Datenausrichtung oder Datenabhängigkeit wird behindert, (weil sie nicht zur Kompilierungszeit bestimmt werden kann), dann werden zwei Versionen der Schleife erzeugt. Dies sind die vektorisiert und nicht-vektorisierten Versionen der Schleife zusammen mit Laufzeitprüfungen für die Ausrichtung oder die Abhängigkeit zu steuern, welche Version ausgeführt wird.

Meine Frage ist, wie wir die Ausrichtung durchzusetzen? Wenn ich eine Schleife gefunden habe, die vektorisierbare ist, soll ich nicht zwei Versionen der Schleife erzeugen wegen der fehlenden Ausrichtung Informationen.

Zum Beispiel. Betrachten Sie die folgenden Code

short a[15]; short b[15]; short c[15];
int i;

void foo()
{
    for (i=0; i<15; i++)
    {
      a[i] = b[i] ;
    }
}

Baum-Dump (Optionen: -fdump-tree-optimierte -ftree-vectorize)

<SNIP>
     vector short int * vect_pa.49;
     vector short int * vect_pb.42;
     vector short int * vect_pa.35;
     vector short int * vect_pb.30;

    bb 2>:
     vect_pb.30 = (vector short int *) &b;
     vect_pa.35 = (vector short int *) &a;
     if (((signed char) vect_pa.35 | (signed char) vect_pb.30) & 3 == 0)    ;; <== (A)
       goto <bb 3>;
     else
       goto <bb 4>;

    bb 3>:
</SNIP>

Bei 'bb 3' Version von vektorisierten Code erzeugt. Bei ‚bb 4‘ Code ohne Vektorisierung erzeugt. Diese werden durchgeführt, indem die Ausrichtung überprüft (Anweisung ‚A‘). Jetzt ohne intrinsics und andere Attribute verwenden, wie soll ich nur den vektorisierten Code erhalten (ohne diese Laufzeitvermessung).

War es hilfreich?

Lösung

Wenn die betreffenden Daten statisch zugeordnet werden, dann können Sie das __align__ Attribut, dass GCC angeben unterstützt, dass es auf die notwendige Grenze ausgerichtet werden soll. Wenn Sie dynamisch sind diese Arrays Zuteilung, können Sie über die Zuordnung eines durch den Ausrichtungswert und dann den zurückgegebenen Zeiger stoßen auf die Ausrichtung Sie benötigen.

Sie können auch die posix_memalign() Funktion verwenden, wenn Sie auf einem System sind, die es unterstützt. Schließlich ist zu beachten, dass immer malloc() Speicher auf die Größe des größten eingebauten Typs ausgerichtet zuzuordnen, in der Regel 8 Bytes für ein Doppel. Wenn Sie nicht besser brauchen als das, dann sollte malloc genügen.

Bearbeiten : Wenn Sie Ihre Zuordnung Code ändern, dass der Check zu zwingen, um wahr zu sein (das heißt overallocate, wie oben vorgeschlagen), sollte der Compiler zwingen, indem nicht die Schleife Code conditionalizing. Wenn Sie die Ausrichtung auf eine 8-Byte-Grenze erforderlich, wie es scheint, dass so etwas wie a = (a + 7) & ~3; wäre.

Andere Tipps

Ich bekomme nur eine Version der Schleife, mit Ihrem genauen Code mit diesen Optionen: gcc -march=core2 -c -O2 -fdump-tree-optimized -ftree-vectorize vec.c

Meine Version von GCC ist gcc version 4.4.1 (Ubuntu 4.4.1-4ubuntu8).

GCC tut etwas Gescheites hier. Es zwingt den Arrays a b und 16-Byte-ausgerichtet werden. Es macht das nicht c, vermutlich weil c nie in einer vektorisierbare Schleife verwendet wird.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top