nissy.dev

JSのコードが実行されるまで

4 min read
  • #note
目次

大きく分けて以下の 3 つのステップ経て、コードは実行される

  1. ソースコードを AST へパース
  2. ASTbytecode へ変換
  3. bytecode をランタイムが解釈

1. ソースコードを AST へパース

テキスト(文字列)であるソースコードを、 AST と呼ばれる構造化されたデータに変換する過程が最初のステップ

テキストは、コンパイラとよばれるプログラムによって parse = 品詞分解され、abstract syntax tree ( AST )に変換される

V8 では全てのコードを一度にパースするとかなり時間がかかることから、遅延パースの仕組みが実装されている

2. AST を bytecode へ変換

ランタイムがコードを実行できるように、 コンパイラによって ASTbytecode に変換する過程が次のステップになる
(V8 の紹介で「JS エンジン」という言葉よく聞くが、エンジン = コンパイラ + ランタイムである)

bytecode とは?

3. bytecode をランタイムが解釈

生成した bytecode を実行エンジン(インタプリタやランタイムなど)が解釈して実行する
現在の JS エンジンの多くは、それぞれ独自のパイプラインによって bytecode を実行させる

一般的な JS エンジンの実行パイプライン : bytecode -> baseline JIT -> optimized JIT

baseline JIT : 最適化がされていない機械語
optimized JIT : 最適化がされた機械語

JIT = Just In Time であり、多くの JS エンジンは実行時に最適化を行うことで実行速度を改善している

アセンブラとは?

アセンブリ言語とは、コンピュータ、マイクロコントローラ、その他のプログラム可能な機器を動作させるための機械語を人間にわかりやすい形で記述する、代表的な低水準言語である

引用:Wikipedia

2019 年に登場した JS エンジンについて

2019 年は、hermesquickjs という 2 つの JS エンジンが公開された

hermes

AOT (A head-Of-Time) とは?

実行時に最適化を行いながらコンパイルする JIT とは異なり、ビルド時 (実行時前) にコンパイルを実行する
これによって、TTI の改善が可能になっている (ちなみに V8 も JIT-less モードを持っている)

quickjs

参考文献