4.1.4 : CMakeLists.txt

Écrivons le fichier CMakeLists.txt :



On commence par définir le projet :
1
2
project(PERFORMANCE_WITH_NAN)
cmake_minimum_required(VERSION 3.0)


Ensuite, on inclue les macros que l'on a déjà développé pour le produit de hadamard :
1
include(${CMAKE_SOURCE_DIR}/Examples/1-HadamardProduct/multiplePerfTest.cmake)


On définie les différentes tailles de vecteurs qui seront les différents points de nos graphes (attention à avoir des multiples de 8 pour que les tests en fonctions intrisèques se passent bien) :
1
set(CONFIG_SQRT "512, 1024, 2048, 2664, 4096, 5008, 10000")


Définissions ce qu'est un NaN (qui se signal) :
1
set(NAN_DEF "std::numeric_limits<float>::signaling_NaN()")


Définissions ce qu'est un infini :
1
set(INF_DEF "std::numeric_limits<float>::infinity()")


Définissons un nombre dénormalisé :
1
set(DENORM_DEF "std::numeric_limits<float>::denorm_min()")


Testons avec le plus petit nombre possible (si on le multiplie par lui même il sera dénormalisé) :
1
set(MIN_TO_DENORM_DEF "std::numeric_limits<float>::min()")


Voici les trois sources de base pour tous les tests de performances de cette partie :
1
2
3
set(SQRT_BASE_SRC sqrt_base.cpp main_sqrt.cpp)
set(SQRT_VECTORIZE_SRC sqrt_vectorize.cpp main_sqrt.cpp)
set(SQRT_INTRINSICS_SRC sqrt_intrinsics.cpp main_sqrt.cpp)


Créons les tests de références :
1
2
3
multiplePerfTest("sqrtBase" sqrt base "" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})
multiplePerfTest("sqrtVectorize" sqrt vectorize "${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})
multiplePerfTest("sqrtIntrinsics" sqrt intrinsics "${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})


Nous pouvons également ajouter des graphes (mais il faut faire attention au nom des programmes que l'on compoare) :
1
2
phoenix_plotPerf("cmpSqrtSafe03" sqrt_base_O3 sqrt_vectorize_O3 sqrt_intrinsics_O3)
phoenix_plotPerf("cmpSqrtSafe0fast" sqrt_base_Ofast sqrt_vectorize_Ofast sqrt_intrinsics_Ofast)


Testons avec des NaN :
1
2
3
4
5
6
7
8
multiplePerfTestValue("sqrtBaseNanO3" sqrt base nan -O3 "${NAN_DEF}"
			"" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})

multiplePerfTestValue("sqrtVectorizeNanO3" sqrt vectorize nan -O3 "${NAN_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})

multiplePerfTestValue("sqrtIntrinsicsNanO3" sqrt intrinsics nan -O3  "${NAN_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})


Testons avec des Inf :
1
2
3
4
5
6
7
8
multiplePerfTestValue("sqrtBaseInfO3" sqrt base inf -O3 "${INF_DEF}"
			"" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})

multiplePerfTestValue("sqrtVectorizeInfO3" sqrt vectorize inf -O3 "${INF_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})

multiplePerfTestValue("sqrtIntrinsicsInfO3" sqrt intrinsics inf -O3  "${INF_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})


Testons avec des nombres dénormalisés :
1
2
3
4
5
6
7
8
multiplePerfTestValue("sqrtBaseDenormO3" sqrt base denorm -O3 "${DENORM_DEF}"
			"" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})

multiplePerfTestValue("sqrtVectorizeDenormO3" sqrt vectorize denorm -O3 "${DENORM_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})

multiplePerfTestValue("sqrtIntrinicsDenormO3" sqrt intrinsics denorm -O3 "${DENORM_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})


Essayons de régler le problème avec des nombres dénormalisés :
1
2
3
4
5
6
7
8
multiplePerfTestValue("sqrtBaseDenormDazO3" sqrt base denormDaz -O3 "${DENORM_DEF}"
			"${DENORM_DAZ_OPTION}" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})

multiplePerfTestValue("sqrtVectorizeDenormDazO3" sqrt vectorize denormDaz -O3 "${DENORM_DEF}"
			"${VECTORIZED_OPTION} ${DENORM_DAZ_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})

multiplePerfTestValue("sqrtIntrinicsDenormDazO3" sqrt intrinsics denormDaz -O3 "${DENORM_DEF}"
			"${VECTORIZED_OPTION} ${DENORM_DAZ_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})


Voyons ce qu'il se passe lorsque le calcul produit des nombres dénormalisés :
1
2
3
4
5
6
7
8
multiplePerfTestValue("sqrtBaseMakeDenormO3" sqrt base make_denorm -O3 "${MIN_TO_DENORM_DEF}"
			"" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})

multiplePerfTestValue("sqrtVectorizeMakeDenormO3" sqrt vectorize make_denorm -O3 "${MIN_TO_DENORM_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})

multiplePerfTestValue("sqrtIntrinicsMakeDenormO3" sqrt intrinsics make_denorm -O3 "${MIN_TO_DENORM_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})


Le fichier CMakeLists.txt complet :

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
project(PERFORMANCE_WITH_NAN)
cmake_minimum_required(VERSION 3.0)
include(${CMAKE_SOURCE_DIR}/Examples/1-HadamardProduct/multiplePerfTest.cmake)
set(CONFIG_SQRT "512, 1024, 2048, 2664, 4096, 5008, 10000")
set(NAN_DEF "std::numeric_limits<float>::signaling_NaN()")
set(INF_DEF "std::numeric_limits<float>::infinity()")
set(DENORM_DEF "std::numeric_limits<float>::denorm_min()")
set(MIN_TO_DENORM_DEF "std::numeric_limits<float>::min()")
set(SQRT_BASE_SRC sqrt_base.cpp main_sqrt.cpp)
set(SQRT_VECTORIZE_SRC sqrt_vectorize.cpp main_sqrt.cpp)
set(SQRT_INTRINSICS_SRC sqrt_intrinsics.cpp main_sqrt.cpp)

multiplePerfTest("sqrtBase" sqrt base "" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})
multiplePerfTest("sqrtVectorize" sqrt vectorize "${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})
multiplePerfTest("sqrtIntrinsics" sqrt intrinsics "${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})
phoenix_plotPerf("cmpSqrtSafe03" sqrt_base_O3 sqrt_vectorize_O3 sqrt_intrinsics_O3)
phoenix_plotPerf("cmpSqrtSafe0fast" sqrt_base_Ofast sqrt_vectorize_Ofast sqrt_intrinsics_Ofast)

multiplePerfTestValue("sqrtBaseNanO3" sqrt base nan -O3 "${NAN_DEF}"
			"" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})

multiplePerfTestValue("sqrtVectorizeNanO3" sqrt vectorize nan -O3 "${NAN_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})

multiplePerfTestValue("sqrtIntrinsicsNanO3" sqrt intrinsics nan -O3  "${NAN_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})
multiplePerfTestValue("sqrtBaseInfO3" sqrt base inf -O3 "${INF_DEF}"
			"" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})

multiplePerfTestValue("sqrtVectorizeInfO3" sqrt vectorize inf -O3 "${INF_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})

multiplePerfTestValue("sqrtIntrinsicsInfO3" sqrt intrinsics inf -O3  "${INF_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})
multiplePerfTestValue("sqrtBaseDenormO3" sqrt base denorm -O3 "${DENORM_DEF}"
			"" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})

multiplePerfTestValue("sqrtVectorizeDenormO3" sqrt vectorize denorm -O3 "${DENORM_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})

multiplePerfTestValue("sqrtIntrinicsDenormO3" sqrt intrinsics denorm -O3 "${DENORM_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})
multiplePerfTestValue("sqrtBaseDenormDazO3" sqrt base denormDaz -O3 "${DENORM_DEF}"
			"${DENORM_DAZ_OPTION}" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})

multiplePerfTestValue("sqrtVectorizeDenormDazO3" sqrt vectorize denormDaz -O3 "${DENORM_DEF}"
			"${VECTORIZED_OPTION} ${DENORM_DAZ_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})

multiplePerfTestValue("sqrtIntrinicsDenormDazO3" sqrt intrinsics denormDaz -O3 "${DENORM_DEF}"
			"${VECTORIZED_OPTION} ${DENORM_DAZ_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})
multiplePerfTestValue("sqrtBaseMakeDenormO3" sqrt base make_denorm -O3 "${MIN_TO_DENORM_DEF}"
			"" "${CONFIG_SQRT}" ${SQRT_BASE_SRC})

multiplePerfTestValue("sqrtVectorizeMakeDenormO3" sqrt vectorize make_denorm -O3 "${MIN_TO_DENORM_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_VECTORIZE_SRC})

multiplePerfTestValue("sqrtIntrinicsMakeDenormO3" sqrt intrinsics make_denorm -O3 "${MIN_TO_DENORM_DEF}"
			"${VECTORIZED_OPTION}" "${CONFIG_SQRT}" ${SQRT_INTRINSICS_SRC})


Vous pouvez le télécharger ici.

Il n'a fallu que quelques lignes pour créer tous les tests dont nous avons besoin.