SlideShare une entreprise Scribd logo
1  sur  39
모두의 JIT 컴파일러
성우경
왓 스튜디오, 넥슨 코리아
발표자
성우경, 게임 개발자
<야생의 땅: 듀랑고> 서버 프로그래머
왓 스튜디오 / 넥슨 코리아
파이썬
파이썬은 인터프리터
소스코드를 직접 실행
빌드 없이, 바로 실행하기 때문에 디버깅이 편함
기계어를 직접 실행하지는 않음
그래서 컴파일된 언어보다 느림
JIT 컴파일
Just-in-time compilation
프로그램을 실제 실행하는 시점에 기계어로 컴파일
인터프리터 속도를 향상 시키는 방법
파이썬은 PyPy라는 JIT 컴파일러가 존재 1
3.62
7.43
CPython
2.7
PyPy
1.5
PyPy
5.7
속도
이번 발표는
PyPy를 다루지 않습니다.
PyPy 보다 좋게 만들 수도 없습니다…
간단한 JIT 컴파일러를 만드는 자리
소스코드는 github에 등록
어려운 거 아닐까?
소스코드를 기계어로 변환
기계어를 실행
다시 실행될 때 캐싱 된 기계어를 다시 실행
이 모든 것을 런타임에…
간단해요
직접 기계어를 변환하는 건 저에게도 너무 어려워요
파이썬엔 강력한 도구가 많고 그걸 사용하겠습니다
레시피
파이썬 코드 파싱 ast
C언어 변환 cython
컴파일 distutils
모듈 동적 로드 importlib
Cython
파이썬 문법을 기반
파이썬 코드를 C 언어로 변환
변환된 소스코드(C 언어)를 컴파일
컴파일된 모듈을 파이썬과 연동
Cython 코드
def integrate_f(double a, double b, int N):
cdef int i
cdef double s, dx
s = 0
dx = (b - a)/N
for i in range(N):
s += f(a + I * dx)
return s * dx
Cython
차이점은 변수 타입을 선언
선언하지 않아도 문제 없습니다
변수 타입을 지정하면 속도 증가
Cython 코드
def integrate_f(double a, double b, int N):
cdef int i
cdef double s, dx
s = 0
dx = (b - a)/N
for i in range(N):
s += f(a + I * dx)
return s * dx
JIT 컴파일 과정
JIT 컴파일 과정
JIT 함수 선언
JIT 함수 실행
Cython 코드 생성
C 코드 생성
컴파일
모듈 로드
실행
JIT 컴파일 과정
JIT 함수 선언
JIT 함수 실행(런타임)
Cython 코드 생성(런타임)
C 코드 생성(런타임)
컴파일(런타임)
모듈 로드(런타임)
실행
JIT 함수 선언
@jit
def f(I, J):
res = 0.0
for i in range(I):
for j in range (J * I):
res += 1
return res
데코레이터로 표시
이 함수가 실행되면 JIT 컴파일
JIT 함수 호출
result = f(1, 500) 호출 시 인자의 타입 정보를 가지고 JIT 컴파일 시작
1은 정수형
500도 정수형
Cython 코드 생성
def f(I, J):
res = 0.0
for i in range(I):
for j in range (J * I):
res += 1
return res
함수 내부의 변수 타입을 찾자(코드를 파싱)
import ast
import inspect
node = ast.parse(inspect.getsource(f))
Cython 코드 생성
def f(I, J):
res = 0.0
for i in range(I):
for j in range (J * I):
res += 1
return res
함수 코드의 AST(Abstract Syntax Tree) 추출
Cython 코드 생성
def f(I, J):
res = 0.0
for i in range(I):
for j in range (J * I):
res += 1
return res
변수 res 는 실수형
Cython 코드 생성
def f(I, J):
res = 0.0
for i in range(I):
for j in range (J * I):
res += 1
return res
변수 i, j 는 정수형
Cython 코드 생성
AST를 다시 코드로 변환하여 Cython 코드 생성 def jit_f(I, J):
res = 0.0
for i in range(I):
for j in range(J * I):
res += 1
return res
Cython 코드 생성
변수 타입 정보를 가지고 Cython 변수 선언
def jit_f(long I, long J):
cdef long j
cdef long i
cdef double res
res = 0.0
for i in range(I):
for j in range(J * I):
res += 1
return res
C 코드 생성
def jit_f(long I, long J):
cdef long j
cdef long i
cdef double res
res = 0.0
for i in range(I):
for j in range(J * I):
res += 1
return res
from Cython.Build.Dependencies import Cythonize
.....
Cythonize(.....)
.....
자동 생성된 C코드
C 코드 생성
컴파일
from distutils.command.build_ext import build_ext
build_extension = build_ext(.....)
.....
build_extension.run()
import imp
Cython_module = imp.load_dynamic(name, path)
f = Cython_module.jit_f
모듈 동적 로드
함수 f는 컴파일 된 함수(jit_f)로 교체
실행
result = f(1, 500)
result = jit_f(1, 500)
def jit(func):
def wrapper(*args, **kwargs):
func 코드를 Cython 코드로 변환
Cython 코드, C 코드 컴파일
모듈 동적 로드
return jit_func(*args, **kwargs)
return wrapper
실행
result = f(1, 500)
result = jit_f(1, 500)
컴파일 된 함수 jit_f(1, 500) 실행
1000000000.0 을 반환하여 result 에 저장
만약 또 f 함수가 실행 된다면?
이미 준비 된 jit_f를 바로 실행
성능
소수 찾기
def primes(kmax):
result = list()
p = [0 for i in range(1000)]
k = 0
n = 2
while k < kmax:
i = 0
while i < k and n % p[i] != 0:
i = i + 1
if i == k:
p[k] = n
k = k + 1
result.append(n)
n = n + 1
return result
def primes(kmax):
result = list()
p = [0 for i in range(1000)]
k = 0
n = 2
while k < kmax:
i = 0
while i < k and n % p[i] != 0:
i = i + 1
if i == k:
p[k] = n
k = k + 1
result.append(n)
n = n + 1
return result
성능
소수 찾기
2.7 배 증가
성능
예제 코드 def f(I, J):
res = 0.0
for i in range(I):
for j in range (J * I):
res += 1
return res
def f(I, J):
res = 0.0
for i in range(I):
for j in range (J * I):
res += 1
return res
성능
예제 코드
36 배 증가
결론
Python 코드를 기계어로 컴파일
컴파일 된 기계어를 로딩하여 실행
같은 코드가 반복 실행되면 캐싱 된 기계어를 직접 실행
위 과정을 런타임에 수행하는 JIT 컴파일러 구현
그러나
간단한 JIT 컴파일러의 제약
함수가 최초로 실행될 때 컴파일 시간이 필요합니다
Python  Cython  C  Binary  Run
자주 반복되지 않으면 직접 실행보다 느릴 수 있습니다
자주 반복되는 코드에 효과적
메모리 누수 발생 가능성?! 예외 처리?!
그래도
프로토타입은 Python 코드  LLVM 중간코드 생성
복잡한 과정 없이 단순하게 LLVM 중간코드 생성
성숙된 LLVM 기술 사용 가능
LLVM 중간코드 생성
@llvm.jit
def f(I, J):
res = 0.0
for i in range(I):
for j in range (J * I):
res += 1
return res
LLVM 중간코드 생성
@llvm.jit
def f(I, J):
res = 0.0
for i in range(I):
for j in range (J * I):
res += 1
return res
마지막으로
LLVM 을 사용하면 효과적인 JIT 컴파일러 제작
LLVM 을 설명하기에는 여백이 부족…
휼륭한 LLVM 기반 JIT 컴파일러가 존재?!
https://numba.pydata.org/
감사합니다

Contenu connexe

Tendances

Extending kubernetes with CustomResourceDefinitions
Extending kubernetes with CustomResourceDefinitionsExtending kubernetes with CustomResourceDefinitions
Extending kubernetes with CustomResourceDefinitionsStefan Schimanski
 
Machine Learning on Your Hand - Introduction to Tensorflow Lite Preview
Machine Learning on Your Hand - Introduction to Tensorflow Lite PreviewMachine Learning on Your Hand - Introduction to Tensorflow Lite Preview
Machine Learning on Your Hand - Introduction to Tensorflow Lite PreviewModulabs
 
Kubernetes extensibility: CRDs & Operators
Kubernetes extensibility: CRDs & OperatorsKubernetes extensibility: CRDs & Operators
Kubernetes extensibility: CRDs & OperatorsSIGHUP
 
Rust: Systems Programming for Everyone
Rust: Systems Programming for EveryoneRust: Systems Programming for Everyone
Rust: Systems Programming for EveryoneC4Media
 
Automated Python Test Frameworks for Hardware Verification and Validation
Automated Python Test Frameworks for Hardware Verification and ValidationAutomated Python Test Frameworks for Hardware Verification and Validation
Automated Python Test Frameworks for Hardware Verification and ValidationBarbara Jones
 
Cilium - Bringing the BPF Revolution to Kubernetes Networking and Security
Cilium - Bringing the BPF Revolution to Kubernetes Networking and SecurityCilium - Bringing the BPF Revolution to Kubernetes Networking and Security
Cilium - Bringing the BPF Revolution to Kubernetes Networking and SecurityThomas Graf
 
Docker and Go: why did we decide to write Docker in Go?
Docker and Go: why did we decide to write Docker in Go?Docker and Go: why did we decide to write Docker in Go?
Docker and Go: why did we decide to write Docker in Go?Jérôme Petazzoni
 
nexus helm 설치, docker/helm repo 설정과 예제
nexus helm 설치, docker/helm repo 설정과 예제nexus helm 설치, docker/helm repo 설정과 예제
nexus helm 설치, docker/helm repo 설정과 예제choi sungwook
 
Managing Multi-Tenant SaaS Applications at Scale
Managing Multi-Tenant SaaS Applications at ScaleManaging Multi-Tenant SaaS Applications at Scale
Managing Multi-Tenant SaaS Applications at ScaleMongoDB
 
Kata Container - The Security of VM and The Speed of Container | Yuntong Jin
Kata Container - The Security of VM and The Speed of Container | Yuntong Jin	Kata Container - The Security of VM and The Speed of Container | Yuntong Jin
Kata Container - The Security of VM and The Speed of Container | Yuntong Jin Vietnam Open Infrastructure User Group
 
Debug Your Kubernetes Network
Debug Your Kubernetes NetworkDebug Your Kubernetes Network
Debug Your Kubernetes NetworkHungWei Chiu
 
Docker Compose by Aanand Prasad
Docker Compose by Aanand Prasad Docker Compose by Aanand Prasad
Docker Compose by Aanand Prasad Docker, Inc.
 
How to Get Started With NGINX
How to Get Started With NGINXHow to Get Started With NGINX
How to Get Started With NGINXNGINX, Inc.
 
OpenShift Meetup - Tokyo - Service Mesh and Serverless Overview
OpenShift Meetup - Tokyo - Service Mesh and Serverless OverviewOpenShift Meetup - Tokyo - Service Mesh and Serverless Overview
OpenShift Meetup - Tokyo - Service Mesh and Serverless OverviewMaría Angélica Bracho
 
Les fonctions lambdas en C++11 et C++14
Les fonctions lambdas en C++11 et C++14Les fonctions lambdas en C++11 et C++14
Les fonctions lambdas en C++11 et C++14Aurélien Regat-Barrel
 
Static Analysis in Go
Static Analysis in GoStatic Analysis in Go
Static Analysis in GoTakuya Ueda
 
Docker introduction
Docker introductionDocker introduction
Docker introductionGourav Varma
 

Tendances (20)

Extending kubernetes with CustomResourceDefinitions
Extending kubernetes with CustomResourceDefinitionsExtending kubernetes with CustomResourceDefinitions
Extending kubernetes with CustomResourceDefinitions
 
Machine Learning on Your Hand - Introduction to Tensorflow Lite Preview
Machine Learning on Your Hand - Introduction to Tensorflow Lite PreviewMachine Learning on Your Hand - Introduction to Tensorflow Lite Preview
Machine Learning on Your Hand - Introduction to Tensorflow Lite Preview
 
Kubernetes extensibility: CRDs & Operators
Kubernetes extensibility: CRDs & OperatorsKubernetes extensibility: CRDs & Operators
Kubernetes extensibility: CRDs & Operators
 
Rust: Systems Programming for Everyone
Rust: Systems Programming for EveryoneRust: Systems Programming for Everyone
Rust: Systems Programming for Everyone
 
Automated Python Test Frameworks for Hardware Verification and Validation
Automated Python Test Frameworks for Hardware Verification and ValidationAutomated Python Test Frameworks for Hardware Verification and Validation
Automated Python Test Frameworks for Hardware Verification and Validation
 
Cilium - Bringing the BPF Revolution to Kubernetes Networking and Security
Cilium - Bringing the BPF Revolution to Kubernetes Networking and SecurityCilium - Bringing the BPF Revolution to Kubernetes Networking and Security
Cilium - Bringing the BPF Revolution to Kubernetes Networking and Security
 
Qemu Introduction
Qemu IntroductionQemu Introduction
Qemu Introduction
 
Intro To Docker
Intro To DockerIntro To Docker
Intro To Docker
 
Docker and Go: why did we decide to write Docker in Go?
Docker and Go: why did we decide to write Docker in Go?Docker and Go: why did we decide to write Docker in Go?
Docker and Go: why did we decide to write Docker in Go?
 
nexus helm 설치, docker/helm repo 설정과 예제
nexus helm 설치, docker/helm repo 설정과 예제nexus helm 설치, docker/helm repo 설정과 예제
nexus helm 설치, docker/helm repo 설정과 예제
 
Managing Multi-Tenant SaaS Applications at Scale
Managing Multi-Tenant SaaS Applications at ScaleManaging Multi-Tenant SaaS Applications at Scale
Managing Multi-Tenant SaaS Applications at Scale
 
Kata Container - The Security of VM and The Speed of Container | Yuntong Jin
Kata Container - The Security of VM and The Speed of Container | Yuntong Jin	Kata Container - The Security of VM and The Speed of Container | Yuntong Jin
Kata Container - The Security of VM and The Speed of Container | Yuntong Jin
 
Debug Your Kubernetes Network
Debug Your Kubernetes NetworkDebug Your Kubernetes Network
Debug Your Kubernetes Network
 
Docker Compose by Aanand Prasad
Docker Compose by Aanand Prasad Docker Compose by Aanand Prasad
Docker Compose by Aanand Prasad
 
How to Get Started With NGINX
How to Get Started With NGINXHow to Get Started With NGINX
How to Get Started With NGINX
 
OpenShift Meetup - Tokyo - Service Mesh and Serverless Overview
OpenShift Meetup - Tokyo - Service Mesh and Serverless OverviewOpenShift Meetup - Tokyo - Service Mesh and Serverless Overview
OpenShift Meetup - Tokyo - Service Mesh and Serverless Overview
 
Helm intro
Helm introHelm intro
Helm intro
 
Les fonctions lambdas en C++11 et C++14
Les fonctions lambdas en C++11 et C++14Les fonctions lambdas en C++11 et C++14
Les fonctions lambdas en C++11 et C++14
 
Static Analysis in Go
Static Analysis in GoStatic Analysis in Go
Static Analysis in Go
 
Docker introduction
Docker introductionDocker introduction
Docker introduction
 

En vedette

AI and Machine Learning Demystified by Carol Smith at Midwest UX 2017
AI and Machine Learning Demystified by Carol Smith at Midwest UX 2017AI and Machine Learning Demystified by Carol Smith at Midwest UX 2017
AI and Machine Learning Demystified by Carol Smith at Midwest UX 2017Carol Smith
 
PyCon Korea 2015: 탐색적으로 큰 데이터 분석하기
PyCon Korea 2015: 탐색적으로 큰 데이터 분석하기PyCon Korea 2015: 탐색적으로 큰 데이터 분석하기
PyCon Korea 2015: 탐색적으로 큰 데이터 분석하기Hyeshik Chang
 
실패한 오픈소스 공헌으로 배워가기
실패한 오픈소스 공헌으로 배워가기실패한 오픈소스 공헌으로 배워가기
실패한 오픈소스 공헌으로 배워가기Sung-Hee Kang
 
Python 게임서버 안녕하십니까 : RPC framework 편
Python 게임서버 안녕하십니까 : RPC framework 편Python 게임서버 안녕하십니까 : RPC framework 편
Python 게임서버 안녕하십니까 : RPC framework 편준철 박
 
PYCON 2017 발표자료 한성준
PYCON 2017 발표자료 한성준PYCON 2017 발표자료 한성준
PYCON 2017 발표자료 한성준sungjun han
 
아마존 에코를 활용한 음성 인식 에어컨 제어 A to z
아마존 에코를 활용한 음성 인식 에어컨 제어 A to z아마존 에코를 활용한 음성 인식 에어컨 제어 A to z
아마존 에코를 활용한 음성 인식 에어컨 제어 A to zJueun Seo
 
Pycon2017 이성용 Dances with the Last Samurai
Pycon2017 이성용 Dances with the Last SamuraiPycon2017 이성용 Dances with the Last Samurai
Pycon2017 이성용 Dances with the Last SamuraiSungYong Lee
 
[PYCON KOREA 2017] Python 입문자의 Data Science(Kaggle) 도전
[PYCON KOREA 2017] Python 입문자의 Data Science(Kaggle) 도전[PYCON KOREA 2017] Python 입문자의 Data Science(Kaggle) 도전
[PYCON KOREA 2017] Python 입문자의 Data Science(Kaggle) 도전Mijeong Park
 
파이썬으로 나만의 강화학습 환경 만들기
파이썬으로 나만의 강화학습 환경 만들기파이썬으로 나만의 강화학습 환경 만들기
파이썬으로 나만의 강화학습 환경 만들기정주 김
 

En vedette (9)

AI and Machine Learning Demystified by Carol Smith at Midwest UX 2017
AI and Machine Learning Demystified by Carol Smith at Midwest UX 2017AI and Machine Learning Demystified by Carol Smith at Midwest UX 2017
AI and Machine Learning Demystified by Carol Smith at Midwest UX 2017
 
PyCon Korea 2015: 탐색적으로 큰 데이터 분석하기
PyCon Korea 2015: 탐색적으로 큰 데이터 분석하기PyCon Korea 2015: 탐색적으로 큰 데이터 분석하기
PyCon Korea 2015: 탐색적으로 큰 데이터 분석하기
 
실패한 오픈소스 공헌으로 배워가기
실패한 오픈소스 공헌으로 배워가기실패한 오픈소스 공헌으로 배워가기
실패한 오픈소스 공헌으로 배워가기
 
Python 게임서버 안녕하십니까 : RPC framework 편
Python 게임서버 안녕하십니까 : RPC framework 편Python 게임서버 안녕하십니까 : RPC framework 편
Python 게임서버 안녕하십니까 : RPC framework 편
 
PYCON 2017 발표자료 한성준
PYCON 2017 발표자료 한성준PYCON 2017 발표자료 한성준
PYCON 2017 발표자료 한성준
 
아마존 에코를 활용한 음성 인식 에어컨 제어 A to z
아마존 에코를 활용한 음성 인식 에어컨 제어 A to z아마존 에코를 활용한 음성 인식 에어컨 제어 A to z
아마존 에코를 활용한 음성 인식 에어컨 제어 A to z
 
Pycon2017 이성용 Dances with the Last Samurai
Pycon2017 이성용 Dances with the Last SamuraiPycon2017 이성용 Dances with the Last Samurai
Pycon2017 이성용 Dances with the Last Samurai
 
[PYCON KOREA 2017] Python 입문자의 Data Science(Kaggle) 도전
[PYCON KOREA 2017] Python 입문자의 Data Science(Kaggle) 도전[PYCON KOREA 2017] Python 입문자의 Data Science(Kaggle) 도전
[PYCON KOREA 2017] Python 입문자의 Data Science(Kaggle) 도전
 
파이썬으로 나만의 강화학습 환경 만들기
파이썬으로 나만의 강화학습 환경 만들기파이썬으로 나만의 강화학습 환경 만들기
파이썬으로 나만의 강화학습 환경 만들기
 

Similaire à 모두의 JIT 컴파일러

NDC 2017 하재승 NEXON ZERO (넥슨 제로) 점검없이 실시간으로 코드 수정 및 게임 정보 수집하기
NDC 2017 하재승 NEXON ZERO (넥슨 제로) 점검없이 실시간으로 코드 수정 및 게임 정보 수집하기NDC 2017 하재승 NEXON ZERO (넥슨 제로) 점검없이 실시간으로 코드 수정 및 게임 정보 수집하기
NDC 2017 하재승 NEXON ZERO (넥슨 제로) 점검없이 실시간으로 코드 수정 및 게임 정보 수집하기Jaeseung Ha
 
Javascript개발자의 눈으로 python 들여다보기
Javascript개발자의 눈으로 python 들여다보기Javascript개발자의 눈으로 python 들여다보기
Javascript개발자의 눈으로 python 들여다보기지수 윤
 
사례를 통해 살펴보는 프로파일링과 최적화 NDC2013
사례를 통해 살펴보는 프로파일링과 최적화 NDC2013사례를 통해 살펴보는 프로파일링과 최적화 NDC2013
사례를 통해 살펴보는 프로파일링과 최적화 NDC2013Esun Kim
 
C++17 Key Features Summary - Ver 2
C++17 Key Features Summary - Ver 2C++17 Key Features Summary - Ver 2
C++17 Key Features Summary - Ver 2Chris Ohk
 
C언어 세미나 - 함수
C언어 세미나 - 함수C언어 세미나 - 함수
C언어 세미나 - 함수SeungHyun Lee
 
파이썬+함수이해하기 20160229
파이썬+함수이해하기 20160229파이썬+함수이해하기 20160229
파이썬+함수이해하기 20160229Yong Joon Moon
 
PS 향유회 세미나 - Python을 서브언어로 편하게 PS해보자
PS 향유회 세미나 - Python을 서브언어로 편하게 PS해보자PS 향유회 세미나 - Python을 서브언어로 편하게 PS해보자
PS 향유회 세미나 - Python을 서브언어로 편하게 PS해보자SesangCho
 
Boost 라이브리와 C++11
Boost 라이브리와 C++11Boost 라이브리와 C++11
Boost 라이브리와 C++11OnGameServer
 
C++20 Key Features Summary
C++20 Key Features SummaryC++20 Key Features Summary
C++20 Key Features SummaryChris Ohk
 
김민욱, (달빛조각사) 엘릭서를 이용한 mmorpg 서버 개발, NDC2019
김민욱, (달빛조각사) 엘릭서를 이용한 mmorpg 서버 개발, NDC2019김민욱, (달빛조각사) 엘릭서를 이용한 mmorpg 서버 개발, NDC2019
김민욱, (달빛조각사) 엘릭서를 이용한 mmorpg 서버 개발, NDC2019min woog kim
 
Python의 계산성능 향상을 위해 Fortran, C, CUDA-C, OpenCL-C 코드들과 연동하기
Python의 계산성능 향상을 위해 Fortran, C, CUDA-C, OpenCL-C 코드들과 연동하기Python의 계산성능 향상을 위해 Fortran, C, CUDA-C, OpenCL-C 코드들과 연동하기
Python의 계산성능 향상을 위해 Fortran, C, CUDA-C, OpenCL-C 코드들과 연동하기Ki-Hwan Kim
 
[조진현] [Kgc2011]direct x11 이야기
[조진현] [Kgc2011]direct x11 이야기[조진현] [Kgc2011]direct x11 이야기
[조진현] [Kgc2011]direct x11 이야기진현 조
 
NDC 2011, 네트워크 비동기 통신, 합의점의 길목에서
NDC 2011, 네트워크 비동기 통신, 합의점의 길목에서NDC 2011, 네트워크 비동기 통신, 합의점의 길목에서
NDC 2011, 네트워크 비동기 통신, 합의점의 길목에서tcaesvk
 
[NDC 2016] 유니티, iOS에서 LINQ 사용하기
[NDC 2016] 유니티, iOS에서 LINQ 사용하기[NDC 2016] 유니티, iOS에서 LINQ 사용하기
[NDC 2016] 유니티, iOS에서 LINQ 사용하기Daehee Kim
 

Similaire à 모두의 JIT 컴파일러 (20)

NDC 2017 하재승 NEXON ZERO (넥슨 제로) 점검없이 실시간으로 코드 수정 및 게임 정보 수집하기
NDC 2017 하재승 NEXON ZERO (넥슨 제로) 점검없이 실시간으로 코드 수정 및 게임 정보 수집하기NDC 2017 하재승 NEXON ZERO (넥슨 제로) 점검없이 실시간으로 코드 수정 및 게임 정보 수집하기
NDC 2017 하재승 NEXON ZERO (넥슨 제로) 점검없이 실시간으로 코드 수정 및 게임 정보 수집하기
 
IPython
IPythonIPython
IPython
 
Javascript개발자의 눈으로 python 들여다보기
Javascript개발자의 눈으로 python 들여다보기Javascript개발자의 눈으로 python 들여다보기
Javascript개발자의 눈으로 python 들여다보기
 
사례를 통해 살펴보는 프로파일링과 최적화 NDC2013
사례를 통해 살펴보는 프로파일링과 최적화 NDC2013사례를 통해 살펴보는 프로파일링과 최적화 NDC2013
사례를 통해 살펴보는 프로파일링과 최적화 NDC2013
 
C++17 Key Features Summary - Ver 2
C++17 Key Features Summary - Ver 2C++17 Key Features Summary - Ver 2
C++17 Key Features Summary - Ver 2
 
C언어 세미나 - 함수
C언어 세미나 - 함수C언어 세미나 - 함수
C언어 세미나 - 함수
 
파이썬+함수이해하기 20160229
파이썬+함수이해하기 20160229파이썬+함수이해하기 20160229
파이썬+함수이해하기 20160229
 
PS 향유회 세미나 - Python을 서브언어로 편하게 PS해보자
PS 향유회 세미나 - Python을 서브언어로 편하게 PS해보자PS 향유회 세미나 - Python을 서브언어로 편하게 PS해보자
PS 향유회 세미나 - Python을 서브언어로 편하게 PS해보자
 
강의자료 2
강의자료 2강의자료 2
강의자료 2
 
Boost 라이브리와 C++11
Boost 라이브리와 C++11Boost 라이브리와 C++11
Boost 라이브리와 C++11
 
C++20 Key Features Summary
C++20 Key Features SummaryC++20 Key Features Summary
C++20 Key Features Summary
 
김민욱, (달빛조각사) 엘릭서를 이용한 mmorpg 서버 개발, NDC2019
김민욱, (달빛조각사) 엘릭서를 이용한 mmorpg 서버 개발, NDC2019김민욱, (달빛조각사) 엘릭서를 이용한 mmorpg 서버 개발, NDC2019
김민욱, (달빛조각사) 엘릭서를 이용한 mmorpg 서버 개발, NDC2019
 
Python의 계산성능 향상을 위해 Fortran, C, CUDA-C, OpenCL-C 코드들과 연동하기
Python의 계산성능 향상을 위해 Fortran, C, CUDA-C, OpenCL-C 코드들과 연동하기Python의 계산성능 향상을 위해 Fortran, C, CUDA-C, OpenCL-C 코드들과 연동하기
Python의 계산성능 향상을 위해 Fortran, C, CUDA-C, OpenCL-C 코드들과 연동하기
 
Swift의 함수와 메소드
Swift의 함수와 메소드Swift의 함수와 메소드
Swift의 함수와 메소드
 
[조진현] [Kgc2011]direct x11 이야기
[조진현] [Kgc2011]direct x11 이야기[조진현] [Kgc2011]direct x11 이야기
[조진현] [Kgc2011]direct x11 이야기
 
06장 함수
06장 함수06장 함수
06장 함수
 
5 swift 기초함수
5 swift 기초함수5 swift 기초함수
5 swift 기초함수
 
NDC 2011, 네트워크 비동기 통신, 합의점의 길목에서
NDC 2011, 네트워크 비동기 통신, 합의점의 길목에서NDC 2011, 네트워크 비동기 통신, 합의점의 길목에서
NDC 2011, 네트워크 비동기 통신, 합의점의 길목에서
 
6 function
6 function6 function
6 function
 
[NDC 2016] 유니티, iOS에서 LINQ 사용하기
[NDC 2016] 유니티, iOS에서 LINQ 사용하기[NDC 2016] 유니티, iOS에서 LINQ 사용하기
[NDC 2016] 유니티, iOS에서 LINQ 사용하기
 

모두의 JIT 컴파일러

  • 1. 모두의 JIT 컴파일러 성우경 왓 스튜디오, 넥슨 코리아
  • 2. 발표자 성우경, 게임 개발자 <야생의 땅: 듀랑고> 서버 프로그래머 왓 스튜디오 / 넥슨 코리아
  • 4. 파이썬은 인터프리터 소스코드를 직접 실행 빌드 없이, 바로 실행하기 때문에 디버깅이 편함 기계어를 직접 실행하지는 않음 그래서 컴파일된 언어보다 느림
  • 5. JIT 컴파일 Just-in-time compilation 프로그램을 실제 실행하는 시점에 기계어로 컴파일 인터프리터 속도를 향상 시키는 방법 파이썬은 PyPy라는 JIT 컴파일러가 존재 1 3.62 7.43 CPython 2.7 PyPy 1.5 PyPy 5.7 속도
  • 6. 이번 발표는 PyPy를 다루지 않습니다. PyPy 보다 좋게 만들 수도 없습니다… 간단한 JIT 컴파일러를 만드는 자리 소스코드는 github에 등록
  • 7. 어려운 거 아닐까? 소스코드를 기계어로 변환 기계어를 실행 다시 실행될 때 캐싱 된 기계어를 다시 실행 이 모든 것을 런타임에…
  • 8. 간단해요 직접 기계어를 변환하는 건 저에게도 너무 어려워요 파이썬엔 강력한 도구가 많고 그걸 사용하겠습니다
  • 9. 레시피 파이썬 코드 파싱 ast C언어 변환 cython 컴파일 distutils 모듈 동적 로드 importlib
  • 10. Cython 파이썬 문법을 기반 파이썬 코드를 C 언어로 변환 변환된 소스코드(C 언어)를 컴파일 컴파일된 모듈을 파이썬과 연동 Cython 코드 def integrate_f(double a, double b, int N): cdef int i cdef double s, dx s = 0 dx = (b - a)/N for i in range(N): s += f(a + I * dx) return s * dx
  • 11. Cython 차이점은 변수 타입을 선언 선언하지 않아도 문제 없습니다 변수 타입을 지정하면 속도 증가 Cython 코드 def integrate_f(double a, double b, int N): cdef int i cdef double s, dx s = 0 dx = (b - a)/N for i in range(N): s += f(a + I * dx) return s * dx
  • 13. JIT 컴파일 과정 JIT 함수 선언 JIT 함수 실행 Cython 코드 생성 C 코드 생성 컴파일 모듈 로드 실행
  • 14. JIT 컴파일 과정 JIT 함수 선언 JIT 함수 실행(런타임) Cython 코드 생성(런타임) C 코드 생성(런타임) 컴파일(런타임) 모듈 로드(런타임) 실행
  • 15. JIT 함수 선언 @jit def f(I, J): res = 0.0 for i in range(I): for j in range (J * I): res += 1 return res 데코레이터로 표시 이 함수가 실행되면 JIT 컴파일
  • 16. JIT 함수 호출 result = f(1, 500) 호출 시 인자의 타입 정보를 가지고 JIT 컴파일 시작 1은 정수형 500도 정수형
  • 17. Cython 코드 생성 def f(I, J): res = 0.0 for i in range(I): for j in range (J * I): res += 1 return res 함수 내부의 변수 타입을 찾자(코드를 파싱) import ast import inspect node = ast.parse(inspect.getsource(f))
  • 18. Cython 코드 생성 def f(I, J): res = 0.0 for i in range(I): for j in range (J * I): res += 1 return res 함수 코드의 AST(Abstract Syntax Tree) 추출
  • 19. Cython 코드 생성 def f(I, J): res = 0.0 for i in range(I): for j in range (J * I): res += 1 return res 변수 res 는 실수형
  • 20. Cython 코드 생성 def f(I, J): res = 0.0 for i in range(I): for j in range (J * I): res += 1 return res 변수 i, j 는 정수형
  • 21. Cython 코드 생성 AST를 다시 코드로 변환하여 Cython 코드 생성 def jit_f(I, J): res = 0.0 for i in range(I): for j in range(J * I): res += 1 return res
  • 22. Cython 코드 생성 변수 타입 정보를 가지고 Cython 변수 선언 def jit_f(long I, long J): cdef long j cdef long i cdef double res res = 0.0 for i in range(I): for j in range(J * I): res += 1 return res
  • 23. C 코드 생성 def jit_f(long I, long J): cdef long j cdef long i cdef double res res = 0.0 for i in range(I): for j in range(J * I): res += 1 return res from Cython.Build.Dependencies import Cythonize ..... Cythonize(.....) .....
  • 24. 자동 생성된 C코드 C 코드 생성
  • 25. 컴파일 from distutils.command.build_ext import build_ext build_extension = build_ext(.....) ..... build_extension.run()
  • 26. import imp Cython_module = imp.load_dynamic(name, path) f = Cython_module.jit_f 모듈 동적 로드 함수 f는 컴파일 된 함수(jit_f)로 교체
  • 27. 실행 result = f(1, 500) result = jit_f(1, 500) def jit(func): def wrapper(*args, **kwargs): func 코드를 Cython 코드로 변환 Cython 코드, C 코드 컴파일 모듈 동적 로드 return jit_func(*args, **kwargs) return wrapper
  • 28. 실행 result = f(1, 500) result = jit_f(1, 500) 컴파일 된 함수 jit_f(1, 500) 실행 1000000000.0 을 반환하여 result 에 저장 만약 또 f 함수가 실행 된다면? 이미 준비 된 jit_f를 바로 실행
  • 29. 성능 소수 찾기 def primes(kmax): result = list() p = [0 for i in range(1000)] k = 0 n = 2 while k < kmax: i = 0 while i < k and n % p[i] != 0: i = i + 1 if i == k: p[k] = n k = k + 1 result.append(n) n = n + 1 return result
  • 30. def primes(kmax): result = list() p = [0 for i in range(1000)] k = 0 n = 2 while k < kmax: i = 0 while i < k and n % p[i] != 0: i = i + 1 if i == k: p[k] = n k = k + 1 result.append(n) n = n + 1 return result 성능 소수 찾기 2.7 배 증가
  • 31. 성능 예제 코드 def f(I, J): res = 0.0 for i in range(I): for j in range (J * I): res += 1 return res
  • 32. def f(I, J): res = 0.0 for i in range(I): for j in range (J * I): res += 1 return res 성능 예제 코드 36 배 증가
  • 33. 결론 Python 코드를 기계어로 컴파일 컴파일 된 기계어를 로딩하여 실행 같은 코드가 반복 실행되면 캐싱 된 기계어를 직접 실행 위 과정을 런타임에 수행하는 JIT 컴파일러 구현
  • 34. 그러나 간단한 JIT 컴파일러의 제약 함수가 최초로 실행될 때 컴파일 시간이 필요합니다 Python  Cython  C  Binary  Run 자주 반복되지 않으면 직접 실행보다 느릴 수 있습니다 자주 반복되는 코드에 효과적 메모리 누수 발생 가능성?! 예외 처리?!
  • 35. 그래도 프로토타입은 Python 코드  LLVM 중간코드 생성 복잡한 과정 없이 단순하게 LLVM 중간코드 생성 성숙된 LLVM 기술 사용 가능
  • 36. LLVM 중간코드 생성 @llvm.jit def f(I, J): res = 0.0 for i in range(I): for j in range (J * I): res += 1 return res
  • 37. LLVM 중간코드 생성 @llvm.jit def f(I, J): res = 0.0 for i in range(I): for j in range (J * I): res += 1 return res
  • 38. 마지막으로 LLVM 을 사용하면 효과적인 JIT 컴파일러 제작 LLVM 을 설명하기에는 여백이 부족… 휼륭한 LLVM 기반 JIT 컴파일러가 존재?! https://numba.pydata.org/