Élimination d'allocations temporaires en...

44

Transcript of Élimination d'allocations temporaires en...

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Élimination d'allocations temporaires en Python

Alan Raynaud

Encadré par Serge GueltonProjet de �n d'étude Telecom-Bretagne

6èmes rencontres de la communauté française de compilation

Alan Raynaud Élimination d'allocations temporaires en Python

1.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Plan de la présentation

1 Contexte

2 Détection des allocations temporaires inutiles

3 Application à Pythran

4 Conclusion

Alan Raynaud Élimination d'allocations temporaires en Python

2.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Les générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

Plan de la présentation

1 ContexteLes générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

2 Détection des allocations temporaires inutilesObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

3 Application à PythranPythranApplicationRésultats

4 Conclusion

Alan Raynaud Élimination d'allocations temporaires en Python

3.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Les générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

Description (informelle) d'un générateur

Un générateur est un objet se comportant comme un itérateur,mais qui créé ses valeurs à la volée.

Alan Raynaud Élimination d'allocations temporaires en Python

4.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Les générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

Exemple

def squa r e ( n ) :fo r i n d e x in range ( n ) :

y i e l d n∗n

def f oo ( n ) :sum( squa r e ( n ) )

Alan Raynaud Élimination d'allocations temporaires en Python

5.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Les générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

List Comprehension et Generator Expression

Syntaxe concise permettant de créer des listes ou des générateurs.List Comprehension :

[ x ∗ x fo r x in range ( n ) ]

Generator Expression :

( x ∗ x fo r x in range ( n ) )

Alan Raynaud Élimination d'allocations temporaires en Python

6.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Les générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

Le module itertools Le module itertools contient desgénérateurs pouvant être utilisés et combinés dans un programmePython.imap est équivalent à map

map( lambda x : x ∗ x , [ 0 , 1 , 2 , 3 , 4 ] )> [ 0 , 1 , 4 , 9 , 1 6 ]

izip est équivalent à zip

z i p ( [ 1 , 2 , 3 ] , [ 4 , 5 , 6 ] )> [ ( 1 , 4 ) , ( 2 , 5 ) , ( 3 , 6 ) ]

ifilter est équivalent à filter

f i l t e r ( lambda x : x < 5 , [ 1 , 2 , 3 , 4 , 5 , 6 , 7 , 8 ] )> [ 1 , 2 , 3 , 4 ]

Alan Raynaud Élimination d'allocations temporaires en Python

7.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Les générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

Performances

0

0.002

0.004

0.006

0.008

0.01

0.012

0.014

0.016

0.018

0 10000 20000 30000 40000 50000 60000 70000 80000 90000 100000

Tem

ps d

’execution

N

Somme des x2 pour x entre 1 et N

Using mapUsing imap

Alan Raynaud Élimination d'allocations temporaires en Python

8.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Les générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

Python 3

Version de Python volontairement incompatible avec Python 2.

Changement notable : map, zip, �lter et range renvoient desgénérateurs et non plus des listes.

L'outil 2to3 e�ectue une conversion automatique mais peuoptimisée.

def f oo ( n ) :return z i p ( range ( n ) , range ( n ) )

devient

def f oo ( n ) :return l i s t ( z i p ( l i s t ( range ( n ) ) , l i s t ( range ( n ) ) ) )

Alan Raynaud Élimination d'allocations temporaires en Python

8.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Les générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

Python 3

Version de Python volontairement incompatible avec Python 2.

Changement notable : map, zip, �lter et range renvoient desgénérateurs et non plus des listes.

L'outil 2to3 e�ectue une conversion automatique mais peuoptimisée.

def f oo ( n ) :return z i p ( range ( n ) , range ( n ) )

devient

def f oo ( n ) :return l i s t ( z i p ( l i s t ( range ( n ) ) , l i s t ( range ( n ) ) ) )

Alan Raynaud Élimination d'allocations temporaires en Python

9.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Plan de la présentation

1 ContexteLes générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

2 Détection des allocations temporaires inutilesObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

3 Application à PythranPythranApplicationRésultats

4 Conclusion

Alan Raynaud Élimination d'allocations temporaires en Python

10.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Détection des allocations temporaires inutiles

Il y a une allocation temporaire inutile si on peut remplacer uneexpression produisant une liste par un générateur.

Objectif

Détecter les expressions pouvant êtres remplacées par ungénérateur.

Alan Raynaud Élimination d'allocations temporaires en Python

10.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Détection des allocations temporaires inutiles

Il y a une allocation temporaire inutile si on peut remplacer uneexpression produisant une liste par un générateur.

Objectif

Détecter les expressions pouvant êtres remplacées par ungénérateur.

Alan Raynaud Élimination d'allocations temporaires en Python

11.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Méthode

On parcourt l'AST (Abstract Syntax Tree) du programme Python.On va chercher à annoter les noeuds de l'AST avec une informationdu type �Peut être remplacé par un générateur�

Alan Raynaud Élimination d'allocations temporaires en Python

12.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Cas simples(1)

fo r e in i t e r :f oo ( e )

AST :For(expr target, expr iter, stmt* body, stmt* orelse)

On peut toujours annoter le noeud iter.

Alan Raynaud Élimination d'allocations temporaires en Python

12.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Cas simples(1)

fo r e in i t e r :f oo ( e )

AST :For(expr target, expr iter, stmt* body, stmt* orelse)

On peut toujours annoter le noeud iter.

Alan Raynaud Élimination d'allocations temporaires en Python

13.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Cas simples(2)

b1 = 5 in range (10)b2 = 5 not in range (10)

AST :Compare(expr left, cmpop op, expr comparator)

Si op = In ou NotIn, on peut annoter comparator.

Alan Raynaud Élimination d'allocations temporaires en Python

13.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Cas simples(2)

b1 = 5 in range (10)b2 = 5 not in range (10)

AST :Compare(expr left, cmpop op, expr comparator)

Si op = In ou NotIn, on peut annoter comparator.

Alan Raynaud Élimination d'allocations temporaires en Python

14.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Cas moins simple

f oo ( a , b , c )

AST :Call(expr func, expr* args, keyword* keywords, expr?

starargs, expr? kwargs)

Problème : comment savoir si les arguments peuvent être remplacéspar des générateurs ?

Alan Raynaud Élimination d'allocations temporaires en Python

14.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Cas moins simple

f oo ( a , b , c )

AST :Call(expr func, expr* args, keyword* keywords, expr?

starargs, expr? kwargs)

Problème : comment savoir si les arguments peuvent être remplacéspar des générateurs ?

Alan Raynaud Élimination d'allocations temporaires en Python

15.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

E�ets des fonctions sur leurs arguments

Proposition : Un argument passé à une fonction peut être remplacépar un générateur s'il n'est jamais modi�é et s'il est lu au plus unefois.

Objectif

Déterminer les arguments véri�ant ce critère pour chaque fonction.

Alan Raynaud Élimination d'allocations temporaires en Python

15.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

E�ets des fonctions sur leurs arguments

Proposition : Un argument passé à une fonction peut être remplacépar un générateur s'il n'est jamais modi�é et s'il est lu au plus unefois.

Objectif

Déterminer les arguments véri�ant ce critère pour chaque fonction.

Alan Raynaud Élimination d'allocations temporaires en Python

16.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Fonction de poids

On va dé�nir une fonction de poids qui renvoie le nombre de lectured'un paramètre formel d'une fonction donnée.u(foo, narg) = nombre de lecture du narg-ieme paramètre formelde foo

Alan Raynaud Élimination d'allocations temporaires en Python

17.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Cas des intrinsèques

Pour les intrinsèques, on dé�nit une table donnant explicitement lepoids des arguments.

Exemple :u(map,1) = 1

Alan Raynaud Élimination d'allocations temporaires en Python

17.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Cas des intrinsèques

Pour les intrinsèques, on dé�nit une table donnant explicitement lepoids des arguments.Exemple :u(map,1) = 1

Alan Raynaud Élimination d'allocations temporaires en Python

18.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Fonctions utilisateur

Méthode : On parcourt l'AST de la dé�nition de fonction pourconstruire la fonction de poids à partir des poids de chaque noeuds.

Une fois la construction de fonction de poids terminée, on peutl'évaluer pour obtenir les poids des arguments des fonctions.

Alan Raynaud Élimination d'allocations temporaires en Python

18.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Fonctions utilisateur

Méthode : On parcourt l'AST de la dé�nition de fonction pourconstruire la fonction de poids à partir des poids de chaque noeuds.Une fois la construction de fonction de poids terminée, on peutl'évaluer pour obtenir les poids des arguments des fonctions.

Alan Raynaud Élimination d'allocations temporaires en Python

19.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Exemple

def f oo (n , l1 , l 2 ) :i f (n<5):

f o r x i n l 1 : bar ( x , l 2 )e l s e :

bar (0 , l 2 )

If(cond, body, else) : cond + max(body, else)

For(iter,body) : iter + MAX * body1 if narg == 0 else 1 u(bar,1) if narg == 2 else 0

1 if narg == 1 else 0 u(bar,1) if narg == 2 else 0

Alan Raynaud Élimination d'allocations temporaires en Python

20.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Cycles et recursivité

Pour détecter les cycles, on mémorise le chemin lors de l'évaluation.(suite des appels à une autre fonction de poids).Exemple :foo -> bar -> jo -> foo -> ...

On estime le poids total du cycle de la façon suivante :Poids total = MAX * poids partiel

Alan Raynaud Élimination d'allocations temporaires en Python

21.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

ObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

Resumé

1 On calcule les fonctions de poids : directement pour lesintrinsèques, en parcourant l'AST pour les fonctions utilisateur.

2 On évalue les poids des arguments de toutes les fonctions.3 On annote l'AST : directement pour les noeuds NotIn, In, et

For. Si le poids est <=1 pour les arguments des noeuds Call.

Alan Raynaud Élimination d'allocations temporaires en Python

22.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

PythranApplicationRésultats

Plan de la présentation

1 ContexteLes générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

2 Détection des allocations temporaires inutilesObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

3 Application à PythranPythranApplicationRésultats

4 Conclusion

Alan Raynaud Élimination d'allocations temporaires en Python

23.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

PythranApplicationRésultats

Pythran en bref

Pythran :

Traduit un sous-ensemble de Python vers C++

Génère des modules utilisables depuis Python

Permet la parallélisation des opérations en utilisant desdirectives openMP.

Alan Raynaud Élimination d'allocations temporaires en Python

24.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

PythranApplicationRésultats

Chaine de compilation

Python Module [.py] Type InfoOpenMP

Pythran

C++boost::python pythonic++

g++

Native Module [.so]

Alan Raynaud Élimination d'allocations temporaires en Python

25.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

PythranApplicationRésultats

Pertinence

0

0.0005

0.001

0.0015

0.002

0.0025

0.003

0.0035

0.004

0.0045

0 100000 200000 300000 400000 500000 600000 700000 800000 900000 1e+06

Tem

ps d

’execution

N

Somme des x2 pour x entre 1 et N

En utilisant mapEn utilisant imap

Alan Raynaud Élimination d'allocations temporaires en Python

26.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

PythranApplicationRésultats

Insertion dans la chaine de compilation

Pythran dispose d'une phase d'optimisation qui travaille sur l'ASTdu programme Python avant la conversion en C++.

Réduction des expressions constantes.

Transformation des List Comprehension en combinaison defonctions.

Transformation des Generator Expressions en combinaison degénérateurs itertools.

Alan Raynaud Élimination d'allocations temporaires en Python

27.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

PythranApplicationRésultats

Optimisations à réaliser

range -> xrange

Fonction -> Équivalent itertools

List Comprehensions -> Generator Expressions

Alan Raynaud Élimination d'allocations temporaires en Python

28.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

PythranApplicationRésultats

Transformation des List Comprehension

Transformation triviale : remplacer un noeud ast.ListComp par unast.GeneratorExpression.

Alan Raynaud Élimination d'allocations temporaires en Python

29.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

PythranApplicationRésultats

Transformation des fonctions

Transformation moins triviale

def range ( n ) :foo = z i preturn map( lambda x , y : x∗y , foo ( range ( n ) , range ( n ) ) )

def bar ( n ) :return sum( range ( n ) )

Alan Raynaud Élimination d'allocations temporaires en Python

30.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

PythranApplicationRésultats

Cas particuliers

0

0.002

0.004

0.006

0.008

0.01

0.012

0.014

0.016

0.018

0 100000 200000 300000 400000 500000 600000 700000 800000 900000

tim

e

n

sum(map(lambda (x,y) : x+y, zip(range(n), range(n))))

With optimizationWithout optimization

Alan Raynaud Élimination d'allocations temporaires en Python

31.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

PythranApplicationRésultats

Cas moyen

Problème : Combien y a-t'il d'allocations temporaires inutiles dansun programme moyen ?

Su�samment pour justi�er les choix de Python 3.

Alan Raynaud Élimination d'allocations temporaires en Python

31.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

PythranApplicationRésultats

Cas moyen

Problème : Combien y a-t'il d'allocations temporaires inutiles dansun programme moyen ?Su�samment pour justi�er les choix de Python 3.

Alan Raynaud Élimination d'allocations temporaires en Python

32.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Plan de la présentation

1 ContexteLes générateurs de PythonLe module itertools pour Python 2.XLe cas Python 3

2 Détection des allocations temporaires inutilesObjectifAnnotation de l'ASTAnalyse interprocéduraleRésumé

3 Application à PythranPythranApplicationRésultats

4 Conclusion

Alan Raynaud Élimination d'allocations temporaires en Python

33.0

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Conclusion

Appliqué à Pythran, la méthode permet des gains deperformances signi�catifs dans les cas qui s'y prêtent.

D'autres applications sont possibles, comme l'amélioration de2to3, le convertisseur Python 2 vers Python 3.

Alan Raynaud Élimination d'allocations temporaires en Python

ContexteDétection des allocations temporaires inutiles

Application à PythranConclusion

Résumé

Contexte

En Python l'allocation de mémoire temporaire à un coût enperformances, mais il existe des outils pour y remédier.

Détection de mémoire temporaire inutile

Annotation des noeuds de l'AST où on pourrait utiliser ungénérateur.

Calcul de fonctions de poids pour déterminer si les argumentspassés à une fonction peuvent être annotés.

Application à Pythran

Implémentation de l'algorithme en Python.

Transformations éliminant les allocations temporaires inutiles.

Alan Raynaud Élimination d'allocations temporaires en Python