Python a un package appelé llvmlite, ce qui était très utile! LLVM IR peut être produit facilement! Je pense que c'est une excellente première étape pour LLVM.
C'est pourquoi je vais essayer "d'installer llvmlite" - "essayer un peu"!
J'ai virtualisé et installé Ubuntu sur Windows 7 avec VirtualBox. Fondamentalement, s'il s'agit d'une distribution dérivée d'Ubuntu, cela fonctionnera. En fait, j'ai installé Linux Mint 17.3 (Cinnamon 64bit) avec la même procédure, mais cela fonctionne bien.
Hôte
Logiciel de virtualisation
OS invité
Nombre de processeurs
Mémoire
S'il ne s'agit pas d'environ 2 Go, LLVM make manquera de mémoire.
Préparez-vous à créer LLVM et à préparer l'environnement de développement Python 3.
$ sudo apt-get install build-essential cmake python3-dev python3-pip python3-setuptools zlib1g-dev libtool
llvmlite nécessite LLVM 3.6. Vous pouvez l'obtenir avec apt-get, mais je veux gérer le répertoire d'installation moi-même, donc je le construis moi-même.
$ wget http://llvm.org/releases/3.6.2/llvm-3.6.2.src.tar.xz
J'aime utiliser cmake. La construction de LLVM prend un certain temps, alors attendez patiemment. (Utilisez make -j4 pour la construction parallèle)
$ tar xvf llvm-3.6.2.src.tar.xz
$ cd llvm-3.6.2.src
$ mkdir build
$ cd build
$ cmake -D CMAKE_INSTALL_PREFIX=/usr/local/llvm-3.6 ..
$ make
$ sudo make install
Faites-le via le chemin vers LLVM
export LLVM_HOME=/usr/local/llvm-3.6
export PATH=${LLVM_HOME}/bin:${PATH}
export LD_LIBRARY_PATH=${LLVM_HOME}/lib:${LD_LIBRARY_PATH}
export LLVM_CONFIG=${LLVM_HOME}/bin/llvm-config
#Définissez également le chemin C include au cas où
export C_INCLUDE_PATH=${LLVM_HOME}/include:${C_INCLUDE_PATH}
export CPLUS_INCLUDE_PATH=${LLVM_HOME}/include:${CPLUS_INCLUDE_PATH}
$ llvm-config --version
3.6.2
Installez ce dont vous avez probablement besoin. Certains peuvent être inutiles. La bibliothèque Python est apt-get, pip, et il existe différentes méthodes d'installation. Seuls scipy et matplotlib ne pouvaient pas être exécutés avec pip, je l'ai donc installé avec apt-get.
$ sudo -E pip3 install numpy
$ sudo apt-get install python3-scipy python3-matplotlib
$ sudo -E pip3 install pandas statsmodels sympy
Installez rapidement llvmlite avec pip
$ sudo -E pip3 install llvmlite
C'est tout!
Essayons-le! Si vous pouvez exécuter le fichier Python suivant, cela fonctionne!
Voici un exemple que j'ai fait de manière appropriée.
from ctypes import CFUNCTYPE, c_int
import llvmlite.ir as ll
import llvmlite.binding as llvm
"""
Faites ceci avec LLVM IR.
def func(x, y):
a = x
b = y
c = 1000
d = a
return a + b + c + d
"""
#Initialisation
llvm.initialize()
llvm.initialize_native_target()
llvm.initialize_native_asmprinter()
i32 = ll.IntType(32)
# int func(int, int)
fnty = ll.FunctionType(i32, [i32, i32])
module = ll.Module()
func = ll.Function(module, fnty, name="func")
bb_entry = func.append_basic_block()
builder = ll.IRBuilder()
builder.position_at_end(bb_entry)
#Argument x, y
x, y = func.args
#Variable a,b,c,Définir d
ptr_a = builder.alloca(i32)
ptr_b = builder.alloca(i32)
ptr_c = builder.alloca(i32)
ptr_d = builder.alloca(i32)
# store
builder.store(x, ptr_a)
builder.store(y, ptr_b)
builder.store(ll.Constant(i32, 1000), ptr_c)
# load
a = builder.load(ptr_a)
b = builder.load(ptr_b)
c = builder.load(ptr_c)
#Stocker également
builder.store(a, ptr_d)
#Ajouter et retourner
ret1 = builder.add(a, b, name="res")
ret2 = builder.add(ret1, c, name="res2")
ret3 = builder.add(ret2, builder.load(ptr_d), name="res3")
builder.ret(ret3)
llvm_ir = str(module)
llvm_ir_parsed = llvm.parse_assembly(llvm_ir)
print("== LLVM IR ====================")
print(llvm_ir_parsed)
# pass
pmb = llvm.create_pass_manager_builder()
pmb.opt_level = 1
pm = llvm.create_module_pass_manager()
pmb.populate(pm)
pm.run(llvm_ir_parsed)
print("== LLVM IR(opt) ===============")
print(llvm_ir_parsed)
target_machine = llvm.Target.from_default_triple().create_target_machine()
print("== Result =====================")
with llvm.create_mcjit_compiler(llvm_ir_parsed, target_machine) as ee:
ee.finalize_object()
cfptr = ee.get_function_address("func")
cfunc = CFUNCTYPE(c_int, c_int, c_int)(cfptr)
res = cfunc(100, 2)
print("res: " + str(res))
== LLVM IR ====================
; ModuleID = '<string>'
target triple = "unknown-unknown-unknown"
define i32 @func(i32 %.1, i32 %.2) {
.4:
%.5 = alloca i32
%.6 = alloca i32
%.7 = alloca i32
%.8 = alloca i32
store i32 %.1, i32* %.5
store i32 %.2, i32* %.6
store i32 1000, i32* %.7
%.12 = load i32* %.5
%.13 = load i32* %.6
%.14 = load i32* %.7
store i32 %.12, i32* %.8
%res = add i32 %.12, %.13
%res2 = add i32 %res, %.14
%.16 = load i32* %.8
%res3 = add i32 %res2, %.16
ret i32 %res3
}
== LLVM IR(opt) ===============
; ModuleID = '<string>'
target triple = "unknown-unknown-unknown"
; Function Attrs: nounwind readnone
define i32 @func(i32 %.1, i32 %.2) #0 {
.4:
%factor = shl i32 %.1, 1
%res2 = add i32 %.2, 1000
%res3 = add i32 %res2, %factor
ret i32 %res3
}
attributes #0 = { nounwind readnone }
== Result =====================
res: 1202
En regardant LLVM IR (opt). Vous pouvez voir qu'il n'y a pas de partie inutile comme le magasin.
example Il existe également un exemple sur le Github d'origine, vous pouvez donc vous y référer. https://github.com/numba/llvmlite
La famille de têtes LLVM a un tutoriel appelé kaléidoscope. Ce qui suit est une implémentation de celui-ci avec llvmlite, ce qui est très utile, je vais donc le présenter.
https://github.com/eliben/pykaleidoscope
Recommended Posts