Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Sign up for free
Menu
Search
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Pricing
Search
Sign in
Sign up for free
jsmini JavaScript Engine を作ってみた話
Search
Yosuke Furukawa
PRO
July 25, 2026
Programming
410
0
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
jsmini JavaScript Engine を作ってみた話
Qiita Tech Festa 2026 で発表
Yosuke Furukawa
PRO
July 25, 2026
More Decks by Yosuke Furukawa
See All by Yosuke Furukawa
Webの地図
yosuke_furukawa
PRO
6
4.7k
XHTMLが残したもの
yosuke_furukawa
PRO
2
830
デザインシステムが必須の時代に
yosuke_furukawa
PRO
2
310
Node.js, Deno, Bun 最新動向とその所感について
yosuke_furukawa
PRO
10
5.3k
Welcome JSConf.jp 2024
yosuke_furukawa
PRO
1
4.8k
tc39 x jsconf.jp Panel Discussion 2024
yosuke_furukawa
PRO
0
370
Removing Corepack
yosuke_furukawa
PRO
9
2k
JavaScript Runtime とはなにか
yosuke_furukawa
PRO
15
3.2k
Strip Types と Storage
yosuke_furukawa
PRO
4
530
Other Decks in Programming
See All in Programming
すこし踏み込む CancellationToken
htkym
2
690
Augmenting AI with the Power of Jakarta EE
ivargrimstad
0
220
Snowflakeで業務アプリを作ろう。 Snowflakeのアプリ機能解説&実践ガイド
ayumu_yamaguchi
2
290
The Past, Present, and Future of Enterprise Java
ivargrimstad
0
490
FreeBSDでZabbixを動かす
kenkino
0
310
Building an Out-of-Order CPU
latte72
1
790
AI活用は、個人から組織へ|マルチプレイヤーエージェントハーネス「QM」の社内活用事例 / AI use is moving from individuals to orgs
rkaga
1
140
AWS Step Functions 大規模並列の壁を越える / jaws-sonic-2026-niigata-step-functions
kasacchiful
PRO
1
500
仕様駆動開発による爆速プロダクト開発 / Bakusoku Spec Driven Development
kobakei
0
120
cdk deploy JawsSonic #MARATHONしながらAWSリソースをデプロイしてみよう
akihisaikeda
2
140
海上で動くGoサーバー: goroutineとchannelでさばく航行データストリーム
atsuki_seo
0
840
技術的負債を組織課題として解く-増えすぎたマイクロサービスとの戦い-
reimaru
1
2.2k
Featured
See All Featured
Building Better People: How to give real-time feedback that sticks.
wjessup
370
20k
Kristin Tynski - Automating Marketing Tasks With AI
techseoconnect
PRO
0
520
What does AI have to do with Human Rights?
axbom
PRO
1
2.4k
First, design no harm
axbom
PRO
2
1.3k
Effective software design: The role of men in debugging patriarchy in IT @ Voxxed Days AMS
baasie
1
530
The World Runs on Bad Software
bkeepers
PRO
72
12k
VelocityConf: Rendering Performance Case Studies
addyosmani
331
25k
Designing Powerful Visuals for Engaging Learning
tmiket
1
570
The B2B funnel & how to create a winning content strategy
katarinadahlin
PRO
1
540
How to build a perfect <img>
jonoalderson
1
6k
Color Theory Basics | Prateek | Gurzu
gurzu
1
470
What Being in a Rock Band Can Teach Us About Real World SEO
427marketing
0
1.1k
Transcript
JavaScript Engine を作った話 (AIといっしょに) Qiita Tech Conference 2026 古川陽介 /
2026/07/25
X: @yosuke_furukawa GitHub: yosuke-furukawa
AI と学ぶ
AI時代において、タスクはAIにおまかせしてて もできてしまう時代である
やれ Loop Engineering だとか、 Claude Fable だとか、この skill 使うといいよとか (ちょっと飽きちゃった)
AI時代だからこそ「AIを業務に使う」だけじゃなくて そもそも知りたかった好奇心を満たすツールにしよう
というわけで本題
JS Engine を作ってみた話
JS Engine • JavaScript のエンジン • JavaScript は 「エンジン」 と「ランタイム」に分かれて実行するモデル
• ランタイム = ブラウザ、Node.js、Deno、Bun • エンジン = V8, JavaScriptCore, SpiderMonkey
JS Runtime • よく聞かれるエンジンとランタイムの違い • エンジンは言語を使った「計算」を担当 JavaScript 機能群 • ランタイムは環境ごとの差異を吸収し、
JavaScript Runtime 環境ごとに必要なAPIを提供する • 例: ブラウザで言うと DOM Node.jsは HTTP Server など DOM, fetch/XHR, navigator, EventLoop JavaScript Engine 分岐処理、繰り返し処理、Promise, 構文
JS Engine motivation • 僕はこれまで Node.js やブラウザを専門としてきた • いわゆる「ランタイム」側の専門家であった。 •
JavaScript 「エンジン」 のことはもちろん知ってた。 • でも内容が難しい、中身を理解しようにも概要レベル以上のものを理解するのは困難 だった。 • AI がせっかくあるなら作ってみようと思った。 • 作りながらわからないことを聞きながら作れば、ゼロから自分で作るのは難しくて も、非常に学びになるはずだと思った。
JS Engine • ざっくり大きく分けて 4 ステップに分かれてる 1. Tokenize 字句解析 2.
Parse 構文解析 3. Bytecode Generate バイトコード生成 4. JIT Compile JIT コンパイル Tokenize Parse Bytecode Generate JIT Compile
Tokenize 字句解析 • めっちゃざっくり言うと、スクリプトという文書を単語に分割する処理 Function Identi ier LeftParen Identi ier
Identi ier RightParen LeftBrace f f f Tokenize Parse Bytecode Generate JIT Compile
Tokenize 字句解析 • 単語に分割したうえで、それが何を表すのかを粗く解析する • 数字なのか?文字なのか?記号なのか? • 文字だとしたらそれは予約されてるキーワードなのか? • 記号だとしたらどんな記号なのか?
• パターンマッチの要領で機械的に解析する Tokenize Parse Bytecode Generate JIT Compile
Tokenize 字句解析 • 最終的に単語とその種別をまとめた結果が出てくる Tokenize Parse Bytecode Generate JIT Compile
Tokenize 字句解析 • ちなみに V8 は・・・ • tokenize 1つとっても特徴的 •
一つ一つのtoken解析の際に非同期に処理できるようになってる • JavaScript の特性上、HTTPからファイルを受け取りながら解析するという目的のためにそう なってる • 普通プログラミング言語は全部のスクリプトが揃ってることが前提なのでこんなふうになっ てるのは JavaScript 特有。マジで変態。 Tokenize Parse Bytecode Generate JIT Compile
Parse 構文解析 • これもめっちゃざっくり言うと、トークンの種別をベースにそれぞれの関係 性を作る。もっと言えばトークンの種別の解析結果を元に木構造にする Function Identi ier LeftParen Identi
ier Identi ier RightParen LeftBrace f f f Tokenize Function Declaration Parse Bytecode Generate Block Statement Return Statement Binary Expression JIT Compile
Parse 構文解析 • 木構造にする Function Declaration Block Statement Return Statement
Binary Expression Tokenize Parse Bytecode Generate JIT Compile
Parse 構文解析 • 木構造は専門的に言うと Abstract Syntax Tree 抽象構文木となる。 • 抽象構文木にする理由はコンピュータで辿りやすいから
• 辿ることで処理が実行できるようになる • これを実行以外の用途で活かしたものが Linter (プログラムのバグチェック) であったり Mini ier (プログラムの不要な処理の削減及び変数の短縮化)であっ たりする f Tokenize Parse Bytecode Generate JIT Compile
Parse 構文解析 • AST(木構造)を辿るだけで実行する形式もある、それをインタプリタと呼ぶ • インタプリタは左から順に辿り 演算内容があったら処理していく • ははーんなるほど、辿って処理 していくだけなら簡単そうだな
と思った人、甘いです。 Tokenize Parse Bytecode Generate JIT Compile
Parse 構文解析 • 辿って処理するだけって言っても、変数や関数の話が入ってくると少し複雑 Parse時だけでは値は決まらない 関数を実行する時になって はじめて a, b に値が入って
計算可能になる Tokenize Parse Bytecode Generate JIT Compile
Parse 構文解析 • 変数を解決するための箱(Environment)を用意しないといけない Tokenize Parse Bytecode Generate key value
a 1 b 1 JIT Compile
Parse 構文解析 • 変数を解決するための箱(Environment)を用意しないといけない • さらに言うと、その箱は特定の関数の中からしか使えないようにしないとい けない(スコープ) • またさらに言うと自分の外側のスコープにある変数も使えないといけない (スコープは入れ子になる)
Tokenize Parse Bytecode Generate JIT Compile
Parse 構文解析 • つまり、JavaScriptの以前までの仕様で関数スコープとグローバルスコープだ けだったとしても、関数を作るたびにスコープと変数を入れる箱が必要にな る • 現代のJavaScriptはこれに加えてブロックスコープなどもあるのでより複雑 Tokenize Parse
Bytecode Generate JIT Compile
Parse 構文解析 • つまり、JavaScriptの以前までの仕様で関数スコープとグローバルスコープだ けだったとしても、関数を作るたびにスコープと変数を入れる箱が必要にな る • 現代のJavaScriptはこれに加えてブロックスコープなどもあるのでより複雑 インタプリタ式で解決する場合、木構造を辿りながら、関数呼び出しの たびに毎回箱を用意しつつ、変数を見つける際にも自分の箱の中だけ
Bytecode ではなく、上の箱にある変数も見つけに行かないといけない Tokenize Parse JIT Compile Generate
Parse 構文解析 • なのでインタプリタ式で実行するJavaScriptエンジンはほとんど存在しない • 木構造を辿りながら、スコープチェーンを辿りながらという方式だと速くな らない • 現代のJavaScriptエンジン(v8, JSC,
SpiderMonkey)はバイトコード生成、そ の後のJITコンパイルに繋げるアーキテクチャになってる Tokenize Parse Bytecode Generate JIT Compile
Parse 構文解析 • ちなみに v8 はここでも変態 • 構文解析を2回する • 最初にざっくり関数ブロックを見つけたらその中身まで追いに行かない
• こうすることで処理を分散させている、JavaScriptの解析に時間がかかりす ぎるとHTML,CSSの処理に影響出るのでそれを軽減するため • 変態、普通はそんな事しない Tokenize Parse Bytecode Generate JIT Compile
Bytecode Generate バイトコード生成 • バイトコード生成は木構造(AST)の構造を一回ざっくり読み、読んだ上で演算 するための命令の配列だけ生成する。 • 変数を格納する箱も別途配列で用意する。 • 木構造の操作をしながら実行するのではなく、木構造を一回全部スキャンし
て命令配列を生成し、その配列の操作だけで完結できるようにする。 • 考えた人は天才。 Tokenize Parse Bytecode Generate JIT Compile
Bytecode Generate バイトコード生成 • 木構造を一回辿ってバイトコードを生成する Tokenize Parse Bytecode Generate JIT
Compile
Bytecode Generate バイトコード生成 • バイトコードは何がいいのか? • 木構造を辿りながら、変数を管理しながら、計算するのは至難の業 • ドン・キホーテの店舗の中を買いたいものを考えながら歩いてなるべく短時 間で買おうとするくらい困難
• 一回ドン・キホーテの店舗の中を歩いて土地勘を掴み、買いたいものをリス トアップしたうえで最短距離を歩いたほうが早い Tokenize Parse Bytecode Generate JIT Compile
Bytecode Generate バイトコード生成 • バイトコードは何がいいのか? • それと同じで、木構造を一度命令の配列にする • そうするとあとは配列操作だけで実行できる Tokenize
Parse Bytecode Generate JIT Compile
Bytecode Generate バイトコード生成 • バイトコードバイトコードと言っているが、実際はエンジンの言語内にある 配列操作にすぎない。多くの場合は C++ の配列操作で、 C++ の演算を行う
• 今回作っている jsmini は中身は JavaScript なので JavaScript の配列操作で JavaScript の演算を行う Tokenize Parse Bytecode Generate JIT Compile
JIT Compile • とうとうここまできた。 • バイトコードで命令配列操作だったら高速 • でもそれはあくまで「木構造のスキャンしながら演算する」のに比べたら高 速という程度 •
「最速」ではない Tokenize Parse Bytecode Generate JIT Compile
JIT Compile • そもそも最速な処理とは? • 1 + 1 を考える。もちろん 2
である。 • でも計算機の世界では? • 数値1つとっても型がある。型同士で演算の仕方は違う。 同じ 1 + 1 でも整数の 1 + 1 と小数を含んだ 1.0 + 1.0 は処理方法が違う。 • もっと言えば 32bit 表現なのか64bit表現なのかでメモリに割り当てるサイズ も違う Tokenize Parse Bytecode Generate JIT Compile
JIT Compile • 最小メモリ割り当てサイズで最適な処理方法で演算できる必要がある • それには型を見つける必要がある • JavaScript の数値は仕様上、全て浮動小数点数表現になっているが、実際の 処理は整数がほとんどである
• どうやって型を見つける・・・? Tokenize Parse Bytecode Generate JIT Compile
JIT Compile • こたえ: 実行してみて見つける • 何回か実行しているうちにどうやらこの値って整数・・・? • みたいに推測する •
推測された値を元に計算を最適化する Tokenize Parse Bytecode Generate JIT Compile
JIT Compile • 関数やループ内の処理ブロックをきっかけに実行後の情報をためておく • 型のフィードバックを行う foo関数の引数も戻り値もuint32っぽい? Tokenize Parse Bytecode
Generate JIT Compile
JIT Compile • 繰り返し繰り返し処理が溜まっていくことで「推測の確度」が上がる • それをもとに最適化する int32であることを元に計算を最適化 Tokenize Parse Bytecode
Generate JIT Compile
JIT Compile • jsmini では バイトコードから WASM の命令に変換 • でも
v8 ではもちろんCPUの命令に変換(WASMよりもその方が速いので) • 中々個人では v8 に追いつくことは困難・・・(AIを持ってしても) Tokenize Parse Bytecode Generate JIT Compile
JIT Compile • 型の推定はJIT Compileの初歩機能である • 実際にはこの他にもエグい最適化をいっぱい行う • 定数畳み込み(const a
= 1 + 1 + 3; みたいになってたら a = 5 にしちゃう) • ループの不変部分の移行(forの中で変わらない値があれば外出しする) • デッドコード削除(使ってないコードをそもそも消す) Tokenize Parse Bytecode Generate JIT Compile
DEMO https://yosuke-furukawa.github.io/jsmini/ Tokenize Parse Bytecode Generate JIT Compile
まとめに入ります
JS Engine を作ってみた
作ってみたら、ものすごく面白かった。 分からなかったことが分かる喜び。
よく考えるとJavaScriptはすごく特殊、 仕様含めて破綻していないのがすごい。 AIとかで矛盾も指摘できない頃からやってる
AIをどう使ったか
AI使い方 • 5つのフェーズに分かれて使った • RESEARCH: 調査フェーズ、他実装の内容、論文調査など • PLAN: いわゆるPLANモード、実装計画の策定 •
TODO: より具体的な実装計画、 • Implement: 実装 • LEARN: 振り返りの実施 • 具体的なのは https://github.com/yosuke-furukawa/jsmini ここを。 RESEARCH PLAN TODO Implement LEARN
僕が伝えたいこと • AIをどう使ったか、今後どうなるかみたいな話をしたかったわけじゃない • 好奇心や探究心を持ってAIを使っていくことで自分の見識を深めてほしい • 見識が深くなることは AI ツールを使う上でももちろん重要だし、問題発見認識ができるよ うになる
• 技術が好きで技術を学びたいという気持ちを持ち続けてほしい • jsminiは僕の技術が好きという気持ちを体現した僕だけが得するプロダクト • でもそれでいいんじゃないか?難しく考えてほしくない • 「技術を知らなくてもプロダクトが作れる時代に僕は技術を知りたい」