ich versuch gerade, Vektorrechnung mit SSE zu implementieren. bekomm allerdings nur einen Fehler: SIGSEGV wobei... ich hab nicht wirklich seeehr viel Ahnung von SSE. Hab mir da so eine PDF- datei von AMD runtergeladen, und such mir da jeweils die Anweisungen zusammen
wobei die Zeile, bei der ich mir nicht sicher war, eigentlich die jeweils dritte war... Naja, der Fehler tritt in der zweiten auf
ach ja, das mit dem {$ifdef amd64} stimmt das so? muss ich da noch seperat intel64 abfragen? Und wie kann ich Lazarus eigentlich sagen, es soll für x64 kompilieren?
ich weiß grad nicht ob das bei dir der fehler ist, aber als ich letzte Woche mit SSE2 rumgespielt habe, bekam ich hin und wieder auch solche abstürze die eigentlich keinen ersichtlichen Grund hatten.
Für SSE2 müßen die daten im Speicher 16byte-aligned sein. Also nicht der Buffer (in deinem Fall 4xFloat = 16byte) muß durch 16 teilbar sein, sondern die Speicheradresse!
@Aya: ja, dürfte das Problem sein. Ich weiß jetzt zwar nicht zweifelsfrei, ob eax oder edx durch 16 teilbar ist, aber definitiv nicht beide. Und anhand der Sigsegv vermute ich mal, dass eax teilbar ist und edx nicht.
müsste ich jetzt wohl irgendwie so machen, dass meine TVec4 immer an einer durch 16 teilbaren adresse sind... weiß wer, wie das geht? der c++ code bringt mich jetzt auch wenig weiter, weil ich nicht mal versteh, was da eigentlich gemacht wird
Registriert: Di Okt 03, 2006 14:07 Beiträge: 1277 Wohnort: Wien
Was Aya macht: sie holt sich einen Datenpuffer, der 15 bytes größer ist als man braucht und das ermöglicht dann, dass man an eine gültige Beginn-Position "rutschen" kann.
Registriert: Di Okt 03, 2006 14:07 Beiträge: 1277 Wohnort: Wien
Dort wo Du's brauchst, schaltest Du es ein, und wenn Du es nicht mehr brauchst, schaltest Du es aus: http://www.freepascal.org/docs-html/user/userap6.html, diese Seite ist ein Auszug aus dem Free Pascal Users Guide, siehe erste Compiler Direktive ganz oben.
Hab noch was vergessen, nämlich den Source-Nachweis: laut dem FPC Programmers Guide ist "$ALIGN" eine lokale Compiler Direktive, das heißt, sie wirkt ab dem Zeitpunkt, wo sie eingeschaltet wird. Nachzulesen hier: http://www.freepascal.org/docs-html/prog/progch1.html#x6-40001
diese Seite ist ein Auszug aus dem Free Pascal Users Guide, siehe erste Compiler Direktive ganz oben.
gut. ich muss es ein und ausschalten. Aber wo muss ich es ein und ausschalten. vor der record definition einschalten bringts nicht, und dort, wo ich das record benutze auch nicht.
probier doch mal von Hand ob es überhaupt klappt, ich merke leider grad das meine Delphi-Syntax-Erinnerungen mehr oder weniger weg sind.. deswegen mal so halb pseudo code mäßig:
Code:
TVec4 ^myVec; Byte ^myVecPtr; // Mußt du erstellen, alloc(sizeof(TVec4) + 15) oder so.
myVec = Ptr((Integer(myVecPtr) + $F) AND NOT $F);
Damit ist myVec dann ein Pointer der 16-byte aligend ist.
Das "&" von C entspricht in delphi dem "AND", das "~" dem "NOT".
Aya
EDIT: Wo ich keine Ahnung habe wie das in FPC geht ist das Pointer -> Integer -> Pointer casten bei 64bit. Unter C++ nehm ich für Pointer einfach grundsätzlich 64-Bit Integers, die funktionieren dann auch auf 32Bit Systemen. Wie das bei FPC ist - keine ahnung
von Hand klappts mehr oder weniger. Die Ptr funktion macht irgendwas ganz komisches, also hab ich den Teil in asm gemacht. Nur halt von den Operatoren (bzw allgemein funktionen) müsst ich mich dann wohl verabschieden, weil da kann ich wohl nicht kontrollieren, wo der result hinschreibt. Jetzt kommt die Sigsegv nämlich beim zurückschreiben ins result. Und.. die 7 Zeilen zum erzeugen von einem gültigen Vektor gefallen mir auch nicht wirklich. Mal abgesehen davon, dass ich keine Ahnung hab, wie ich das ding dann wieder freigeben soll, ohne den Originalpointer auch noch zu speichern.
Registriert: Di Okt 03, 2006 14:07 Beiträge: 1277 Wohnort: Wien
Das Ganze scheint allerdings mehr zu benötigen als nur ein Alignment. Ich habe grade Folgendes gefunden: http://wiki.freepascal.org/Improving_language_shootout_results, und dort ist die Rede von einer zusätzlichen Compiler-Direktive namens "Cfsse2", mitsamt Code-Beispiel.
Allerdings muss ich mich jetzt leider ausklinken, weil ich einen Termin habe, sorry.
Hab das ganze zwar mal zum Laufen gebracht, indem ich movups (unaligned) statt movaps (aligned) verwende, aber das Problem löst das nicht (bzw nicht perfekt - Irgendwie geht es damit schon... und wenns jetzt auch noch ein addups gäbe...). Grundsätzlich funktionierts. Nur halt siehts nicht ganz so aus, wie ich mir das vorstelle.
Registriert: Do Sep 02, 2004 19:42 Beiträge: 4158
Programmiersprache: FreePascal, C++
Das kommt jetzt etwas spät, ich weiß. Aber wenn du nicht gerade scharf darauf bist, das alles selber zu machen, möchtest du vielleicht einen Blick auf die Unit "mmx", die bei FPC dabei ist, werfen.
greetings
_________________ If you find any deadlinks, please send me a notification – Wenn du tote Links findest, sende mir eine Benachrichtigung. current projects: ManiacLab; aioxmpp zombofant network • my photostream „Writing code is like writing poetry“ - source unknown
„Give a man a fish, and you feed him for a day. Teach a man to fish and you feed him for a lifetime. “ ~ A Chinese Proverb
Registriert: Di Mai 18, 2004 16:45 Beiträge: 2623 Wohnort: Berlin
Programmiersprache: Go, C/C++
gcc, fpc, und vsc++ haben builtin variablen und funktionen für SIMD. Erstens ist ein 128Bit variable notwendig, dies geht unter vsc++ und gcc mit folgendem
//hilfsstruktur für elementeweises zugreifen union f4vector { v4sf v; float f[4]; };
Funktionen kann man bei beiden direkt( __builtin_ia32_shufps() ) oder indirekt( f4vector a,b; a+=b; ) ansprechen. Damit er weiß, welche optimierung er nutzen soll, gibt man in den compiler optionen das SIMD Featureset an also SSE1-5 oder MMX. GCC kann zusätzlich noch pro Funktion die optimierung ändern und z.B. in eine binary jede SIMD variante einbetten und zur laufzeit dann vom usercode entsprechend aufgerufen werden.
FPC, hier ist es genauso, man hat 128Bit Variablen und über compiler setting wird dann das jeweilige SIMD Featureset genutzt. Der Vorteil hier ist, dass man kein 32/64Bit-, sowie CPU- und Platform-abhängigen Code schreibt. Ich weiß leider nicht mehr den datentyp, ich hab das auch früher kaum genutzt.
_________________ "Wer die Freiheit aufgibt um Sicherheit zu gewinnen, der wird am Ende beides verlieren" Benjamin Franklin
gcc, fpc, und vsc++ haben builtin variablen und funktionen für SIMD.
Wenn ich mich da irgendwann einigermaßen zurechtfinde, werd ich mir das auch noch ansehen. Momentan gehts mir aber eher darum, das selber zu machen. Trotzdem gut zu wissen.
Mitglieder in diesem Forum: 0 Mitglieder und 5 Gäste
Du darfst keine neuen Themen in diesem Forum erstellen. Du darfst keine Antworten zu Themen in diesem Forum erstellen. Du darfst deine Beiträge in diesem Forum nicht ändern. Du darfst deine Beiträge in diesem Forum nicht löschen. Du darfst keine Dateianhänge in diesem Forum erstellen.