Comparaison c et sse2/3 (win32)

Soyez le premier à donner votre avis sur cette source.

Vue 9 264 fois - Téléchargée 619 fois

Description

Suite à discussion sur cette source:
http://www.cppfrance.com/code.aspx?ID=41170
voici la démo de comparaison.

IMPORTANT AVANT TOUT:
Lancer Excpt.exe, si affiche:
- ERR, alors STOP ne pas aller plus loin.
- 2, SSE2 prise en charge.
- 3, SSE3 ok, vous pourrez mettre en comment la ligne "#define BNSSE3NOT" de cumSSE.c et recompiler.
Le code de cela est également dans un zip, ne modifier QUE si vous savez ce que vous faites.
-------------------------

Un tableau de 6336 float est créé.
Il s'agit de retourner INT(SUM(SQRT(tabFloat))) avec la seule contrainte que si un float est < 1.0 alors le considérer 1.0, voila tout.
int __fastcall cumSqrt_C(float *pflt)
{
float f, r = 0.0;
int i = 6335;
do {
f = pflt[i];
r += ((f > 1.0) ? sqrt(f): 1.0);
} while(i--);
return (int) (r);
}

Le fichier cumSSE.c contient la version SSE2, le benef de perf est énorme. Si on augmente la taille tableau, les écarts deviennent rapidement abyssaux.
Il y a dialogbox pour tester les 2 à répétition.
Si qlq'un veut améliorer les perfs en C (fichier cumC.c ONLY) de qlq manière que ce soit, qu'il amène et on testera, je suis preneur.
Je précise que cet exe est déjà compilé option SSE2 et full optimisation.

Qu'on évite de continuer à se prendre le choux à se demander si c'est utile d'optimiser, quand on est payé pour (et pas trop mal), on a autre chose à faire que de philosopher là dessus.
Cette mini fonction est une des centaines contenues dans le calculateur, on boucle une centaine de fois avec contraintes différentes sur des dizaine de milliers d'enregistrement (1 ligne de float comme exemple par enreg).
Il est clair qu'un gros compte qui attend ses stats entre 2 fluctuations des cours de bourse se fout complètement (ou presque) du prix du calculateur et des specs matérielles demandées.
Code générique, portable, ceci cela et autre baliverne n'a rien à faire ici, on veut des perfs et basta.

Codes Sources

A voir également

Ajouter un commentaire Commentaires
gnairod
Messages postés
37
Date d'inscription
samedi 22 novembre 2008
Statut
Membre
Dernière intervention
11 avril 2010

20 mai 2010 à 11:32
Pardon je voulais dire sans coder en ASM ;)
gnairod
Messages postés
37
Date d'inscription
samedi 22 novembre 2008
Statut
Membre
Dernière intervention
11 avril 2010

20 mai 2010 à 10:43
J'aime bien cette source j'y retourne souvent :)

Pour ceux qui veulent des perfs mais sans coder en C ou bien tout simplement savoir comment utiliser les fonctions intrinseques. Voici mon code.

#include

/* RETOURNE INT(SOMME DES SQRT de 6336 FLOAT D'UN VECTEUR)
SI FLOAT < 1.0 ALORS SERA 1.0 */
int __fastcall cumSqrt_C(float *pflt)
{
const __declspec(align(16)) float MIN[] = { 1.0f, 1.0f, 1.0f, 1.0f };

__m128 mem;
__m128 min;
__m128 sum;

unsigned int i;

sum = _mm_setzero_ps();
min = _mm_load_ps(MIN);

for (i = 0; i < 6336; i += sizeof(__m128) / sizeof(int))
{
mem = _mm_load_ps(pflt + i);
mem = _mm_max_ps(mem, min);
mem = _mm_sqrt_ps(mem);
sum = _mm_add_ps(sum, mem);
}

sum = _mm_hadd_ps(sum, sum);
sum = _mm_hadd_ps(sum, sum);

return _mm_cvttss_si32(sum);
}

Code SSE3 car instruction haddps donc attention crash si proco ne supporte pas l'instruction.
gnairod
Messages postés
37
Date d'inscription
samedi 22 novembre 2008
Statut
Membre
Dernière intervention
11 avril 2010

22 déc. 2008 à 18:33
Brunews tu dis : "Si qlq'un veut améliorer les perfs en C (fichier cumC.c ONLY) de qlq manière que ce soit, qu'il amène et on testera, je suis preneur."

int __fastcall cumSqrt_C(float *pflt)
{
float f, r = 0.0f;
unsigned int i = 6335;
do {
f = pflt[i];
r += ((f > 1.0f) ? (float)sqrt(f): 1.0f);
} while(i--);

return (int) (r);
}

Est optimal, ce qui va entre en jeu cest le compilateur. Sera t-il capable de generer un code qui puisse rivalise avec le tiens ? La reponse est oui avec le compilo Intel (Verifie). Je t'accordes tout de meme que le prix est eleve et que l'inge fera tjr mieux que le compilateur, il est donc plus "interessant" d'embauche un/des gars pour faire ce boulot que d'achete un compilo hors de prix. Cependant y a pas bcp de monde qui a les competences pour faire du bon code ASM :)

PS :
Dans ton code ASM evite de lire par coupure dans la memoire. Tu perds qq cycles.
cs_max12
Messages postés
1491
Date d'inscription
dimanche 19 novembre 2000
Statut
Modérateur
Dernière intervention
7 juillet 2014

7 août 2008 à 05:03
Je retombait sur cette source par hasard et j'ai refais le test avec un autre matériel.

SSE2 663
C 5303

Intel Core Duo 2 T5600 1.83 GHZ
BruNews
Messages postés
21041
Date d'inscription
jeudi 23 janvier 2003
Statut
Modérateur
Dernière intervention
21 août 2019
19
12 août 2007 à 14:34
SUPER EXACT !!!

Je passe de 280 à 226, c'est toujours très loin des 74 en asm manuel mais c'est mieux.
Purée ce qu'on peut oublier par moments, peut-être début de sénilité...

Je m'étais pourtant demandé pourquoi le compilo générait 'addsd' au lieu de 'addss', ça crevait pourtant les yeux.
Merci.
Afficher les 60 commentaires

Vous n'êtes pas encore membre ?

inscrivez-vous, c'est gratuit et ça prend moins d'une minute !

Les membres obtiennent plus de réponses que les utilisateurs anonymes.

Le fait d'être membre vous permet d'avoir un suivi détaillé de vos demandes et codes sources.

Le fait d'être membre vous permet d'avoir des options supplémentaires.