docs: restore docs/private/roadmap from 7b4908f9 (Phase 20.31)
This commit is contained in:
203
docs/private/roadmap/phases/phase-20-python-integration/INDEX.md
Normal file
203
docs/private/roadmap/phases/phase-20-python-integration/INDEX.md
Normal file
@ -0,0 +1,203 @@
|
||||
# Phase 20 Python Integration - INDEX
|
||||
|
||||
## 📋 全体概要
|
||||
|
||||
**Phase 20: Python-Hakorune統合** - PythonのAST/木構造をHakoruneに落とし、Python-Hakorune間の相互運用を実現するフェーズです。
|
||||
|
||||
**出典**: 旧Phase 10.5(Phase 10.1系)の内容を整理・再編成
|
||||
|
||||
## 🗂️ フォルダ構成
|
||||
|
||||
```
|
||||
phase-20-python-integration/
|
||||
├── README.md # ⭐ メインドキュメント
|
||||
├── INDEX.md # このファイル
|
||||
│
|
||||
├── 📁 planning/ # 計画・設計
|
||||
│ ├── README.md
|
||||
│ ├── integrated-plan.md # ChatGPT5統合計画
|
||||
│ ├── python-parser-plan-summary.md # パーサー計画サマリー
|
||||
│ ├── python-parser-box-design.md # パーサーBox設計
|
||||
│ └── expert-feedback.md # AI専門家フィードバック
|
||||
│
|
||||
├── 📁 parser-integration/ # パーサー統合
|
||||
│ ├── README.md
|
||||
│ ├── implementation-plan.md # 実装計画
|
||||
│ └── builtin-box-flow.md # ビルトインBox実装フロー
|
||||
│
|
||||
├── 📁 core-implementation/ # コア実装
|
||||
│ ├── README.md
|
||||
│ └── implementation-roadmap.md # 実装ロードマップ
|
||||
│
|
||||
├── 📁 transpiler/ # トランスパイラー
|
||||
│ ├── README.md
|
||||
│ └── python-to-hakorune-spec.md # Python→Hakorune変換仕様
|
||||
│
|
||||
├── 📁 design/ # 設計ドキュメント
|
||||
│ ├── README.md
|
||||
│ ├── abi-design.md # ABI設計
|
||||
│ ├── native-build-consolidation.md # ネイティブビルド
|
||||
│ └── handle-first-plugininvoke-plan.md # Handle-First設計
|
||||
│
|
||||
├── 📁 testing/ # テスト計画
|
||||
│ └── README.md
|
||||
│
|
||||
└── 📁 documentation/ # ドキュメント計画
|
||||
└── README.md
|
||||
```
|
||||
|
||||
## 🎯 クイックナビゲーション
|
||||
|
||||
### 🚀 初めての方へ
|
||||
1. [メインREADME](README.md) - 全体概要を理解
|
||||
2. **[強化版アーキテクチャv2](design/enhanced-architecture-v2.md)** - ChatGPT Pro最新設計(推奨)
|
||||
3. [マイルストーン](planning/milestones.md) - M0〜M6実装計画
|
||||
4. [Planning README](planning/README.md) - 計画の詳細を確認
|
||||
5. [統合計画](planning/integrated-plan.md) - ChatGPT5による詳細計画
|
||||
|
||||
### 🏗️ 設計を知りたい
|
||||
- **[強化版アーキテクチャv2](design/enhanced-architecture-v2.md)** ⭐ ChatGPT Pro最新設計(2025-10-02)
|
||||
- [ABI設計](design/abi-design.md) - Python-Hakorune間のABI
|
||||
- [Handle-First設計](design/handle-first-plugininvoke-plan.md) - プラグイン呼び出し設計
|
||||
- [ネイティブビルド](design/native-build-consolidation.md) - AOT/EXE生成
|
||||
- [メタ設定例](design/meta-config-examples.md) - hako.toml設定リファレンス
|
||||
- [リスクと対策](design/risks-and-mitigations.md) - 既知のリスクと対策
|
||||
|
||||
### 💻 実装を見たい
|
||||
- [パーサー実装計画](parser-integration/implementation-plan.md) - PythonパーサーBox
|
||||
- [コア実装ロードマップ](core-implementation/implementation-roadmap.md) - PyRuntimeBox/PyObjectBox
|
||||
- [トランスパイラー仕様](transpiler/python-to-hakorune-spec.md) - Python→Hakorune変換
|
||||
|
||||
### 🧪 テストについて
|
||||
- [テスト計画](testing/README.md) - テスト戦略とチェックリスト
|
||||
|
||||
### 📚 ドキュメントについて
|
||||
- [ドキュメント計画](documentation/README.md) - ドキュメント構成
|
||||
|
||||
## 📊 実装ステータス
|
||||
|
||||
| カテゴリ | コンポーネント | ステータス |
|
||||
|---------|--------------|----------|
|
||||
| **計画** | 設計・計画書 | ✅ 完了 |
|
||||
| **計画** | 強化版アーキテクチャv2 | ✅ 完了(2025-10-02)|
|
||||
| **計画** | マイルストーン(M0-M6) | ✅ 完了(2025-10-02)|
|
||||
| **設計** | ABI設計 | ✅ 完了 |
|
||||
| **設計** | Handle-First | ✅ 完了 |
|
||||
| **設計** | ネイティブビルド | ✅ 完了 |
|
||||
| **設計** | メタ設定例 | ✅ 完了(2025-10-02)|
|
||||
| **設計** | リスク管理 | ✅ 完了(2025-10-02)|
|
||||
| **実装** | PyRuntimeBox | 📅 未実装(M0予定)|
|
||||
| **実装** | PyObjectBox | 📅 未実装(M0予定)|
|
||||
| **実装** | PythonパーサーBox | 📅 未実装(M4予定)|
|
||||
| **実装** | トランスパイラー | 📅 未実装 |
|
||||
| **テスト** | ユニットテスト | 📅 未実装 |
|
||||
| **テスト** | 統合テスト | 📅 未実装 |
|
||||
| **ドキュメント** | ユーザーガイド | 📅 未実装 |
|
||||
| **ドキュメント** | APIリファレンス | 📅 未実装 |
|
||||
|
||||
## 🎯 主要コンポーネント
|
||||
|
||||
### 1. PyRuntimeBox
|
||||
**目的**: Python実行環境の提供
|
||||
|
||||
```hakorune
|
||||
box PyRuntimeBox {
|
||||
eval(code: StringBox) -> PyObjectBox
|
||||
import(name: StringBox) -> PyObjectBox
|
||||
}
|
||||
```
|
||||
|
||||
### 2. PyObjectBox
|
||||
**目的**: Pythonオブジェクトの管理
|
||||
|
||||
```hakorune
|
||||
box PyObjectBox {
|
||||
getattr(name: StringBox) -> PyObjectBox
|
||||
setattr(name: StringBox, value: PyObjectBox)
|
||||
call(args: ArrayBox) -> PyObjectBox
|
||||
to_string() -> StringBox
|
||||
to_int() -> IntegerBox
|
||||
}
|
||||
```
|
||||
|
||||
### 3. PythonパーサーBox
|
||||
**目的**: Python AST → Hakorune MIR変換
|
||||
|
||||
```hakorune
|
||||
box PythonParserBox {
|
||||
parse(code: StringBox) -> ASTBox
|
||||
to_hakorune_ast(ast: ASTBox) -> HakoruneASTBox
|
||||
to_mir(ast: ASTBox) -> MIRBox
|
||||
}
|
||||
```
|
||||
|
||||
### 4. トランスパイラー
|
||||
**目的**: Python構文 → Hakorune構文変換
|
||||
|
||||
```hakorune
|
||||
box PythonTranspiler {
|
||||
transpile(python_code: StringBox) -> StringBox
|
||||
}
|
||||
```
|
||||
|
||||
## ⚠️ 現在のステータス
|
||||
|
||||
**保留中** - Phase 15(Hakoruneセルフホスティング)完了後に着手予定
|
||||
|
||||
### 保留理由
|
||||
1. **優先度**: まずHakorune自身の基盤を固める
|
||||
2. **依存関係**: セルフホスティング実現が先決
|
||||
3. **リソース**: 段階的に実装する方が安全
|
||||
|
||||
### 再開条件
|
||||
- ✅ Phase 15完了(Rust VM + LLVM 2本柱体制確立)
|
||||
- ✅ セルフホスティング実現
|
||||
- ✅ プラグインシステム安定化
|
||||
|
||||
## 🔗 関連Phase
|
||||
|
||||
### 前提Phase
|
||||
- [Phase 15 - セルフホスティング](../phase-15/) - 現在進行中
|
||||
- [Phase 12 - TypeBox統合](../phase-12/) - 完了
|
||||
|
||||
### 後続Phase(予定)
|
||||
- Phase 21 - 箱データベース
|
||||
- Phase 22+ - 未定
|
||||
|
||||
## 📚 元資料
|
||||
|
||||
このPhase 20は以下の旧資料を整理・統合したものです:
|
||||
|
||||
- **元の場所**: `docs/archive/phases/phase-10.5/phase-10.5/`
|
||||
- **旧Phase名**: Phase 10.5(Phase 10.1系を再編成)
|
||||
- **作成時期**: 2025年8月頃
|
||||
- **主要貢献者**: ChatGPT5, Gemini, Codex
|
||||
|
||||
## 🎯 将来の展望
|
||||
|
||||
### 短期目標(Phase 15後)
|
||||
1. PyRuntimeBox基本実装
|
||||
2. PyObjectBox基本実装
|
||||
3. 基本的なPython呼び出し動作
|
||||
|
||||
### 中期目標
|
||||
1. PythonパーサーBox実装
|
||||
2. Python AST → Hakorune MIR変換
|
||||
3. トランスパイラー実装
|
||||
|
||||
### 長期目標
|
||||
1. Python-Hakoruneシームレス統合
|
||||
2. Pythonライブラリの完全活用
|
||||
3. ハイブリッド開発の実現
|
||||
|
||||
## 📞 お問い合わせ
|
||||
|
||||
- **メインドキュメント**: [README.md](README.md)
|
||||
- **マスタープラン**: [00_MASTER_ROADMAP.md](../00_MASTER_ROADMAP.md)
|
||||
- **現在のフェーズ**: [Phase 15](../phase-15/)
|
||||
|
||||
---
|
||||
|
||||
**最終更新**: 2025-10-02
|
||||
**整理者**: Claude Code
|
||||
**ステータス**: 計画済み・実装待ち
|
||||
@ -0,0 +1,127 @@
|
||||
# Phase 20: Python-Hakorune統合 - PythonのAST/木構造をHakoruneに落とす
|
||||
|
||||
## 📋 概要
|
||||
|
||||
PythonのAST(抽象構文木)をHakoruneの木構造(MIR/AST)に変換し、Python-Hakorune間の相互運用を実現するフェーズです。
|
||||
|
||||
**出典**: 旧Phase 10.5(Phase 10.1系)の内容を整理・再編成
|
||||
|
||||
## 🎯 目的
|
||||
|
||||
1. **PythonパーサーBox**: PythonコードをHakoruneで解析
|
||||
2. **AST変換**: Python AST → Hakorune MIR/AST
|
||||
3. **相互運用**: Python ⇄ Hakorune の双方向呼び出し
|
||||
4. **トランスパイラー**: Python → Hakorune コード変換
|
||||
|
||||
## 📁 フォルダ構成
|
||||
|
||||
```
|
||||
phase-20-python-integration/
|
||||
├── README.md # このファイル
|
||||
├── INDEX.md # 全体ナビゲーション ⭐推奨
|
||||
│
|
||||
├── planning/ # 計画・設計ドキュメント
|
||||
│ ├── README.md
|
||||
│ ├── milestones.md # ⭐M0-M6実装計画(2025-10-02追加)
|
||||
│ ├── integrated-plan.md # 統合計画
|
||||
│ ├── expert-feedback.md # AI専門家フィードバック
|
||||
│ └── python-parser-box-design.md
|
||||
│
|
||||
├── parser-integration/ # パーサー統合
|
||||
│ ├── README.md
|
||||
│ ├── implementation-plan.md
|
||||
│ └── builtin-box-flow.md
|
||||
│
|
||||
├── core-implementation/ # コア実装
|
||||
│ ├── README.md
|
||||
│ └── implementation-roadmap.md
|
||||
│
|
||||
├── transpiler/ # トランスパイラー
|
||||
│ ├── README.md
|
||||
│ └── python-to-hakorune-spec.md
|
||||
│
|
||||
├── testing/ # テスト計画
|
||||
│ └── README.md
|
||||
│
|
||||
├── documentation/ # ドキュメント
|
||||
│ └── README.md
|
||||
│
|
||||
└── design/ # 設計ドキュメント
|
||||
├── README.md
|
||||
├── enhanced-architecture-v2.md ⭐ChatGPT Pro最新設計(2025-10-02追加)
|
||||
├── meta-config-examples.md ⭐hako.toml設定例(2025-10-02追加)
|
||||
├── risks-and-mitigations.md ⭐リスク管理(2025-10-02追加)
|
||||
├── abi-design.md # ABI設計
|
||||
├── native-build-consolidation.md # ネイティブビルド
|
||||
└── handle-first-plugininvoke-plan.md # Handle-First設計
|
||||
```
|
||||
|
||||
## 🎯 主要コンポーネント
|
||||
|
||||
### 1. PythonパーサーBox
|
||||
- PythonコードをHakorune内で解析
|
||||
- `PyRuntimeBox`: Python実行環境
|
||||
- `PyObjectBox`: Pythonオブジェクト管理
|
||||
|
||||
### 2. AST変換
|
||||
- Python AST → Hakorune MIR
|
||||
- 型情報の保持
|
||||
- スコープ解決
|
||||
|
||||
### 3. 相互運用
|
||||
- Hakorune → Python: BoxCall経由
|
||||
- Python → Hakorune: FFI経由
|
||||
- エラーハンドリング
|
||||
|
||||
### 4. トランスパイラー
|
||||
- Python構文 → Hakorune構文
|
||||
- イディオム変換
|
||||
- 最適化
|
||||
|
||||
## 📊 実装ステータス
|
||||
|
||||
| コンポーネント | ステータス | 備考 |
|
||||
|--------------|----------|------|
|
||||
| 計画・設計 | ✅ 完了 | 詳細設計済み |
|
||||
| パーサーBox | 📅 未実装 | Phase 15後に実装予定 |
|
||||
| AST変換 | 📅 未実装 | - |
|
||||
| 相互運用 | 📅 未実装 | - |
|
||||
| トランスパイラー | 📅 未実装 | - |
|
||||
|
||||
## 🎯 重要ドキュメント(2025-10-02追加)
|
||||
|
||||
### 最新設計(ChatGPT Pro UltraThink)
|
||||
1. **[強化版アーキテクチャv2](design/enhanced-architecture-v2.md)** ⭐必読 - Effect/Capability/Contract/Policy統合設計
|
||||
2. **[マイルストーン(M0-M6)](planning/milestones.md)** - 段階的実装計画
|
||||
3. **[メタ設定例](design/meta-config-examples.md)** - hako.toml設定リファレンス
|
||||
4. **[リスクと対策](design/risks-and-mitigations.md)** - GILデッドロック・メモリリーク等
|
||||
|
||||
### ナビゲーション
|
||||
- **[INDEX.md](INDEX.md)** - 全体ナビゲーション
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- **元資料**: `docs/archive/phases/phase-10.5/phase-10.5/`
|
||||
- **現在のフェーズ**: [Phase 15 - セルフホスティング](../phase-15/)
|
||||
- **マスタープラン**: [00_MASTER_ROADMAP.md](../00_MASTER_ROADMAP.md)
|
||||
|
||||
## ⚠️ 開発優先度
|
||||
|
||||
**現在は保留中** - Phase 15(Hakoruneセルフホスティング)完了後に着手予定
|
||||
|
||||
理由:
|
||||
- まずHakorune自身の基盤(Rust VM + LLVM)を固める
|
||||
- セルフホスティングの実現が優先
|
||||
- Python統合は後段で段階的に実装
|
||||
|
||||
## 🚀 将来の展望
|
||||
|
||||
1. **短期**: Python FFI統合(PyO3等)
|
||||
2. **中期**: Python AST → Hakorune MIR 変換
|
||||
3. **長期**: Python-Hakorune シームレス統合
|
||||
|
||||
---
|
||||
|
||||
**最終更新**: 2025-10-02
|
||||
**ステータス**: 計画済み・実装待ち
|
||||
**優先度**: Phase 15完了後
|
||||
@ -0,0 +1,151 @@
|
||||
# Core Implementation - コア実装
|
||||
|
||||
## 📋 概要
|
||||
|
||||
Python-Hakorune統合のコア実装計画です。
|
||||
|
||||
## 📁 ファイル一覧
|
||||
|
||||
- **[implementation-roadmap.md](implementation-roadmap.md)** - Python実装ロードマップ
|
||||
|
||||
## 🎯 実装コンポーネント
|
||||
|
||||
### 1. PyRuntimeBox(Python実行環境)
|
||||
|
||||
```hakorune
|
||||
box PyRuntimeBox {
|
||||
// 初期化・終了
|
||||
init()
|
||||
shutdown()
|
||||
|
||||
// コード実行
|
||||
eval(code: StringBox) -> PyObjectBox
|
||||
exec(code: StringBox)
|
||||
|
||||
// モジュール
|
||||
import(name: StringBox) -> PyObjectBox
|
||||
}
|
||||
```
|
||||
|
||||
### 2. PyObjectBox(Pythonオブジェクト)
|
||||
|
||||
```hakorune
|
||||
box PyObjectBox {
|
||||
// 属性アクセス
|
||||
getattr(name: StringBox) -> PyObjectBox
|
||||
setattr(name: StringBox, value: PyObjectBox)
|
||||
|
||||
// 呼び出し
|
||||
call(args: ArrayBox) -> PyObjectBox
|
||||
|
||||
// 変換
|
||||
to_string() -> StringBox
|
||||
to_int() -> IntegerBox
|
||||
to_bool() -> BoolBox
|
||||
}
|
||||
```
|
||||
|
||||
### 3. 相互運用レイヤー
|
||||
|
||||
#### Hakorune → Python
|
||||
- BoxCall → CPython C API
|
||||
- 型変換: Hakorune Box → PyObject*
|
||||
- エラーハンドリング
|
||||
|
||||
#### Python → Hakorune
|
||||
- CPython拡張モジュール(`hakorunert`)
|
||||
- 型変換: PyObject* → Hakorune Box
|
||||
- GIL管理
|
||||
|
||||
## 🏗️ アーキテクチャ
|
||||
|
||||
### レイヤー構造
|
||||
|
||||
```
|
||||
┌─────────────────────────────┐
|
||||
│ Hakorune Application │
|
||||
├─────────────────────────────┤
|
||||
│ PyRuntimeBox/PyObjectBox │
|
||||
├─────────────────────────────┤
|
||||
│ FFI/Plugin Interface │
|
||||
├─────────────────────────────┤
|
||||
│ CPython C API │
|
||||
├─────────────────────────────┤
|
||||
│ CPython Runtime │
|
||||
└─────────────────────────────┘
|
||||
```
|
||||
|
||||
### プラグイン化
|
||||
|
||||
- `hakorune-python-plugin` (cdylib/staticlib)
|
||||
- `nyplug_python_invoke` FFI関数
|
||||
- 動的ロード/静的リンク対応
|
||||
|
||||
## 🔧 技術的詳細
|
||||
|
||||
### 1. メモリ管理
|
||||
|
||||
#### Python側
|
||||
- `Py_INCREF` / `Py_DECREF`
|
||||
- Boxライフサイクルとの連携
|
||||
- 循環参照の回避
|
||||
|
||||
#### Hakorune側
|
||||
- Handle管理(TLV tag=8)
|
||||
- Arc<PyObject> でのラップ
|
||||
- Drop時の自動DECREF
|
||||
|
||||
### 2. GIL管理
|
||||
|
||||
```rust
|
||||
// 基本パターン
|
||||
{
|
||||
let gil = Python::acquire_gil();
|
||||
let py = gil.python();
|
||||
|
||||
// Python操作
|
||||
let result = py.eval(code, None, None)?;
|
||||
|
||||
// GILは自動解放
|
||||
}
|
||||
```
|
||||
|
||||
### 3. エラーハンドリング
|
||||
|
||||
- Python例外 → Hakorune文字列エラー(tag=6)
|
||||
- トレースバック情報の保持
|
||||
- 双方向のエラー伝搬
|
||||
|
||||
## 📊 実装ステータス
|
||||
|
||||
| コンポーネント | ステータス | 備考 |
|
||||
|--------------|----------|------|
|
||||
| PyRuntimeBox設計 | ✅ 完了 | - |
|
||||
| PyObjectBox設計 | ✅ 完了 | - |
|
||||
| FFI統合 | 📅 未実装 | - |
|
||||
| GIL管理 | 📅 未実装 | - |
|
||||
| エラーハンドリング | 📅 未実装 | - |
|
||||
| メモリ管理 | 📅 未実装 | - |
|
||||
|
||||
## ⚠️ リスク要因
|
||||
|
||||
### 1. GILデッドロック
|
||||
- 入口/出口での厳格な管理
|
||||
- ネスト呼び出し時の方針
|
||||
- デッドロック検出機能
|
||||
|
||||
### 2. 参照カウントリーク
|
||||
- BoxライフサイクルでのDECREF保証
|
||||
- リークテストの追加
|
||||
- デバッグツール整備
|
||||
|
||||
### 3. パフォーマンス
|
||||
- FFIオーバーヘッド
|
||||
- GIL待機時間
|
||||
- 最適化戦略
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- [Phase 20 メインREADME](../README.md)
|
||||
- [Planning](../planning/)
|
||||
- [Design Documents](../design/)
|
||||
@ -0,0 +1,264 @@
|
||||
# PythonParserBox 実装ロードマップ(エキスパート統合版)
|
||||
Based on ChatGPT5's Python Language Feature Surface Map + Expert Feedback
|
||||
更新日: 2025-08-27
|
||||
|
||||
## 🎯 実装優先順位の考え方(エキスパート統合)
|
||||
|
||||
### 🏯 核心戦略:関数単位フォールバック
|
||||
**両エキスパートが強調:** ファイル全体ではなく、**関数単位**でコンパイル/フォールバックを判断
|
||||
```python
|
||||
def supported_function(): # → Nyash MIR/JIT
|
||||
return x + y
|
||||
|
||||
def unsupported_function(): # → CPython exec
|
||||
yield from generator # Phase 1では未対応
|
||||
```
|
||||
|
||||
### 🔧 Python 3.11固定
|
||||
- AST安定性確保(3.8 Constant統一、3.10 match/case、3.12位置情報)
|
||||
- `py_version`と`ast_format`をJSON IRに埋め込む
|
||||
|
||||
### 🌟 Differential Testing戦略
|
||||
- **世界中のPythonコードがNyashのテストケースに**
|
||||
- CPythonをオラクルとして使用、出力・戻り値・例外を比較
|
||||
- 微妙なセマンティクスバグを自動発見
|
||||
|
||||
### 📊 テレメトリー重視
|
||||
- 未対応ノードの記録(`support_level`フィールド)
|
||||
- フォールバック率の計測
|
||||
- ソース位置情報保持(`lineno/col_offset/end_*`)
|
||||
|
||||
## 📋 Phase 1: Core Subset(1-2週間)
|
||||
**目標**: 基本的なPythonコードをNyashで実行可能にする
|
||||
|
||||
### ❌ Phase 1での必須意味論要素(Codex先生強調)
|
||||
- **LEGB + locals/freevars**: スコーピング規則
|
||||
- **デフォルト引数の評価タイミング**: 定義時に一度だけ
|
||||
- **イテレータベースのfor文**: `__iter__`/`__next__`プロトコル
|
||||
- **for/else + while/else**: Python独特のelse節
|
||||
- **Python真偽値判定**: `__bool__` → `__len__`
|
||||
- **短絡評価**: and/orの正確な挙動
|
||||
|
||||
### 文(Statement)
|
||||
- [x] def - 関数定義 → Nyash関数/Box
|
||||
- デフォルト引数の定義時評価
|
||||
- argumentsオブジェクトの完全解析
|
||||
- [x] if/elif/else - 条件分岐 → CondBr
|
||||
- [x] for - ループ → Loop + Iterator
|
||||
- **else節対応必須**
|
||||
- [x] while - ループ → Loop
|
||||
- **else節対応必須**
|
||||
- [x] break/continue - ループ制御
|
||||
- [x] return - 戻り値 → Return
|
||||
- [ ] pass - 空文
|
||||
- [ ] import(Phase 3へ延期)
|
||||
|
||||
### 式(Expression)
|
||||
- [x] 関数呼び出し - Call → BoxCall
|
||||
- [x] 算術演算子 - +,-,*,/,//,% → BinOp
|
||||
- `/`: true division(常にfloat)
|
||||
- `//`: floor division
|
||||
- [x] 比較演算子 - ==,!=,<,>,<=,>=,is,is not → Compare
|
||||
- [x] 論理演算子 - and,or,not → BoolOp/UnaryOp
|
||||
- 短絡評価の正確な実装
|
||||
- [x] 変数参照/代入 - Name → Load/Store
|
||||
- [x] リテラル - 数値/文字列/bool → Constant
|
||||
- [x] 三項演算子 - IfExp
|
||||
|
||||
### データ型(最小限)
|
||||
- [x] int → IntegerBox(大整数対応)
|
||||
- [x] float → FloatBox(NaNの扱い注意)
|
||||
- [x] str → StringBox
|
||||
- [x] bool → BoolBox
|
||||
- [x] list(基本) → ArrayBox
|
||||
|
||||
## 📋 Phase 2: Data Model(2-3週間)
|
||||
**目標**: Pythonの特殊メソッドをNyashのBoxメソッドにマッピング
|
||||
|
||||
### 特殊メソッド
|
||||
- [ ] __init__ → constructor/birth
|
||||
- [ ] __len__ → length()
|
||||
- [ ] __getitem__ → get()
|
||||
- [ ] __setitem__ → set()
|
||||
- [ ] __iter__ → iterator()
|
||||
- [ ] __str__ → toString()
|
||||
|
||||
### コレクション拡張
|
||||
- [ ] dict → MapBox
|
||||
- [ ] tuple → ImmutableArrayBox(新規)
|
||||
- [ ] set → SetBox(新規)
|
||||
|
||||
### 演算子オーバーロード
|
||||
- [ ] __add__, __sub__ 等 → operator+, operator-
|
||||
- [ ] __eq__, __lt__ 等 → equals(), compareTo()
|
||||
|
||||
## 📋 Phase 3: Advanced Features(1ヶ月)
|
||||
**目標**: Pythonの生産性の高い機能を実装
|
||||
|
||||
### 制御フロー拡張
|
||||
- [ ] try/except → エラーハンドリング
|
||||
- [ ] with文 → リソース管理
|
||||
- [ ] break/continue → ループ制御
|
||||
|
||||
### 高度な機能
|
||||
- [ ] ジェネレータ(yield) → GeneratorBox
|
||||
- [ ] デコレータ → 関数ラッパー
|
||||
- [ ] 内包表記 → 最適化されたループ
|
||||
- [ ] ラムダ式 → 匿名関数
|
||||
|
||||
### クラスシステム
|
||||
- [ ] class文 → box定義
|
||||
- [ ] 継承 → from構文
|
||||
- [ ] super() → from Parent.method()
|
||||
|
||||
## 📋 Phase 4: Modern Python(将来)
|
||||
**目標**: 最新のPython機能をサポート
|
||||
|
||||
### 非同期
|
||||
- [ ] async/await → 非同期Box(将来のNyash非同期と統合)
|
||||
- [ ] async for/with → 非同期イテレータ
|
||||
|
||||
### パターンマッチ(3.10+)
|
||||
- [ ] match/case → Nyashのパターンマッチ(将来実装時)
|
||||
|
||||
### 型ヒント
|
||||
- [ ] 型アノテーション → MIRの型情報として活用
|
||||
- [ ] typing モジュール → 静的型チェック情報
|
||||
|
||||
## 🚀 実装戦略
|
||||
|
||||
### Step 1: AST変換の基礎(Phase 1開始)
|
||||
```python
|
||||
# Python側でAST→JSON
|
||||
import ast
|
||||
import json
|
||||
|
||||
def parse_to_json(code):
|
||||
tree = ast.parse(code)
|
||||
return json.dumps(ast_to_dict(tree))
|
||||
|
||||
# 最小限のノードから実装
|
||||
def ast_to_dict(node):
|
||||
if isinstance(node, ast.FunctionDef):
|
||||
return {
|
||||
"type": "FunctionDef",
|
||||
"name": node.name,
|
||||
"args": [arg.arg for arg in node.args.args],
|
||||
"body": [ast_to_dict(stmt) for stmt in node.body]
|
||||
}
|
||||
# ... 他のノードタイプを順次追加
|
||||
```
|
||||
|
||||
### Step 2: Nyash AST生成(Rust側)
|
||||
```rust
|
||||
// JSON → Nyash AST
|
||||
fn convert_python_ast(json: &str) -> Result<ast::Program> {
|
||||
let py_ast: PythonAst = serde_json::from_str(json)?;
|
||||
match py_ast {
|
||||
PythonAst::FunctionDef { name, args, body } => {
|
||||
// Python def → Nyash function
|
||||
ast::BoxDef {
|
||||
name,
|
||||
methods: vec![ast::Method {
|
||||
name: name.clone(),
|
||||
params: args,
|
||||
body: convert_statements(body),
|
||||
}],
|
||||
..
|
||||
}
|
||||
}
|
||||
// ... 他のケース
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Step 3: 段階的な実行
|
||||
1. 最初はCPython exec()でそのまま実行
|
||||
2. 変換可能な部分からMIR生成
|
||||
3. MIR化された部分はVM/JITで高速実行
|
||||
4. 未対応部分は自動的にCPythonフォールバック
|
||||
|
||||
## 📊 期待される成果
|
||||
|
||||
### Phase 1完了時点
|
||||
- 簡単な数値計算スクリプトが2-5倍高速化
|
||||
- 基本的なループが最適化される
|
||||
- Nyashの既存Box(FileBox等)がPythonから使える
|
||||
|
||||
### Phase 2完了時点
|
||||
- Pythonのリスト/辞書操作が高速化
|
||||
- NyashとPythonのデータ構造が相互運用可能
|
||||
- 特殊メソッドによる自然な統合
|
||||
|
||||
### Phase 3完了時点
|
||||
- Pythonの生産的な機能がNyashで高速実行
|
||||
- 既存Pythonコードの大部分が動作
|
||||
- デコレータやジェネレータも最適化
|
||||
|
||||
## 🎯 最初の一歩(今すぐ開始)
|
||||
|
||||
1. pyo3でPythonParserBoxの骨組み作成
|
||||
2. 最小限のparse_to_json実装(def + return)
|
||||
3. 単純な関数のAST変換テスト
|
||||
4. "Hello from Python in Nyash"を表示
|
||||
|
||||
```python
|
||||
# 最初のテストケース
|
||||
def hello():
|
||||
return "Hello from Python in Nyash"
|
||||
|
||||
# これがNyashで動けば成功!
|
||||
```
|
||||
|
||||
## 📊 成功の測定基準(エキスパート推奨)
|
||||
|
||||
### 定量的指標
|
||||
| 指標 | 目標 | 測定方法 |
|
||||
|------|-------|----------|
|
||||
| カバレッジ率 | 70%以上 | コンパイル済み vs フォールバック関数の比率 |
|
||||
| 性能向上 | 2-10倍 | 純Pythonループのベンチマーク |
|
||||
| バグ発見数 | 10+件/Phase | Differential Testingで発見されたNyashバグ |
|
||||
| エコシステム | 1以上 | 動作する有名Pythonライブラリ |
|
||||
|
||||
### マイルストーン
|
||||
- Phase 1: "Hello from Python in Nyash"が動作
|
||||
- Phase 2: scikit-learnの基本アルゴリズムが動作
|
||||
- Phase 3: FlaskのHello Worldが動作
|
||||
- Phase 4: PyPIトップ100の30%が基本動作
|
||||
|
||||
## 🔧 GIL管理の黄金律
|
||||
|
||||
```rust
|
||||
// GILは最小限に!
|
||||
let json_ast = Python::with_gil(|py| {
|
||||
// Python側でJSON生成(高速)
|
||||
py_helper.parse_to_json(py, code)
|
||||
})?;
|
||||
|
||||
// GIL外でRust処理(並列可能)
|
||||
let nyash_ast = py.allow_threads(|| {
|
||||
convert_json_to_nyash(json_ast)
|
||||
});
|
||||
```
|
||||
|
||||
## 🔍 JSON IR設計(Codex先生推奨)
|
||||
|
||||
```json
|
||||
{
|
||||
"node_type": "FunctionDef",
|
||||
"py_version": "3.11",
|
||||
"ast_format": "v2",
|
||||
"support_level": "full", // "partial", "fallback"
|
||||
"lineno": 1,
|
||||
"col_offset": 0,
|
||||
"end_lineno": 3,
|
||||
"end_col_offset": 15,
|
||||
"name": "hello",
|
||||
"args": {...},
|
||||
"body": [...]
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
作成日: 2025-08-27
|
||||
ChatGPT5のサーフェスマップ + Gemini/Codex先生のエキスパートフィードバックを統合
|
||||
@ -0,0 +1,193 @@
|
||||
# Design - 設計ドキュメント
|
||||
|
||||
## 📋 概要
|
||||
|
||||
Python-Hakorune統合の設計ドキュメント集です。
|
||||
|
||||
## 📁 ファイル一覧
|
||||
|
||||
### 🌟 最新設計(2025-10-02追加)
|
||||
- **[enhanced-architecture-v2.md](enhanced-architecture-v2.md)** ⭐必読 - ChatGPT Pro UltraThink強化版アーキテクチャ
|
||||
- **[meta-config-examples.md](meta-config-examples.md)** - hako.toml設定リファレンス
|
||||
- **[risks-and-mitigations.md](risks-and-mitigations.md)** - リスク管理ドキュメント
|
||||
|
||||
### ABI・FFI設計
|
||||
- **[abi-design.md](abi-design.md)** - Python-Hakorune ABI設計
|
||||
- **[handle-first-plugininvoke-plan.md](handle-first-plugininvoke-plan.md)** - Handle-First PluginInvoke設計
|
||||
|
||||
### ビルド・実行
|
||||
- **[native-build-consolidation.md](native-build-consolidation.md)** - ネイティブビルド基盤設計
|
||||
|
||||
## 🎯 設計の核心
|
||||
|
||||
### 1. ABI設計方針
|
||||
|
||||
#### ハンドル管理
|
||||
- **TLV tag=8**: Python object handle
|
||||
- **type_id + instance_id**: 箱の識別
|
||||
- **Arc<PyObject>**: Rust側での管理
|
||||
|
||||
#### 型変換
|
||||
|
||||
| Hakorune | Python | 備考 |
|
||||
|---------|--------|------|
|
||||
| BoolBox | bool | 真偽値 |
|
||||
| IntegerBox | int | 整数 |
|
||||
| StringBox | str | 文字列 |
|
||||
| ArrayBox | list | 配列 |
|
||||
| MapBox | dict | 辞書 |
|
||||
| PyObjectBox | object | 任意のPythonオブジェクト |
|
||||
|
||||
### 2. Handle-First 設計
|
||||
|
||||
#### 原則
|
||||
- 第一引数(a0)は常にハンドル
|
||||
- `nyash.handle.of(receiver)` で変換
|
||||
- TLV統一: String/Integer以外はHandle(tag=8)
|
||||
|
||||
#### メリット
|
||||
- 型安全性の向上
|
||||
- 統一されたインターフェース
|
||||
- デバッグの容易さ
|
||||
|
||||
### 3. GIL管理戦略
|
||||
|
||||
#### 基本方針
|
||||
- **birth/invoke/decRef中はGIL確保**
|
||||
- **AOTでも同等の処理**
|
||||
- **ネスト呼び出しの安全性保証**
|
||||
|
||||
#### 実装パターン
|
||||
```rust
|
||||
pub fn invoke_python_method(handle: Handle, method: &str, args: &[Value]) -> Result<Value> {
|
||||
// GIL獲得
|
||||
let gil = Python::acquire_gil();
|
||||
let py = gil.python();
|
||||
|
||||
// Pythonオブジェクト取得
|
||||
let obj = get_pyobject_from_handle(handle)?;
|
||||
|
||||
// メソッド呼び出し
|
||||
let result = obj.call_method(py, method, args, None)?;
|
||||
|
||||
// 結果を変換
|
||||
let value = pyobject_to_value(result)?;
|
||||
|
||||
Ok(value)
|
||||
// GILは自動解放
|
||||
}
|
||||
```
|
||||
|
||||
## 🏗️ アーキテクチャ概要
|
||||
|
||||
### レイヤー構造
|
||||
|
||||
```
|
||||
┌─────────────────────────────────┐
|
||||
│ Hakorune Application │
|
||||
├─────────────────────────────────┤
|
||||
│ Python Integration Layer │
|
||||
│ - PyRuntimeBox │
|
||||
│ - PyObjectBox │
|
||||
├─────────────────────────────────┤
|
||||
│ FFI/Plugin Interface │
|
||||
│ - Handle-First design │
|
||||
│ - TLV type system │
|
||||
├─────────────────────────────────┤
|
||||
│ CPython C API │
|
||||
├─────────────────────────────────┤
|
||||
│ CPython Runtime │
|
||||
└─────────────────────────────────┘
|
||||
```
|
||||
|
||||
### プラグイン構成
|
||||
|
||||
```
|
||||
hakorune-python-plugin/
|
||||
├── src/
|
||||
│ ├── lib.rs # FFI entry point
|
||||
│ ├── runtime.rs # PyRuntimeBox
|
||||
│ ├── object.rs # PyObjectBox
|
||||
│ ├── conversion.rs # 型変換
|
||||
│ └── gil.rs # GIL管理
|
||||
├── Cargo.toml
|
||||
└── build.rs
|
||||
```
|
||||
|
||||
## 🔧 ネイティブビルド戦略
|
||||
|
||||
### AOT/EXEパイプライン
|
||||
|
||||
```
|
||||
Hakorune Source (.hkr)
|
||||
↓ Parse
|
||||
AST
|
||||
↓ Lower
|
||||
MIR
|
||||
↓ JIT Compile
|
||||
CLIF IR
|
||||
↓ Object Generation
|
||||
Object File (.o)
|
||||
↓ Link (with libhakorunert.a + Python libs)
|
||||
Native Executable
|
||||
```
|
||||
|
||||
### クロスプラットフォーム対応
|
||||
|
||||
| Platform | Python Library | 備考 |
|
||||
|----------|---------------|------|
|
||||
| Linux | libpython3.X.so | 動的リンク |
|
||||
| macOS | libpython3.X.dylib | 動的リンク |
|
||||
| Windows | python3X.dll | 動的リンク |
|
||||
|
||||
## 📊 設計決定事項
|
||||
|
||||
### 1. Embedding vs Extending
|
||||
|
||||
**決定**: Embedding優先
|
||||
|
||||
理由:
|
||||
- HakoruneからPythonを制御
|
||||
- デプロイが簡単
|
||||
- ユーザー体験が良い
|
||||
|
||||
### 2. 静的 vs 動的リンク
|
||||
|
||||
**決定**: 動的リンク優先、静的リンクはオプション
|
||||
|
||||
理由:
|
||||
- Python標準の配布方法
|
||||
- ライセンス問題の回避
|
||||
- 柔軟性の確保
|
||||
|
||||
### 3. サポート対象Python
|
||||
|
||||
**決定**: Python 3.8以降
|
||||
|
||||
理由:
|
||||
- 型ヒントの充実
|
||||
- 十分な普及
|
||||
- メンテナンス負荷
|
||||
|
||||
## ⚠️ リスク要因
|
||||
|
||||
### 1. CPython依存
|
||||
- バージョン互換性
|
||||
- プラットフォーム差異
|
||||
- ビルド環境の複雑さ
|
||||
|
||||
### 2. パフォーマンス
|
||||
- FFIオーバーヘッド
|
||||
- GIL待機時間
|
||||
- メモリコピーコスト
|
||||
|
||||
### 3. デバッグ困難性
|
||||
- 言語境界を越えるエラー
|
||||
- スタックトレースの複雑さ
|
||||
- メモリリークの追跡
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- [Phase 20 メインREADME](../README.md)
|
||||
- [Planning](../planning/)
|
||||
- [Core Implementation](../core-implementation/)
|
||||
@ -0,0 +1,53 @@
|
||||
# Phase 10.5a – Python 統合 ABI 設計(Draft)
|
||||
|
||||
目的: Everything is Plugin/AOT の既存基盤上に Python を最小リスクで統合するための ABI と型・メソッド定義を固定する。
|
||||
|
||||
## スコープ(10.5a)
|
||||
- v2 プラグイン ABI 準拠(`nyash_plugin_abi/init/invoke`)の Python プラグイン雛形を作成
|
||||
- 2 Box を定義: `PyRuntimeBox(type_id=40)`, `PyObjectBox(type_id=41)`
|
||||
- メソッド ID の割り当てと TLV 方針を文書化(実装は 10.5b 以降)
|
||||
|
||||
## TLV マッピング(現行運用)
|
||||
- 1 = Bool (1 byte)
|
||||
- 2 = I32 (4 bytes, LE)
|
||||
- 3 = I64 (8 bytes, LE)
|
||||
- 4 = F32 (4 bytes, LE)
|
||||
- 5 = F64 (8 bytes, LE)
|
||||
- 6 = String (UTF-8, n bytes)
|
||||
- 7 = Bytes (opaque, n bytes)
|
||||
- 8 = Handle/BoxRef (`u32 type_id || u32 instance_id`)
|
||||
|
||||
備考: 既存ドキュメントには古い表記の混在があるため、VM_README 準拠で統一。
|
||||
|
||||
## Box とメソッド設計
|
||||
|
||||
### PyRuntimeBox (type_id=40)
|
||||
- birth(0): ランタイムの生成(後続で GIL 初期化などを担当)。戻り値: `instance_id`(非 TLV, u32 LE)
|
||||
- eval(1, code: String): Python コードを評価して `PyObjectBox` を返す。戻り値: `Handle(tag=8)`
|
||||
- import(2, name: String): `__import__(name)` または `importlib.import_module`。戻り値: `Handle(tag=8)`
|
||||
- fini(MAX): ランタイム破棄(GIL 終了・クリーンアップ)
|
||||
|
||||
### PyObjectBox (type_id=41)
|
||||
- birth(0): 予約(通常は runtime 側から生まれる)
|
||||
- getattr(1, name: String): 属性取得 → `Handle(tag=8)`
|
||||
- call(2, args: TLV...): 可変長引数。初期段は I64/String/Bool/Bytes/Handle のサブセットに限定。戻り値: `Handle(tag=8)`
|
||||
- str(3): Python 側で `PyObject_Str` → String へ。戻り値: `String(tag=6)`
|
||||
- fini(MAX): 参照カウント `Py_DECREF` に対応(後続)
|
||||
|
||||
## 参照管理・GIL(概要)
|
||||
- GIL: birth/invoke/fini の入口で確保し、出口で解放(再入を許容)。
|
||||
- 参照: `PyObjectBox` は生成時に `INCREF`、`fini` で `DECREF`。ランタイム終了時に孤立検知の簡易テストを導入。
|
||||
|
||||
## 設定ファイル(nyash.toml)
|
||||
- `libnyash_python_plugin.so` を 2 Box 含む形で登録(path/type_id/method_id を固定)
|
||||
- JIT/VM 側は既存の `plugin_invoke` 経由で呼び出し(AOT は 10.5d で `libnyrt.a` にシム追加)
|
||||
|
||||
## 次フェーズ(10.5b 以降)
|
||||
- 10.5b: `PyRuntimeBox`/`PyObjectBox` 実装(CPython 埋め込み、最小 RO 経路)
|
||||
- 10.5c: Python→Nyash 方向(CPython 拡張 `nyashrt`)
|
||||
- 10.5d: JIT/AOT 連携(`emit_plugin_invoke` 対応・静的リンクシム)
|
||||
- 10.5e: サンプル・テスト・ドキュメント
|
||||
|
||||
---
|
||||
|
||||
補足: 本ドキュメントは「設計の固定」を目的とし、実装は段階的に進める。タグ/ID は既存と衝突しない値を選定した(40/41)。
|
||||
@ -0,0 +1,543 @@
|
||||
# Python-Hakorune統合 強化版アーキテクチャ v2
|
||||
|
||||
**作成**: 2025-10-02
|
||||
**ソース**: ChatGPT Pro UltraThink Mode
|
||||
**ステータス**: 設計提案
|
||||
|
||||
---
|
||||
|
||||
## 📋 概要
|
||||
|
||||
Phase 10.5の「Active」設計を踏まえつつ、**強化版Hakorune**(Effect/Capability/Contract/Policy・PHI検証・BlockVMap等)の上に載せる、**安全で境界に問題を閉じ込めたPythonブリッジ**の設計書です。
|
||||
|
||||
---
|
||||
|
||||
## 🎯 ねらい(Phase 10.5の「Active」意図との整合)
|
||||
|
||||
- 最小コアで **"箱(Box)に閉じ込めたPython実行環境"** を提供
|
||||
- VM/LLVM/AOTラインから同じ呼び出し規約で扱える
|
||||
- **当面はVMハーネス(llvmlite側)を使って決定実行とスモークの安定性を優先**、AOT/EXEは段階導入
|
||||
|
||||
---
|
||||
|
||||
## 🏗️ 1. Box階層(木構造)の基本セット
|
||||
|
||||
### PyRuntimeBox(ルート・単一 or 少数)
|
||||
|
||||
**役割**:
|
||||
- Pythonランタイム(CPython埋め込み)
|
||||
- `import` 解決
|
||||
- GIL管理
|
||||
- モジュールキャッシュ
|
||||
|
||||
**ライフサイクル**:
|
||||
- `init`: インタプリタ起動
|
||||
- `fini`: 停止
|
||||
- **Capability**で"import可能モジュール/FS/NET/ENV"を限定
|
||||
|
||||
**実装指針**:
|
||||
- まずは既存 **Plugin-First**(C ABI・TLV)でブリッジ
|
||||
- 後段で **Hakorune ABI(vtable)** に段階移行
|
||||
- `HAKO_ABI_VTABLE` 等のgateを活用
|
||||
|
||||
```hakorune
|
||||
box PyRuntimeBox {
|
||||
// 初期化・終了
|
||||
init()
|
||||
fini()
|
||||
|
||||
// モジュール
|
||||
import(name: StringBox) -> PyModuleBox
|
||||
reflect(module_name: StringBox) -> PyModuleBox
|
||||
|
||||
// 実行
|
||||
eval(code: StringBox) -> PyObjectBox
|
||||
exec(code: StringBox)
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### PyModuleBox
|
||||
|
||||
**役割**:
|
||||
- `import "pkg.mod"` の結果をBoxとして公開
|
||||
- 属性 = フィールド
|
||||
- 関数 = MethodBox
|
||||
|
||||
**ライフサイクル**:
|
||||
- `PyRuntimeBox` が所有
|
||||
- `fini` で参照解除(refcnt を減らす)
|
||||
|
||||
```hakorune
|
||||
box PyModuleBox {
|
||||
// 属性アクセス
|
||||
get(name: StringBox) -> PyObjectBox
|
||||
set(name: StringBox, value: PyObjectBox)
|
||||
|
||||
// 列挙
|
||||
list_attributes() -> ArrayBox
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### PyTypeBox / PyInstanceBox
|
||||
|
||||
**役割**:
|
||||
- Pythonのクラス定義とインスタンスをBox化
|
||||
- `get/setField` と `call_method` を統一導線に
|
||||
|
||||
**所有権タグ**:
|
||||
- **shared**(CPython RC前提)
|
||||
- `unique` が必要な場合は"借用トークン"で一時的に排他操作を許可
|
||||
|
||||
```hakorune
|
||||
box PyTypeBox {
|
||||
// クラス情報
|
||||
get_name() -> StringBox
|
||||
get_bases() -> ArrayBox
|
||||
get_methods() -> ArrayBox
|
||||
|
||||
// インスタンス化
|
||||
new_instance(args: ArrayBox) -> PyInstanceBox
|
||||
}
|
||||
|
||||
box PyInstanceBox {
|
||||
// フィールドアクセス
|
||||
get_field(name: StringBox) -> PyObjectBox
|
||||
set_field(name: StringBox, value: PyObjectBox)
|
||||
|
||||
// メソッド呼び出し
|
||||
call_method(name: StringBox, args: ArrayBox) -> PyObjectBox
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### PyFunctionBox / PyCallableBox
|
||||
|
||||
**役割**:
|
||||
- 呼出しを `exec(args)->result`(Pulse的)に落として**最小ライフサイクル**で扱える
|
||||
|
||||
```hakorune
|
||||
box PyFunctionBox {
|
||||
// Pulse: 完全な一発実行
|
||||
exec(args: ArrayBox) -> PyObjectBox
|
||||
|
||||
// メタ情報
|
||||
get_name() -> StringBox
|
||||
get_signature() -> StringBox
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### PyIteratorBox / PyGeneratorBox(必要に応じて)
|
||||
|
||||
**役割**:
|
||||
- `__iter__`/`__next__` をBox化
|
||||
- flow実行と相性を取る
|
||||
|
||||
```hakorune
|
||||
box PyIteratorBox {
|
||||
next() -> PyObjectBox
|
||||
has_next() -> BoolBox
|
||||
}
|
||||
|
||||
box PyGeneratorBox {
|
||||
send(value: PyObjectBox) -> PyObjectBox
|
||||
throw(error: ErrorBox)
|
||||
}
|
||||
```
|
||||
|
||||
> **Phase 10.5の設計メモと整合**:"最小の箱から着手 → 後から拡張"
|
||||
|
||||
---
|
||||
|
||||
## 🔄 2. ライフサイクル対応(Hakorune流)
|
||||
|
||||
### init/fini
|
||||
|
||||
**PyRuntimeBox.init()**:
|
||||
```rust
|
||||
fn init() {
|
||||
Py_Initialize();
|
||||
// import policyのロード
|
||||
// キャッシュ構築
|
||||
}
|
||||
```
|
||||
|
||||
**PyRuntimeBox.fini()**:
|
||||
```rust
|
||||
fn fini() {
|
||||
// weakref.finalize併用で安全解放(循環対策)
|
||||
Py_Finalize();
|
||||
}
|
||||
```
|
||||
|
||||
### Pulse
|
||||
|
||||
**PyFunctionBox.exec** は完全Pulse(init/fini不要):
|
||||
- **作用範囲はmetaのCapabilityに閉じ込め**
|
||||
- 副作用は明示的にEffect宣言
|
||||
|
||||
### 所有権タグ
|
||||
|
||||
- 既定: **shared**(RC準拠)
|
||||
- **unique** が必要な経路: `BorrowMutToken` を発行して**単発処理中のみ**排他
|
||||
|
||||
> これらは **管理棟のトグル**とも親和性が高い(dev: 緩める / prod: 厳格)
|
||||
|
||||
---
|
||||
|
||||
## 🎭 3. Effect / Capability / Contract の外付け(meta)
|
||||
|
||||
### Effect(論理的効果名)
|
||||
|
||||
```toml
|
||||
[box.PyRuntimeBox.effects]
|
||||
available = [
|
||||
"py.import",
|
||||
"py.fs",
|
||||
"py.net",
|
||||
"py.env",
|
||||
"py.time",
|
||||
"py.random",
|
||||
"py.subprocess"
|
||||
]
|
||||
```
|
||||
|
||||
### Capability(許可リスト)
|
||||
|
||||
```toml
|
||||
[box.PyRuntimeBox.capabilities]
|
||||
allow = [
|
||||
"py.import:math",
|
||||
"py.import:json",
|
||||
"py.time:monotonic"
|
||||
]
|
||||
deny = [
|
||||
"py.subprocess",
|
||||
"py.net"
|
||||
]
|
||||
enforce = true # devではfalse→観測のみ
|
||||
```
|
||||
|
||||
### Contract
|
||||
|
||||
**Pre条件**:
|
||||
```toml
|
||||
[contracts.PyFunctionBox.exec]
|
||||
pre = [
|
||||
"args.len <= 8",
|
||||
"bytes_total <= 1_000_000"
|
||||
]
|
||||
```
|
||||
|
||||
**Post条件**:
|
||||
```toml
|
||||
[contracts.PyFunctionBox.exec]
|
||||
post = [
|
||||
"result.size <= 1_000_000",
|
||||
"no_exception",
|
||||
"allow_none = true"
|
||||
]
|
||||
```
|
||||
|
||||
### 監査トグル
|
||||
|
||||
```bash
|
||||
# Dev/CI
|
||||
HAKO_PLUGIN_CAPS_ENFORCE=1
|
||||
HAKO_CHECK_CONTRACTS=1
|
||||
|
||||
# Prod
|
||||
HAKO_PLUGIN_CAPS_ENFORCE=1
|
||||
HAKO_CHECK_CONTRACTS=0 # 警告のみ
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🔁 4. Deterministic / Repro の扱い
|
||||
|
||||
### Deterministic モード
|
||||
|
||||
**問題**:
|
||||
- `random`, `time`, `os.urandom` 等は非決定的
|
||||
|
||||
**解決策**:
|
||||
- **Capability トークン経由**で提供するshimsを使用
|
||||
|
||||
**実装例**:
|
||||
|
||||
```python
|
||||
# py.random shim
|
||||
class DeterministicRandom:
|
||||
def __init__(self, seed):
|
||||
self._rng = random.Random(seed)
|
||||
|
||||
def random(self):
|
||||
return self._rng.random()
|
||||
|
||||
# py.time shim
|
||||
class LogicalClock:
|
||||
def __init__(self):
|
||||
self._tick = 0
|
||||
|
||||
def monotonic(self):
|
||||
self._tick += 1
|
||||
return float(self._tick)
|
||||
```
|
||||
|
||||
**トグル**:
|
||||
```bash
|
||||
# Deterministic モード有効化
|
||||
HAKO_DETERMINISTIC=1
|
||||
HAKO_TRACE_EFFECTS=1 # 効果ログ収集
|
||||
```
|
||||
|
||||
**メリット**:
|
||||
- **flow Main.main** 実行のスナップショット再現が可能
|
||||
- デバッグ容易性向上
|
||||
- テストの再現性保証
|
||||
|
||||
---
|
||||
|
||||
## 🌳 5. 木構造への「落とし方」(反射 → Box化)
|
||||
|
||||
### ビルダー(反射)
|
||||
|
||||
**PyRuntimeBox.reflect(module_name: String) -> PyModuleBox**:
|
||||
|
||||
1. `dir(module)` と `inspect` で**属性ツリーを走査**
|
||||
2. **Box**を生成
|
||||
3. **規約**:
|
||||
- 公開対象は `__all__` 優先
|
||||
- ない場合は `_` 先頭を除外
|
||||
- `@hako_export` デコレータがあれば優先で `FunctionBox` 化
|
||||
|
||||
**実装擬似コード**:
|
||||
|
||||
```python
|
||||
# Python側(リフレクションヘルパー)
|
||||
def reflect_module(module_name):
|
||||
mod = importlib.import_module(module_name)
|
||||
|
||||
# 属性リスト取得
|
||||
if hasattr(mod, '__all__'):
|
||||
attrs = mod.__all__
|
||||
else:
|
||||
attrs = [a for a in dir(mod) if not a.startswith('_')]
|
||||
|
||||
# Box化
|
||||
boxes = {}
|
||||
for attr_name in attrs:
|
||||
attr = getattr(mod, attr_name)
|
||||
|
||||
if callable(attr):
|
||||
boxes[attr_name] = create_function_box(attr)
|
||||
elif inspect.isclass(attr):
|
||||
boxes[attr_name] = create_type_box(attr)
|
||||
else:
|
||||
boxes[attr_name] = create_object_box(attr)
|
||||
|
||||
return boxes
|
||||
```
|
||||
|
||||
### 使用例
|
||||
|
||||
```hakorune
|
||||
using "python"
|
||||
|
||||
box Main {
|
||||
flow main() {
|
||||
// init: CPython起動
|
||||
let py = PyRuntimeBox();
|
||||
|
||||
// PyModuleBox
|
||||
let m = py.reflect("math");
|
||||
|
||||
// PyFunctionBox
|
||||
let sqrt = m.get("sqrt");
|
||||
|
||||
// 実行
|
||||
let r = sqrt.exec([2.0]);
|
||||
print(r); // -> 1.4142...
|
||||
|
||||
// 正常停止
|
||||
py.fini();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
> 反射で"木"を作り、**Box統一API(get/set/call)で走る** — Phase 10.5の「Activeは最小の箱から導入」を踏襲
|
||||
|
||||
---
|
||||
|
||||
## ⚠️ 6. 例外とエラー境界
|
||||
|
||||
### Python例外 → ErrorBox
|
||||
|
||||
```hakorune
|
||||
box ErrorBox {
|
||||
type: StringBox // "ZeroDivisionError"
|
||||
message: StringBox // "division by zero"
|
||||
traceback: StringBox // フルトレースバック
|
||||
}
|
||||
```
|
||||
|
||||
**変換例**:
|
||||
```python
|
||||
# Python側
|
||||
try:
|
||||
result = some_function()
|
||||
except Exception as e:
|
||||
return ErrorBox(
|
||||
type=type(e).__name__,
|
||||
message=str(e),
|
||||
traceback=traceback.format_exc()
|
||||
)
|
||||
```
|
||||
|
||||
### Contract違反
|
||||
|
||||
**Strict モード**:
|
||||
```bash
|
||||
HAKO_EXTERN_STRICT=1 # fail-fast
|
||||
```
|
||||
|
||||
**通常モード**:
|
||||
```bash
|
||||
HAKO_EXTERN_STRICT=0 # 警告 + ErrorBox返却
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🎛️ 7. 実行ポリシーとトグル(管理棟)
|
||||
|
||||
### ハーネス
|
||||
|
||||
```bash
|
||||
# 既定でPythonハーネス使用
|
||||
HAKO_LLVM_USE_HARNESS=1 # デフォルトON
|
||||
```
|
||||
|
||||
### PHIオプション
|
||||
|
||||
**ブリッジ互換**(PHI-off):
|
||||
```bash
|
||||
HAKO_VERIFY_ALLOW_NO_PHI=1 # 互換用途のみ
|
||||
```
|
||||
|
||||
**統一**(PHI-on):
|
||||
```bash
|
||||
HAKO_VERIFY_ALLOW_NO_PHI=0 # 推奨
|
||||
# Verifierを**PHI直後に常時実行**
|
||||
```
|
||||
|
||||
**モード設定**:
|
||||
- Dev: fail-fast
|
||||
- Prod: 警告
|
||||
|
||||
### ABI
|
||||
|
||||
**初期**(C ABI - TLV):
|
||||
```bash
|
||||
HAKO_ABI_VTABLE=0 # C ABI使用
|
||||
```
|
||||
|
||||
**段階移行**(Hakorune ABI - vtable):
|
||||
```bash
|
||||
HAKO_ABI_VTABLE=1
|
||||
HAKO_ABI_STRICT=1 # フォールバック禁止
|
||||
```
|
||||
|
||||
### Plugin観測
|
||||
|
||||
```bash
|
||||
# CI/Dev
|
||||
HAKO_TRACE_EFFECTS=1
|
||||
HAKO_PLUGIN_META=1
|
||||
HAKO_PLUGIN_CAPS_ENFORCE=1
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🚀 強化版Hakoruneでの設計図アップデート
|
||||
|
||||
### 1. 境界検証を"必須フェーズ"に
|
||||
|
||||
**実装**:
|
||||
- `finalize_phis()` の直後で **SSA/支配関係/到達性**を検証
|
||||
- Dev: 例外
|
||||
- Prod: 警告+トレース保全
|
||||
|
||||
**効果**:
|
||||
- Pythonブリッジ有無に関わらず**毎回**回る
|
||||
- IR品質を境界に閉じ込める
|
||||
|
||||
### 2. BlockVMap型でvmap/_current_vmapを統合
|
||||
|
||||
**実装**:
|
||||
- 参照は必ず `BlockVMap::at(block)` 経由
|
||||
- 呼び出し側から**どの視点が"真"か**を隠蔽
|
||||
|
||||
**効果**:
|
||||
- Python連携でもブロック境界で値がぶれない
|
||||
- 事故防止
|
||||
|
||||
### 3. InstructionContextを必須引数化
|
||||
|
||||
**実装**:
|
||||
- すべての `lower_*` に統一コンテキストを渡す
|
||||
- **ログ/例外に命令位置・BB名を強制添付**
|
||||
|
||||
**効果**:
|
||||
- 原因追跡が一気に楽に
|
||||
|
||||
### 4. flow Main.main を"仕様"として固定
|
||||
|
||||
**実装**:
|
||||
- Phase 10.5のActive方針と揃えて **flow優先**
|
||||
- staticを覚える必要なし
|
||||
|
||||
**効果**:
|
||||
- 入口の一意化
|
||||
- セルフホストの再現ビルド検証にも効く
|
||||
|
||||
### 5. 開発→本番の昇格パスを明確化
|
||||
|
||||
**Dev**:
|
||||
```bash
|
||||
HAKO_*_ENFORCE=0
|
||||
HAKO_TRACE=1
|
||||
# fail-fast ON
|
||||
```
|
||||
|
||||
**Prod**:
|
||||
```bash
|
||||
HAKO_*_ENFORCE=1
|
||||
HAKO_TRACE=0
|
||||
# fail-fast OFF(ErrorBox+警告)
|
||||
```
|
||||
|
||||
**効果**:
|
||||
- **管理棟env**にすでに集約されている設計
|
||||
- 運用で迷わない
|
||||
|
||||
---
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- [マイルストーン](../planning/milestones.md) - M0〜M6の詳細計画
|
||||
- [メタ設定例](meta-config-examples.md) - hako.toml設定例
|
||||
- [リスクと対策](risks-and-mitigations.md) - 既知のリスクと対策
|
||||
- [Phase 20 README](../README.md) - 全体概要
|
||||
|
||||
---
|
||||
|
||||
**最終更新**: 2025-10-02
|
||||
**作成者**: ChatGPT Pro (UltraThink Mode)
|
||||
**レビュー**: 未実施
|
||||
**ステータス**: 設計提案・Phase 15完了後に実装予定
|
||||
@ -0,0 +1,46 @@
|
||||
# Phase 10.5c — Handle-First PluginInvoke 設計(最優先計画)
|
||||
|
||||
目的: Python専用の型伝搬を撤廃し、プラグイン呼び出しを「Everything is Handle」で統一。Lowererは箱名や戻り型に依存しない最小知識で `PluginInvoke` を実Emitし、型解決は実行時(TLV/Handle)に委譲する。
|
||||
|
||||
## 背景と問題
|
||||
- 現状のLowererに「import/getattr/call の戻りを PyObjectBox とみなす」暫定コードが混入。これは Python 特化のハードコーディングで、将来のプラグイン拡張(File/Net/DB 等)にブレーキとなる。
|
||||
- すでに ABI/VM は TLV tag=8(Handle)を標準化。戻り値を Handle として受け取り、タイプ情報(type_id)は実行時に判明する。
|
||||
|
||||
## 原則(Handle-First)
|
||||
- すべてのプラグインメソッドの戻りは Handle(TLV: tag=8)またはプリミティブ(i64/f64/bool/string/bytes)。
|
||||
- Lowerer は「戻り型が box かどうか」だけを気にすればよい。個々の箱名(PyObjectBox 等)を前提にしない。
|
||||
- 型の詳細は `type_id` によって実行時に解決される。JIT/AOT は型非依存の汎用コード生成を行う。
|
||||
|
||||
## 設計
|
||||
1) メタデータ駆動
|
||||
- `nyash_box.toml` の `methods.*.returns = { type = "box" | "i64" | "f64" | "string" | "void" | ... }` を単一の参照源に。
|
||||
- `PluginHost.resolve_method` に `returns.type` を含む情報を公開(Lowerer から参照)。
|
||||
|
||||
2) Lowerer の汎用化
|
||||
- `PluginInvoke` を常に `emit_plugin_invoke(type_id, method_id, argc, has_ret)` に落とす。
|
||||
- 「戻りが box のときに特定箱名を記録する」実装を撤去。必要なら「dst は Handle(box)」のヒントのみ保持。
|
||||
- 受け手箱名が未確定の場合に備え、by-name 経路(後述)を用意。
|
||||
|
||||
3) by-name シム(任意→推奨)
|
||||
- `nyrt`/builder に `nyash_plugin_invoke_by_name_{i64,f64}(box_type_name?, method_name, a0, a1, a2)` を追加。
|
||||
- 受け手の箱名が Lowerer 時点で特定できない場合、by-name シムを使用して実行時に `method_id` を解決。
|
||||
|
||||
4) 実行時の統一
|
||||
- 既存の `nyash_plugin_invoke3_{i64,f64}` と同様に、TLVで引数を構築。Handle/プリミティブ変換(StringBox/IntegerBoxの自動プリミティブ化)を継続。
|
||||
- 戻りTLVの tag を見て i64/f64 経由の値化(`NYASH_JIT_NATIVE_F64`)またはハンドル登録を行う。
|
||||
|
||||
## マイルストーン
|
||||
- M1: Lowerer から Python特化の型伝搬を除去(dst=Handle ヒントのみ)。
|
||||
- M2: `PluginHost.resolve_method` 拡張で `returns.type` を取得可能に。
|
||||
- M3: by-name シムの追加と Lowerer 配線(箱名未確定時)。
|
||||
- M4: AOT 最小ケース(import→getattr→call)を Handle-First で Green。
|
||||
- M5: ドキュメントと CURRENT_TASK を刷新。
|
||||
|
||||
## 受け入れ条件(DoD)
|
||||
- VM: `py.import("math"); (math.getattr("sqrt")).call(9)` が Green(autodecode=1 で 3)。
|
||||
- AOT(strict): 上記チェーン最小例で unsupported=0。Console 出力経路は PluginInvoke または extern 経由で表示。
|
||||
- Lowerer に Python 固有の型分岐が存在しない(grepで検出不可)。
|
||||
|
||||
## 運用メモ
|
||||
- 将来的な最適化(箱名が静的に分かる場面での特殊化)は、Handle-First を壊さない範囲で「分岐の1箇所」に限定して導入する。
|
||||
|
||||
@ -0,0 +1,531 @@
|
||||
# hako.toml メタ設定例
|
||||
|
||||
**作成**: 2025-10-02
|
||||
**ソース**: ChatGPT Pro UltraThink Mode
|
||||
**用途**: Python統合のメタデータ設定リファレンス
|
||||
|
||||
---
|
||||
|
||||
## 📋 概要
|
||||
|
||||
Python-Hakorune統合における`hako.toml`の設定例集です。
|
||||
Effect/Capability/Contract/Policyの具体的な設定方法を示します。
|
||||
|
||||
---
|
||||
|
||||
## 🎯 基本設定
|
||||
|
||||
### 最小構成
|
||||
|
||||
```toml
|
||||
# hako.toml (minimal)
|
||||
[box.PyRuntimeBox]
|
||||
effects.allow = ["py.import:math"]
|
||||
```
|
||||
|
||||
### 標準構成
|
||||
|
||||
```toml
|
||||
# hako.toml (standard)
|
||||
[box.PyRuntimeBox]
|
||||
effects.allow = [
|
||||
"py.import:math",
|
||||
"py.import:json",
|
||||
"py.time:monotonic"
|
||||
]
|
||||
capabilities.enforce = true
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🎭 Effect設定
|
||||
|
||||
### 利用可能なEffect一覧
|
||||
|
||||
```toml
|
||||
[box.PyRuntimeBox.effects]
|
||||
available = [
|
||||
# モジュールインポート
|
||||
"py.import",
|
||||
|
||||
# ファイルシステム
|
||||
"py.fs.read",
|
||||
"py.fs.write",
|
||||
|
||||
# ネットワーク
|
||||
"py.net.http",
|
||||
"py.net.socket",
|
||||
|
||||
# 環境変数
|
||||
"py.env.read",
|
||||
"py.env.write",
|
||||
|
||||
# 時刻
|
||||
"py.time.monotonic",
|
||||
"py.time.real",
|
||||
|
||||
# ランダム
|
||||
"py.random",
|
||||
|
||||
# プロセス
|
||||
"py.subprocess"
|
||||
]
|
||||
```
|
||||
|
||||
### Effect許可例
|
||||
|
||||
```toml
|
||||
[box.PyRuntimeBox.effects]
|
||||
allow = [
|
||||
"py.import:math",
|
||||
"py.import:json",
|
||||
"py.import:re",
|
||||
"py.time:monotonic",
|
||||
"py.fs.read:/tmp/**"
|
||||
]
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🛡️ Capability設定
|
||||
|
||||
### 基本Capability
|
||||
|
||||
```toml
|
||||
[box.PyRuntimeBox.capabilities]
|
||||
# 許可リスト
|
||||
allow = [
|
||||
"py.import:math",
|
||||
"py.import:json"
|
||||
]
|
||||
|
||||
# 拒否リスト
|
||||
deny = [
|
||||
"py.subprocess",
|
||||
"py.net"
|
||||
]
|
||||
|
||||
# 厳格モード
|
||||
enforce = true
|
||||
```
|
||||
|
||||
### 詳細Capability(モジュール別)
|
||||
|
||||
```toml
|
||||
[box.PyRuntimeBox.capabilities.import]
|
||||
# 標準ライブラリ
|
||||
stdlib = [
|
||||
"math",
|
||||
"json",
|
||||
"re",
|
||||
"datetime",
|
||||
"collections"
|
||||
]
|
||||
|
||||
# サードパーティ(ホワイトリスト)
|
||||
allow_third_party = [
|
||||
"numpy",
|
||||
"pandas"
|
||||
]
|
||||
|
||||
# 拒否(ブラックリスト)
|
||||
deny = [
|
||||
"os",
|
||||
"subprocess",
|
||||
"socket"
|
||||
]
|
||||
```
|
||||
|
||||
### ファイルシステムCapability
|
||||
|
||||
```toml
|
||||
[box.PyRuntimeBox.capabilities.fs]
|
||||
# 読み取り許可
|
||||
read_paths = [
|
||||
"/tmp/**",
|
||||
"/data/input/**",
|
||||
"~/.config/app/**"
|
||||
]
|
||||
|
||||
# 書き込み許可
|
||||
write_paths = [
|
||||
"/tmp/**",
|
||||
"/data/output/**"
|
||||
]
|
||||
|
||||
# 拒否
|
||||
deny_paths = [
|
||||
"/etc/**",
|
||||
"/sys/**",
|
||||
"~/.ssh/**"
|
||||
]
|
||||
```
|
||||
|
||||
### ネットワークCapability
|
||||
|
||||
```toml
|
||||
[box.PyRuntimeBox.capabilities.net]
|
||||
# HTTP許可
|
||||
http_allow = [
|
||||
"https://api.example.com/**",
|
||||
"https://data.example.org/api/**"
|
||||
]
|
||||
|
||||
# Socket許可(ホスト:ポート)
|
||||
socket_allow = [
|
||||
"localhost:8080",
|
||||
"127.0.0.1:5432"
|
||||
]
|
||||
|
||||
# 拒否
|
||||
deny = [
|
||||
"0.0.0.0:*", # すべてのインターフェース
|
||||
"*:22", # SSH
|
||||
"*:3389" # RDP
|
||||
]
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## ✅ Contract設定
|
||||
|
||||
### PyFunctionBox Contract
|
||||
|
||||
```toml
|
||||
[contracts.PyFunctionBox.exec]
|
||||
# Pre条件(引数チェック)
|
||||
pre = [
|
||||
"args.len <= 8", # 引数は8個まで
|
||||
"bytes_total <= 1_000_000", # 合計1MB以下
|
||||
"no_file_descriptors" # ファイルディスクリプタ禁止
|
||||
]
|
||||
|
||||
# Post条件(返り値チェック)
|
||||
post = [
|
||||
"result.size <= 1_000_000", # 返り値1MB以下
|
||||
"no_exception", # 例外禁止
|
||||
"allow_none = true", # None許可
|
||||
"execution_time <= 5.0" # 5秒以内
|
||||
]
|
||||
|
||||
# 違反時の挙動
|
||||
on_violation = "error" # "error" | "warn" | "ignore"
|
||||
```
|
||||
|
||||
### PyModuleBox Contract
|
||||
|
||||
```toml
|
||||
[contracts.PyModuleBox.import]
|
||||
pre = [
|
||||
"module_name.len <= 100", # モジュール名100文字以内
|
||||
"no_relative_import" # 相対インポート禁止
|
||||
]
|
||||
|
||||
post = [
|
||||
"module_size <= 10_000_000", # モジュールサイズ10MB以下
|
||||
"no_native_code" # ネイティブコード禁止(オプション)
|
||||
]
|
||||
```
|
||||
|
||||
### PyInstanceBox Contract
|
||||
|
||||
```toml
|
||||
[contracts.PyInstanceBox.call_method]
|
||||
pre = [
|
||||
"method_name.len <= 50", # メソッド名50文字以内
|
||||
"args.len <= 16" # 引数16個まで
|
||||
]
|
||||
|
||||
post = [
|
||||
"result.size <= 1_000_000", # 返り値1MB以下
|
||||
"no_side_effects" # 副作用禁止(Pure)
|
||||
]
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🎛️ Policy設定
|
||||
|
||||
### 開発モード(Dev)
|
||||
|
||||
```toml
|
||||
[policy.dev]
|
||||
# Capability
|
||||
capabilities.enforce = false # 観測のみ
|
||||
capabilities.log = true # ログ記録
|
||||
|
||||
# Contract
|
||||
contracts.enforce = true # 厳格チェック
|
||||
contracts.on_violation = "error" # 違反時エラー
|
||||
|
||||
# Deterministic
|
||||
deterministic = false # 非決定的許可
|
||||
|
||||
# Trace
|
||||
trace.effects = true # 効果トレース
|
||||
trace.calls = true # 呼び出しトレース
|
||||
trace.errors = true # エラートレース
|
||||
|
||||
# Verifier
|
||||
verify.phi = true # PHI検証
|
||||
verify.ssa = true # SSA検証
|
||||
verify.on_fail = "error" # 検証失敗時エラー
|
||||
```
|
||||
|
||||
### 本番モード(Prod)
|
||||
|
||||
```toml
|
||||
[policy.prod]
|
||||
# Capability
|
||||
capabilities.enforce = true # 厳格適用
|
||||
capabilities.log = false # ログなし
|
||||
|
||||
# Contract
|
||||
contracts.enforce = true # 厳格チェック
|
||||
contracts.on_violation = "warn" # 違反時警告
|
||||
|
||||
# Deterministic
|
||||
deterministic = true # 決定的実行
|
||||
|
||||
# Trace
|
||||
trace.effects = false # トレースなし
|
||||
trace.calls = false
|
||||
trace.errors = true # エラーのみ
|
||||
|
||||
# Verifier
|
||||
verify.phi = true # PHI検証
|
||||
verify.ssa = true # SSA検証
|
||||
verify.on_fail = "warn" # 検証失敗時警告
|
||||
```
|
||||
|
||||
### テストモード(Test)
|
||||
|
||||
```toml
|
||||
[policy.test]
|
||||
# Capability
|
||||
capabilities.enforce = true # 厳格適用
|
||||
capabilities.log = true # ログ記録
|
||||
|
||||
# Contract
|
||||
contracts.enforce = true # 厳格チェック
|
||||
contracts.on_violation = "error" # 違反時エラー
|
||||
|
||||
# Deterministic
|
||||
deterministic = true # 決定的実行(再現性)
|
||||
|
||||
# Trace
|
||||
trace.effects = true # 全トレース
|
||||
trace.calls = true
|
||||
trace.errors = true
|
||||
|
||||
# Verifier
|
||||
verify.phi = true # 全検証
|
||||
verify.ssa = true
|
||||
verify.on_fail = "error" # 検証失敗時エラー
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🔧 環境変数によるオーバーライド
|
||||
|
||||
### 優先順位
|
||||
|
||||
1. 環境変数(最優先)
|
||||
2. hako.toml
|
||||
3. hakorune.toml
|
||||
4. デフォルト値
|
||||
|
||||
### 環境変数例
|
||||
|
||||
```bash
|
||||
# Capability
|
||||
export HAKO_PLUGIN_CAPS_ENFORCE=1
|
||||
export HAKO_TRACE_EFFECTS=1
|
||||
|
||||
# Contract
|
||||
export HAKO_CHECK_CONTRACTS=1
|
||||
export HAKO_CONTRACT_VIOLATION=error
|
||||
|
||||
# Deterministic
|
||||
export HAKO_DETERMINISTIC=1
|
||||
|
||||
# ABI
|
||||
export HAKO_ABI_VTABLE=1
|
||||
export HAKO_ABI_STRICT=1
|
||||
|
||||
# Verifier
|
||||
export HAKO_VERIFY_ALLOW_NO_PHI=0
|
||||
export HAKO_VERIFY_ON_FAIL=error
|
||||
|
||||
# LLVM
|
||||
export HAKO_LLVM_USE_HARNESS=1
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📊 実用例
|
||||
|
||||
### 例1: 数学計算のみ許可
|
||||
|
||||
```toml
|
||||
# hako.toml
|
||||
[box.PyRuntimeBox]
|
||||
effects.allow = ["py.import:math"]
|
||||
capabilities.enforce = true
|
||||
|
||||
[contracts.PyFunctionBox.exec]
|
||||
pre = ["args.len <= 4"]
|
||||
post = ["no_exception", "execution_time <= 1.0"]
|
||||
```
|
||||
|
||||
```hakorune
|
||||
using "python"
|
||||
|
||||
box Main {
|
||||
flow main() {
|
||||
let py = PyRuntimeBox();
|
||||
let math = py.import("math");
|
||||
let sqrt = math.get("sqrt");
|
||||
let r = sqrt.exec([2.0]);
|
||||
print(r); // OK
|
||||
py.fini();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 例2: データ処理(ファイル読み取り)
|
||||
|
||||
```toml
|
||||
# hako.toml
|
||||
[box.PyRuntimeBox]
|
||||
effects.allow = [
|
||||
"py.import:json",
|
||||
"py.fs.read:/data/input/**"
|
||||
]
|
||||
|
||||
[box.PyRuntimeBox.capabilities.fs]
|
||||
read_paths = ["/data/input/**"]
|
||||
write_paths = [] # 書き込み禁止
|
||||
```
|
||||
|
||||
```hakorune
|
||||
using "python"
|
||||
|
||||
box Main {
|
||||
flow main() {
|
||||
let py = PyRuntimeBox();
|
||||
let json = py.import("json");
|
||||
|
||||
// ファイル読み取り(許可)
|
||||
let data = py.eval("open('/data/input/test.json').read()");
|
||||
let parsed = json.get("loads").exec([data]);
|
||||
|
||||
print(parsed);
|
||||
py.fini();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 例3: API呼び出し(ネットワーク)
|
||||
|
||||
```toml
|
||||
# hako.toml
|
||||
[box.PyRuntimeBox]
|
||||
effects.allow = [
|
||||
"py.import:urllib",
|
||||
"py.net.http"
|
||||
]
|
||||
|
||||
[box.PyRuntimeBox.capabilities.net]
|
||||
http_allow = [
|
||||
"https://api.example.com/**"
|
||||
]
|
||||
|
||||
[contracts.PyFunctionBox.exec]
|
||||
pre = ["args.len <= 2"]
|
||||
post = [
|
||||
"result.size <= 1_000_000",
|
||||
"execution_time <= 10.0"
|
||||
]
|
||||
```
|
||||
|
||||
```hakorune
|
||||
using "python"
|
||||
|
||||
box Main {
|
||||
flow main() {
|
||||
let py = PyRuntimeBox();
|
||||
|
||||
let code = "
|
||||
import urllib.request
|
||||
def fetch(url):
|
||||
with urllib.request.urlopen(url) as r:
|
||||
return r.read()
|
||||
";
|
||||
py.exec(code);
|
||||
let fetch = py.get("fetch");
|
||||
|
||||
// API呼び出し(許可)
|
||||
let result = fetch.exec(["https://api.example.com/data"]);
|
||||
print(result);
|
||||
|
||||
py.fini();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🔍 デバッグ設定
|
||||
|
||||
### 詳細ログ
|
||||
|
||||
```toml
|
||||
[debug]
|
||||
# すべてのトレース有効化
|
||||
trace.all = true
|
||||
|
||||
# 個別トレース
|
||||
trace.effects = true
|
||||
trace.capabilities = true
|
||||
trace.contracts = true
|
||||
trace.python_calls = true
|
||||
trace.gil = true
|
||||
|
||||
# ログレベル
|
||||
log_level = "debug"
|
||||
|
||||
# ログ出力先
|
||||
log_file = "/tmp/hakorune-python-debug.log"
|
||||
```
|
||||
|
||||
### パフォーマンスプロファイル
|
||||
|
||||
```toml
|
||||
[profile]
|
||||
# タイミング記録
|
||||
timing.enabled = true
|
||||
timing.threshold = 0.1 # 100ms以上
|
||||
|
||||
# メモリ使用量
|
||||
memory.track = true
|
||||
memory.threshold = 10_000_000 # 10MB以上
|
||||
|
||||
# GC統計
|
||||
gc.enabled = true
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- [強化版アーキテクチャv2](enhanced-architecture-v2.md) - 設計詳細
|
||||
- [マイルストーン](../planning/milestones.md) - 実装計画
|
||||
- [リスクと対策](risks-and-mitigations.md) - リスク管理
|
||||
- [Phase 20 README](../README.md) - 全体概要
|
||||
|
||||
---
|
||||
|
||||
**最終更新**: 2025-10-02
|
||||
**作成者**: ChatGPT Pro (UltraThink Mode)
|
||||
**ステータス**: 設定リファレンス
|
||||
@ -0,0 +1,37 @@
|
||||
# 10.5b – ネイティブビルド基盤の固め(AOT/EXE)
|
||||
|
||||
Python統合を本格化する前に、配布可能なネイティブ実行ファイル(EXE)の足回りを先に完成させる。JITは実行エンジンから外し、EXE生成専用のコンパイラとして運用する。
|
||||
|
||||
## 🎯 目的
|
||||
- VM=実行、JIT=EXE(AOT)の二系統を明確化(フォールバックなし/Fail-Fast)
|
||||
- CLIF→.o→`libnyrt`リンク→EXEのパイプラインを実効化
|
||||
- プラグイン解決をクロスプラットフォームに(.so/.dll/.dylib、自動lib剥がし、検索パス)
|
||||
- Windowsを含む実用的な配布体験を整備
|
||||
|
||||
## 🧩 範囲
|
||||
- JIT分離・Strict運用(Fail-Fast/No-fallback)
|
||||
- AOTパイプライン: `--compile-native` と `tools/build_aot.{sh,ps1}`
|
||||
- プラグインローダの拡張: 拡張子変換/`lib`剥がし、`plugin_paths`+`NYASH_PLUGIN_PATHS`
|
||||
- Windowsリンク: clang優先(`nyrt.lib`/`libnyrt.a`両対応)、bash+cc fallback
|
||||
- 観測/EXE出力の統一: `Result: <val>`、終了コード=<val>
|
||||
|
||||
## ✅ 成果(DoD)
|
||||
- `cargo build --release --features cranelift-jit` の後、
|
||||
- Linux: `./tools/build_aot.sh examples/aot_min_string_len.nyash -o app && ./app`
|
||||
- Windows: `powershell -ExecutionPolicy Bypass -File tools\build_aot.ps1 -Input examples\aot_min_string_len.nyash -Out app.exe && .\app.exe`
|
||||
- プラグインは `.so` 記述でも各OSで自動解決(.dll/.dylib へ変換、lib剥がし)
|
||||
- `tools/smoke_aot_vs_vm.sh` で VM/EXE の `Result:` 行比較が可能(差異は警告表示)
|
||||
|
||||
## 🔧 実装メモ
|
||||
- `src/runtime/plugin_loader_v2.rs` に `resolve_library_path()` を追加:
|
||||
- OS別拡張子、Windowsの`lib`剥がし、`plugin_paths`探索
|
||||
- `src/config/nyash_toml_v2.rs` に `NYASH_PLUGIN_PATHS` を追加(`;`/`:`区切り)
|
||||
- `AotConfigBox` に `set_plugin_paths()` 追加(env同期)
|
||||
- `crates/nyrt` の EXE出力統一(`Result:`/exit code)
|
||||
- Windows: `tools/build_aot.ps1`(clang→bash fallback)、Linux: `tools/build_aot.sh`
|
||||
|
||||
## 📌 次(10.5c 以降)
|
||||
- PyRuntimeBox/PyObjectBox(RO優先)
|
||||
- Python ABIルータを `libnyrt` に同梱(type_id→invokeディスパッチ)
|
||||
- 配布用パッケージ整備(nyash.toml/プラグイン配置ガイドの最終化)
|
||||
|
||||
@ -0,0 +1,441 @@
|
||||
# リスクと対策
|
||||
|
||||
**作成**: 2025-10-02
|
||||
**ソース**: ChatGPT Pro UltraThink Mode
|
||||
**用途**: Python統合における既知のリスクと対策
|
||||
|
||||
---
|
||||
|
||||
## 📋 概要
|
||||
|
||||
Python-Hakorune統合における技術的リスク、運用リスク、およびその対策をまとめます。
|
||||
|
||||
---
|
||||
|
||||
## 🔥 高リスク項目
|
||||
|
||||
### 1. GILデッドロック
|
||||
|
||||
#### リスク詳細
|
||||
- **問題**: Hakorune並列実行とPython GILのズレ
|
||||
- **発生条件**: Hakorune側マルチスレッド + Python呼び出しのネスト
|
||||
- **影響**: プログラム全体がハング、デバッグ困難
|
||||
|
||||
#### 対策
|
||||
|
||||
**アーキテクチャレベル**:
|
||||
```rust
|
||||
// PyRuntimeBoxを専用スレッドで実行
|
||||
pub struct PyRuntimeBox {
|
||||
thread: JoinHandle<()>,
|
||||
tx: Sender<PyCommand>,
|
||||
rx: Receiver<PyResult>,
|
||||
}
|
||||
|
||||
impl PyRuntimeBox {
|
||||
pub fn init() -> Self {
|
||||
let (tx, rx_cmd) = channel();
|
||||
let (tx_result, rx) = channel();
|
||||
|
||||
let thread = thread::spawn(move || {
|
||||
// このスレッドでGILを保持
|
||||
let gil = Python::acquire_gil();
|
||||
let py = gil.python();
|
||||
|
||||
loop {
|
||||
match rx_cmd.recv() {
|
||||
Ok(PyCommand::Import(name)) => {
|
||||
let result = py.import(&name);
|
||||
tx_result.send(PyResult::Module(result)).unwrap();
|
||||
}
|
||||
Ok(PyCommand::Shutdown) => break,
|
||||
Err(_) => break,
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
PyRuntimeBox { thread, tx, rx }
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**ガードレール**:
|
||||
```toml
|
||||
[debug.gil]
|
||||
# GIL獲得・解放のログ
|
||||
trace = true
|
||||
|
||||
# タイムアウト検出
|
||||
timeout = 5.0 # 5秒
|
||||
|
||||
# デッドロック検出
|
||||
detect_deadlock = true
|
||||
```
|
||||
|
||||
**モニタリング**:
|
||||
```bash
|
||||
# GILトレース有効化
|
||||
export HAKO_TRACE_GIL=1
|
||||
|
||||
# タイムアウト設定
|
||||
export HAKO_GIL_TIMEOUT=5.0
|
||||
```
|
||||
|
||||
#### 回避策
|
||||
1. **専用スレッド**でPython実行を隔離
|
||||
2. **メッセージパッシング**でHakorune-Python間通信
|
||||
3. **タイムアウト**で異常検出
|
||||
4. **ログ**で原因追跡
|
||||
|
||||
---
|
||||
|
||||
### 2. メモリリーク
|
||||
|
||||
#### リスク詳細
|
||||
- **問題**: Python参照カウント管理ミス
|
||||
- **発生条件**: `Py_INCREF`/`Py_DECREF`の不一致
|
||||
- **影響**: メモリ使用量増大、最悪OOM
|
||||
|
||||
#### 対策
|
||||
|
||||
**Arc管理**:
|
||||
```rust
|
||||
// PythonオブジェクトをArcでラップ
|
||||
pub struct PyObjectBox {
|
||||
inner: Arc<PyObjectInner>,
|
||||
}
|
||||
|
||||
struct PyObjectInner {
|
||||
py_obj: Py<PyAny>,
|
||||
}
|
||||
|
||||
impl Drop for PyObjectInner {
|
||||
fn drop(&mut self) {
|
||||
// 確実にDECREF
|
||||
Python::with_gil(|py| {
|
||||
self.py_obj.as_ref(py);
|
||||
});
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**weakref.finalize**:
|
||||
```python
|
||||
# Python側で自動クリーンアップ
|
||||
import weakref
|
||||
|
||||
def create_hakorune_object(obj):
|
||||
# finalizer登録
|
||||
finalizer = weakref.finalize(obj, cleanup_callback, obj_id)
|
||||
return obj
|
||||
```
|
||||
|
||||
**リーク検出**:
|
||||
```toml
|
||||
[debug.memory]
|
||||
# メモリトラッキング
|
||||
track = true
|
||||
|
||||
# リーク検出
|
||||
detect_leaks = true
|
||||
|
||||
# 定期チェック
|
||||
check_interval = 10.0 # 10秒
|
||||
```
|
||||
|
||||
**ツール**:
|
||||
```bash
|
||||
# Valgrind
|
||||
valgrind --leak-check=full ./hakorune script.hkr
|
||||
|
||||
# AddressSanitizer
|
||||
RUSTFLAGS="-Z sanitizer=address" cargo build
|
||||
|
||||
# Python memory profiler
|
||||
export PYTHONTRACEMALLOC=1
|
||||
```
|
||||
|
||||
#### 回避策
|
||||
1. **Arc/Drop**で自動管理
|
||||
2. **weakref.finalize**で循環参照対策
|
||||
3. **定期チェック**で早期発見
|
||||
4. **テスト**で継続監視
|
||||
|
||||
---
|
||||
|
||||
### 3. C拡張モジュールの扱い
|
||||
|
||||
#### リスク詳細
|
||||
- **問題**: numpy等のC拡張は特殊な扱いが必要
|
||||
- **発生条件**: ネイティブコードの直接呼び出し
|
||||
- **影響**: セグフォ、未定義動作
|
||||
|
||||
#### 対策
|
||||
|
||||
**Capability制御**:
|
||||
```toml
|
||||
[box.PyRuntimeBox.capabilities.native]
|
||||
# C拡張の許可
|
||||
allow_native = true
|
||||
|
||||
# ホワイトリスト
|
||||
allow_modules = [
|
||||
"numpy",
|
||||
"pandas",
|
||||
"_ctypes"
|
||||
]
|
||||
|
||||
# ブラックリスト
|
||||
deny_modules = [
|
||||
"ctypes", # 任意ネイティブコード実行
|
||||
"cffi"
|
||||
]
|
||||
```
|
||||
|
||||
**サンドボックス**(将来):
|
||||
```toml
|
||||
[sandbox]
|
||||
# ネイティブコードをサンドボックスで実行
|
||||
enable = true
|
||||
mode = "seccomp" # Linux
|
||||
```
|
||||
|
||||
**検証**:
|
||||
```rust
|
||||
// ロード前に検証
|
||||
fn verify_module_safety(module_name: &str) -> Result<()> {
|
||||
// シグネチャ確認
|
||||
// 既知の安全なモジュールか
|
||||
// ブラックリスト確認
|
||||
}
|
||||
```
|
||||
|
||||
#### 回避策
|
||||
1. **ホワイトリスト**で既知の安全なモジュールのみ許可
|
||||
2. **サンドボックス**で隔離実行(将来)
|
||||
3. **検証**でロード前チェック
|
||||
|
||||
---
|
||||
|
||||
## ⚠️ 中リスク項目
|
||||
|
||||
### 4. パフォーマンスオーバーヘッド
|
||||
|
||||
#### リスク詳細
|
||||
- **問題**: FFI境界・GIL・型変換のコスト
|
||||
- **影響**: 性能劣化
|
||||
|
||||
#### 対策
|
||||
|
||||
**最適化**:
|
||||
```rust
|
||||
// 型変換キャッシュ
|
||||
struct TypeCache {
|
||||
string_to_pyobject: HashMap<String, Py<PyString>>,
|
||||
int_to_pyobject: HashMap<i64, Py<PyLong>>,
|
||||
}
|
||||
|
||||
impl TypeCache {
|
||||
fn get_or_create_string(&mut self, py: Python, s: &str) -> Py<PyString> {
|
||||
self.string_to_pyobject
|
||||
.entry(s.to_string())
|
||||
.or_insert_with(|| PyString::new(py, s).into())
|
||||
.clone()
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**バッチ処理**:
|
||||
```rust
|
||||
// 複数呼び出しをまとめる
|
||||
fn batch_call(funcs: Vec<PyFunctionBox>, args: Vec<Vec<Value>>) -> Vec<Value> {
|
||||
Python::with_gil(|py| {
|
||||
funcs.iter().zip(args.iter())
|
||||
.map(|(f, a)| f.exec_with_gil(py, a))
|
||||
.collect()
|
||||
})
|
||||
}
|
||||
```
|
||||
|
||||
**ベンチマーク**:
|
||||
```bash
|
||||
# パフォーマンステスト
|
||||
cargo bench --features python-integration
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### 5. プラットフォーム固有問題
|
||||
|
||||
#### リスク詳細
|
||||
- **問題**: Python配布形態の違い(Linux/macOS/Windows)
|
||||
- **影響**: ビルド・実行時エラー
|
||||
|
||||
#### 対策
|
||||
|
||||
**プラットフォーム別設定**:
|
||||
```toml
|
||||
# Linux
|
||||
[target.x86_64-unknown-linux-gnu]
|
||||
python-lib = "python3.11"
|
||||
python-path = "/usr/lib/python3.11"
|
||||
|
||||
# macOS
|
||||
[target.x86_64-apple-darwin]
|
||||
python-lib = "python3.11"
|
||||
python-path = "/usr/local/opt/python@3.11"
|
||||
|
||||
# Windows
|
||||
[target.x86_64-pc-windows-msvc]
|
||||
python-lib = "python311"
|
||||
python-path = "C:/Python311"
|
||||
```
|
||||
|
||||
**CI/CD**:
|
||||
```yaml
|
||||
# .github/workflows/python-integration.yml
|
||||
strategy:
|
||||
matrix:
|
||||
os: [ubuntu-latest, macos-latest, windows-latest]
|
||||
python-version: ['3.8', '3.9', '3.10', '3.11']
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### 6. 例外伝播の複雑さ
|
||||
|
||||
#### リスク詳細
|
||||
- **問題**: Python例外とHakoruneエラーの境界
|
||||
- **影響**: エラーハンドリングの困難さ
|
||||
|
||||
#### 対策
|
||||
|
||||
**統一ErrorBox**:
|
||||
```hakorune
|
||||
box ErrorBox {
|
||||
type: StringBox // "ZeroDivisionError"
|
||||
message: StringBox // "division by zero"
|
||||
traceback: StringBox // フルスタックトレース
|
||||
source: StringBox // "python" | "hakorune"
|
||||
}
|
||||
```
|
||||
|
||||
**変換層**:
|
||||
```rust
|
||||
fn convert_py_exception(py_err: &PyErr) -> ErrorBox {
|
||||
ErrorBox {
|
||||
type_: py_err.get_type().name().to_string(),
|
||||
message: py_err.to_string(),
|
||||
traceback: format_traceback(py_err),
|
||||
source: "python".to_string(),
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📊 低リスク項目
|
||||
|
||||
### 7. ドキュメント不足
|
||||
|
||||
#### 対策
|
||||
- 段階的にドキュメント整備
|
||||
- コードサンプル充実
|
||||
- チュートリアル作成
|
||||
|
||||
### 8. テストカバレッジ
|
||||
|
||||
#### 対策
|
||||
- ユニットテスト追加
|
||||
- 統合テスト充実
|
||||
- E2Eテスト自動化
|
||||
|
||||
---
|
||||
|
||||
## 🛡️ リスク管理マトリックス
|
||||
|
||||
| リスク | 深刻度 | 発生確率 | 優先度 | 対策状況 |
|
||||
|-------|-------|---------|-------|---------|
|
||||
| GILデッドロック | 高 | 中 | 最優先 | 設計段階で対策 |
|
||||
| メモリリーク | 高 | 中 | 最優先 | Arc/Drop自動化 |
|
||||
| C拡張問題 | 高 | 低 | 高 | ホワイトリスト |
|
||||
| パフォーマンス | 中 | 高 | 中 | 最適化計画 |
|
||||
| プラットフォーム | 中 | 中 | 中 | CI/CD網羅 |
|
||||
| 例外伝播 | 中 | 低 | 低 | ErrorBox統一 |
|
||||
| ドキュメント | 低 | 高 | 低 | 段階的整備 |
|
||||
| テストカバレッジ | 低 | 中 | 低 | 継続改善 |
|
||||
|
||||
---
|
||||
|
||||
## 🔍 監視・検出
|
||||
|
||||
### 自動検出
|
||||
|
||||
```toml
|
||||
[monitoring]
|
||||
# GIL監視
|
||||
gil.timeout = 5.0
|
||||
gil.alert_on_timeout = true
|
||||
|
||||
# メモリ監視
|
||||
memory.threshold = 100_000_000 # 100MB
|
||||
memory.alert_on_threshold = true
|
||||
|
||||
# パフォーマンス監視
|
||||
performance.slow_call_threshold = 1.0 # 1秒
|
||||
performance.alert_on_slow = true
|
||||
```
|
||||
|
||||
### ログ
|
||||
|
||||
```bash
|
||||
# すべての監視ログ
|
||||
export HAKO_TRACE_GIL=1
|
||||
export HAKO_TRACE_MEMORY=1
|
||||
export HAKO_TRACE_PERFORMANCE=1
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📝 インシデント対応
|
||||
|
||||
### 1. GILデッドロック発生時
|
||||
|
||||
```bash
|
||||
# 1. ログ確認
|
||||
cat /tmp/hakorune-debug.log | grep GIL
|
||||
|
||||
# 2. スタックトレース取得
|
||||
kill -QUIT <pid>
|
||||
|
||||
# 3. デバッガー接続
|
||||
gdb -p <pid>
|
||||
```
|
||||
|
||||
### 2. メモリリーク発生時
|
||||
|
||||
```bash
|
||||
# 1. メモリ使用量確認
|
||||
ps aux | grep hakorune
|
||||
|
||||
# 2. Valgrind実行
|
||||
valgrind --leak-check=full ./hakorune script.hkr
|
||||
|
||||
# 3. Python側確認
|
||||
export PYTHONTRACEMALLOC=1
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- [強化版アーキテクチャv2](enhanced-architecture-v2.md) - 設計詳細
|
||||
- [マイルストーン](../planning/milestones.md) - 実装計画
|
||||
- [メタ設定例](meta-config-examples.md) - 設定例
|
||||
- [Phase 20 README](../README.md) - 全体概要
|
||||
|
||||
---
|
||||
|
||||
**最終更新**: 2025-10-02
|
||||
**作成者**: ChatGPT Pro (UltraThink Mode)
|
||||
**ステータス**: リスク管理ドキュメント
|
||||
@ -0,0 +1,270 @@
|
||||
# Documentation - ドキュメント
|
||||
|
||||
## 📋 概要
|
||||
|
||||
Python-Hakorune統合のドキュメント計画です。
|
||||
|
||||
## 📚 ドキュメント構成
|
||||
|
||||
### 1. ユーザーガイド
|
||||
|
||||
#### クイックスタート
|
||||
```markdown
|
||||
# Python統合クイックスタート
|
||||
|
||||
## インストール
|
||||
|
||||
hakorune-pythonプラグインをインストール:
|
||||
```bash
|
||||
cargo build --release --features python-integration
|
||||
```
|
||||
|
||||
## 基本的な使い方
|
||||
|
||||
```hakorune
|
||||
// Pythonコードを実行
|
||||
local py = new PyRuntimeBox()
|
||||
local result = py.eval("2 + 3")
|
||||
console.log(result.to_string()) // "5"
|
||||
|
||||
// モジュールをインポート
|
||||
local math = py.import("math")
|
||||
local pi = math.getattr("pi")
|
||||
console.log(pi.to_string()) // "3.14159..."
|
||||
```
|
||||
```
|
||||
|
||||
#### チュートリアル
|
||||
- Python基本操作
|
||||
- モジュールインポート
|
||||
- オブジェクト操作
|
||||
- エラーハンドリング
|
||||
- パフォーマンス最適化
|
||||
|
||||
### 2. リファレンス
|
||||
|
||||
#### PyRuntimeBox API
|
||||
```markdown
|
||||
# PyRuntimeBox
|
||||
|
||||
Python実行環境を提供するBox。
|
||||
|
||||
## メソッド
|
||||
|
||||
### eval(code: StringBox) -> PyObjectBox
|
||||
Pythonコードを評価し、結果を返す。
|
||||
|
||||
**引数:**
|
||||
- `code`: 実行するPythonコード
|
||||
|
||||
**戻り値:**
|
||||
- `PyObjectBox`: 実行結果
|
||||
|
||||
**例:**
|
||||
```hakorune
|
||||
local py = new PyRuntimeBox()
|
||||
local result = py.eval("2 + 3")
|
||||
```
|
||||
|
||||
### import(name: StringBox) -> PyObjectBox
|
||||
Pythonモジュールをインポート。
|
||||
|
||||
**引数:**
|
||||
- `name`: モジュール名
|
||||
|
||||
**戻り値:**
|
||||
- `PyObjectBox`: インポートされたモジュール
|
||||
|
||||
**例:**
|
||||
```hakorune
|
||||
local math = py.import("math")
|
||||
```
|
||||
```
|
||||
|
||||
#### PyObjectBox API
|
||||
```markdown
|
||||
# PyObjectBox
|
||||
|
||||
Pythonオブジェクトを表すBox。
|
||||
|
||||
## メソッド
|
||||
|
||||
### getattr(name: StringBox) -> PyObjectBox
|
||||
オブジェクトの属性を取得。
|
||||
|
||||
### setattr(name: StringBox, value: PyObjectBox)
|
||||
オブジェクトの属性を設定。
|
||||
|
||||
### call(args: ArrayBox) -> PyObjectBox
|
||||
オブジェクトを関数として呼び出し。
|
||||
|
||||
### to_string() -> StringBox
|
||||
Pythonオブジェクトを文字列に変換。
|
||||
|
||||
### to_int() -> IntegerBox
|
||||
Pythonオブジェクトを整数に変換。
|
||||
|
||||
### to_bool() -> BoolBox
|
||||
Pythonオブジェクトを真偽値に変換。
|
||||
```
|
||||
|
||||
### 3. 設計ドキュメント
|
||||
|
||||
#### アーキテクチャ
|
||||
- 全体構成
|
||||
- レイヤー構造
|
||||
- データフロー
|
||||
|
||||
#### ABI仕様
|
||||
- ハンドル管理
|
||||
- 型変換ルール
|
||||
- エラーハンドリング
|
||||
|
||||
#### GIL管理
|
||||
- 獲得・解放ルール
|
||||
- ネスト呼び出し
|
||||
- マルチスレッド対応
|
||||
|
||||
### 4. 開発者ガイド
|
||||
|
||||
#### プラグイン開発
|
||||
```markdown
|
||||
# Python統合プラグイン開発ガイド
|
||||
|
||||
## プラグインの構造
|
||||
|
||||
```rust
|
||||
// src/lib.rs
|
||||
use hakorune_plugin_api::*;
|
||||
|
||||
#[no_mangle]
|
||||
pub extern "C" fn nyplug_python_invoke(
|
||||
method_id: u32,
|
||||
args: *const TLV,
|
||||
args_len: usize,
|
||||
ret: *mut TLV,
|
||||
) -> i32 {
|
||||
// 実装
|
||||
}
|
||||
```
|
||||
|
||||
## ビルド
|
||||
|
||||
```bash
|
||||
cargo build --release --crate-type cdylib
|
||||
```
|
||||
```
|
||||
|
||||
#### コントリビューション
|
||||
- コーディング規約
|
||||
- テストガイドライン
|
||||
- プルリクエストプロセス
|
||||
|
||||
### 5. トラブルシューティング
|
||||
|
||||
#### よくある問題
|
||||
|
||||
**Q: Pythonモジュールが見つからない**
|
||||
```
|
||||
A: PYTHONPATHを設定してください:
|
||||
export PYTHONPATH=/path/to/modules:$PYTHONPATH
|
||||
```
|
||||
|
||||
**Q: GILデッドロックが発生する**
|
||||
```
|
||||
A: ネスト呼び出しを避けるか、GILを明示的に解放してください。
|
||||
```
|
||||
|
||||
**Q: メモリリークが発生する**
|
||||
```
|
||||
A: PyObjectBoxを適切にdropしているか確認してください。
|
||||
```
|
||||
|
||||
## 📝 ドキュメント作成タスク
|
||||
|
||||
### Phase 1: 基本ドキュメント
|
||||
- [ ] README.md(概要)
|
||||
- [ ] QUICKSTART.md(クイックスタート)
|
||||
- [ ] INSTALLATION.md(インストール)
|
||||
|
||||
### Phase 2: API リファレンス
|
||||
- [ ] PyRuntimeBox API
|
||||
- [ ] PyObjectBox API
|
||||
- [ ] 型変換ルール
|
||||
|
||||
### Phase 3: チュートリアル
|
||||
- [ ] 基本操作
|
||||
- [ ] モジュールインポート
|
||||
- [ ] オブジェクト操作
|
||||
- [ ] エラーハンドリング
|
||||
|
||||
### Phase 4: 開発者向け
|
||||
- [ ] アーキテクチャ設計
|
||||
- [ ] プラグイン開発ガイド
|
||||
- [ ] コントリビューションガイド
|
||||
|
||||
### Phase 5: その他
|
||||
- [ ] トラブルシューティング
|
||||
- [ ] パフォーマンスガイド
|
||||
- [ ] ベストプラクティス
|
||||
|
||||
## 🎯 ドキュメント品質基準
|
||||
|
||||
### 必須要件
|
||||
- [ ] コードサンプルが動作する
|
||||
- [ ] 用語が一貫している
|
||||
- [ ] エラーメッセージが明確
|
||||
- [ ] プラットフォーム差異を記載
|
||||
|
||||
### 推奨要件
|
||||
- [ ] 図表を含む
|
||||
- [ ] ビデオチュートリアル
|
||||
- [ ] 多言語対応(日本語・英語)
|
||||
- [ ] 検索可能
|
||||
|
||||
## 📊 ドキュメント構成図
|
||||
|
||||
```
|
||||
docs/
|
||||
├── guides/
|
||||
│ ├── python-integration/
|
||||
│ │ ├── README.md # 概要
|
||||
│ │ ├── quickstart.md # クイックスタート
|
||||
│ │ ├── installation.md # インストール
|
||||
│ │ ├── tutorial/ # チュートリアル
|
||||
│ │ │ ├── 01-basics.md
|
||||
│ │ │ ├── 02-modules.md
|
||||
│ │ │ ├── 03-objects.md
|
||||
│ │ │ └── 04-errors.md
|
||||
│ │ └── troubleshooting.md # トラブルシューティング
|
||||
│ └── ...
|
||||
├── reference/
|
||||
│ ├── python-integration/
|
||||
│ │ ├── pyruntimebox-api.md # PyRuntimeBox API
|
||||
│ │ ├── pyobjectbox-api.md # PyObjectBox API
|
||||
│ │ ├── type-conversion.md # 型変換ルール
|
||||
│ │ └── error-handling.md # エラーハンドリング
|
||||
│ └── ...
|
||||
└── development/
|
||||
└── python-integration/
|
||||
├── architecture.md # アーキテクチャ
|
||||
├── plugin-dev.md # プラグイン開発
|
||||
└── contributing.md # コントリビューション
|
||||
```
|
||||
|
||||
## 🔗 関連リソース
|
||||
|
||||
### 公式ドキュメント
|
||||
- [Python C API](https://docs.python.org/3/c-api/)
|
||||
- [PyO3 Guide](https://pyo3.rs/)
|
||||
|
||||
### 参考実装
|
||||
- Rust PyO3
|
||||
- Node.js Python bindings
|
||||
- Julia Python interop
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- [Phase 20 メインREADME](../README.md)
|
||||
- [Planning](../planning/)
|
||||
- [Core Implementation](../core-implementation/)
|
||||
@ -0,0 +1,121 @@
|
||||
# Parser Integration - Pythonパーサー統合
|
||||
|
||||
## 📋 概要
|
||||
|
||||
PythonのAST(抽象構文木)をHakoruneで扱うためのパーサー統合設計です。
|
||||
|
||||
## 📁 ファイル一覧
|
||||
|
||||
### 実装計画
|
||||
- **[implementation-plan.md](implementation-plan.md)** - PythonパーサーBox実装計画
|
||||
- **[builtin-box-flow.md](builtin-box-flow.md)** - ビルトインBox実装フロー
|
||||
|
||||
## 🎯 目的
|
||||
|
||||
### PythonパーサーBoxの役割
|
||||
|
||||
1. **Python AST解析**
|
||||
- Pythonコードをパース
|
||||
- AST(抽象構文木)を生成
|
||||
- Hakorune内で操作可能な形式に変換
|
||||
|
||||
2. **型推論・スコープ解決**
|
||||
- Python動的型の静的解析
|
||||
- スコープ情報の抽出
|
||||
- 型アノテーション活用
|
||||
|
||||
3. **Hakorune MIRへの変換**
|
||||
- Python AST → Hakorune AST
|
||||
- Hakorune AST → MIR
|
||||
- 最適化情報の付与
|
||||
|
||||
## 🏗️ アーキテクチャ
|
||||
|
||||
### PythonParserBox(計画)
|
||||
|
||||
```hakorune
|
||||
box PythonParserBox {
|
||||
// パース
|
||||
parse(code: StringBox) -> ASTBox
|
||||
|
||||
// AST操作
|
||||
visit_nodes(ast: ASTBox, visitor: FunctionBox)
|
||||
get_node_type(node: ASTBox) -> StringBox
|
||||
|
||||
// 変換
|
||||
to_hakorune_ast(ast: ASTBox) -> HakoruneASTBox
|
||||
to_mir(ast: ASTBox) -> MIRBox
|
||||
}
|
||||
```
|
||||
|
||||
### ビルトインBox統合フロー
|
||||
|
||||
1. **パーサー初期化**
|
||||
- CPython APIの初期化
|
||||
- パーサーモジュールのロード
|
||||
|
||||
2. **パース実行**
|
||||
- コード文字列を受け取り
|
||||
- Python ASTを生成
|
||||
- エラーハンドリング
|
||||
|
||||
3. **AST変換**
|
||||
- Python AST → Hakorune AST
|
||||
- 型情報の付与
|
||||
- スコープ情報の追加
|
||||
|
||||
4. **MIR生成**
|
||||
- Hakorune AST → MIR
|
||||
- 最適化パスの適用
|
||||
|
||||
## 🔧 技術的課題
|
||||
|
||||
### 1. Python AST API統合
|
||||
- CPython C API使用
|
||||
- `ast` モジュールとの連携
|
||||
- メモリ管理(参照カウント)
|
||||
|
||||
### 2. 型推論
|
||||
- Python動的型の静的解析
|
||||
- 型アノテーション活用
|
||||
- 型推論アルゴリズム
|
||||
|
||||
### 3. スコープ解決
|
||||
- Pythonのスコープルール(LEGB)
|
||||
- Hakoruneスコープへのマッピング
|
||||
- クロージャ・ネストスコープ対応
|
||||
|
||||
### 4. 構文マッピング
|
||||
- Python構文 → Hakorune構文
|
||||
- イディオム変換
|
||||
- サポートする機能範囲の決定
|
||||
|
||||
## 📊 実装ステータス
|
||||
|
||||
| コンポーネント | ステータス | 備考 |
|
||||
|--------------|----------|------|
|
||||
| パーサーBox設計 | ✅ 完了 | 設計書完成 |
|
||||
| CPython API統合 | 📅 未実装 | - |
|
||||
| AST変換 | 📅 未実装 | - |
|
||||
| 型推論 | 📅 未実装 | - |
|
||||
| MIR生成 | 📅 未実装 | - |
|
||||
|
||||
## ⚠️ リスク要因
|
||||
|
||||
1. **CPython依存**
|
||||
- CPythonバージョン互換性
|
||||
- プラットフォーム固有の問題
|
||||
|
||||
2. **型推論の精度**
|
||||
- Python動的型の限界
|
||||
- 型アノテーションの不完全性
|
||||
|
||||
3. **パフォーマンス**
|
||||
- パース・変換のオーバーヘッド
|
||||
- 大規模コードベースでの性能
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- [Phase 20 メインREADME](../README.md)
|
||||
- [Planning](../planning/)
|
||||
- [Core Implementation](../core-implementation/)
|
||||
@ -0,0 +1,553 @@
|
||||
# PythonParserBox ビルトインBox実装フロー(エキスパート統合版)
|
||||
~CPythonパーサー統合とPhase 1実装の具体的な流れ~
|
||||
更新日: 2025-08-27
|
||||
|
||||
## 🎯 全体の実装フロー
|
||||
|
||||
### Step 0: Python 3.11固定(エキスパート推奨)
|
||||
```
|
||||
- Python 3.11.9を使用(AST安定性確保)
|
||||
- pyenvまたはpython3.11コマンドで固定
|
||||
- py_versionとast_formatをJSON IRに必ず含める
|
||||
```
|
||||
|
||||
### Step 1: ビルトインBoxとしての基盤作成
|
||||
```
|
||||
1. src/boxes/python_parser_box/mod.rs を作成
|
||||
2. BoxBase + BoxCore統一アーキテクチャに準拠
|
||||
3. PythonParserBoxの基本構造を定義
|
||||
4. src/boxes/mod.rs に登録
|
||||
5. テレメトリー基盤を初期から組み込む
|
||||
```
|
||||
|
||||
### Step 2: pyo3統合とCPythonパーサー接続
|
||||
```
|
||||
1. Cargo.tomlに pyo3依存関係追加
|
||||
2. pyo3::prepare_freethreaded_python()で一度だけ初期化
|
||||
3. ast.parse()へのFFIブリッジ実装
|
||||
4. JSON中間表現への変換(Python側でJSON生成)
|
||||
5. GILは最小限に、py.allow_threads()でRust処理
|
||||
```
|
||||
|
||||
### Step 3: Phase 1機能の実装(必須意味論要素)
|
||||
```
|
||||
必須要素(Codex先生強調):
|
||||
- LEGBスコーピング + locals/freevars
|
||||
- デフォルト引数の定義時評価
|
||||
- イテレータプロトコル(for文)
|
||||
- for/else + while/else
|
||||
- Python真偽値判定
|
||||
- 短絡評価(and/or)
|
||||
|
||||
実装手順:
|
||||
1. 関数単位フォールバック戦略の実装
|
||||
2. 基本的なAST変換(def, if, for, while, return)
|
||||
3. 式の変換(算術/比較/論理演算子、関数呼び出し)
|
||||
4. Nyash ASTへの意味論を保ったマッピング
|
||||
5. Differential Testingフレームワーク
|
||||
```
|
||||
|
||||
## 📝 具体的な実装コード
|
||||
|
||||
### 1. ビルトインBox定義(src/boxes/python_parser_box/mod.rs)
|
||||
```rust
|
||||
use crate::core::{BoxBase, BoxCore, NyashBox};
|
||||
use crate::ast;
|
||||
use pyo3::prelude::*;
|
||||
use std::sync::{Arc, Mutex};
|
||||
|
||||
pub struct PythonParserBox {
|
||||
base: BoxBase,
|
||||
py_helper: Arc<Mutex<PyHelper>>, // Python実行環境
|
||||
}
|
||||
|
||||
impl BoxCore for PythonParserBox {
|
||||
fn box_id(&self) -> u64 {
|
||||
self.base.box_id()
|
||||
}
|
||||
|
||||
fn parent_type_id(&self) -> Option<std::any::TypeId> {
|
||||
self.base.parent_type_id()
|
||||
}
|
||||
|
||||
fn fmt_box(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
|
||||
write!(f, "PythonParserBox#{}", self.box_id())
|
||||
}
|
||||
}
|
||||
|
||||
impl NyashBox for PythonParserBox {
|
||||
fn type_name(&self) -> &'static str {
|
||||
"PythonParserBox"
|
||||
}
|
||||
|
||||
fn clone_box(&self) -> Box<dyn NyashBox> {
|
||||
Box::new(PythonParserBox {
|
||||
base: BoxBase::new(),
|
||||
py_helper: self.py_helper.clone(),
|
||||
})
|
||||
}
|
||||
|
||||
fn as_any(&self) -> &dyn std::any::Any {
|
||||
self
|
||||
}
|
||||
|
||||
fn as_any_mut(&mut self) -> &mut dyn std::any::Any {
|
||||
self
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 2. メソッド実装(Phase 1対応)
|
||||
```rust
|
||||
// テレメトリー用構造体
|
||||
#[derive(Default)]
|
||||
pub struct CompilationTelemetry {
|
||||
compiled_functions: Vec<String>,
|
||||
fallback_functions: Vec<(String, String, usize)>, // (name, reason, lineno)
|
||||
unsupported_nodes: HashMap<String, usize>, // node_type -> count
|
||||
}
|
||||
|
||||
impl PythonParserBox {
|
||||
// コンストラクタ
|
||||
pub fn new() -> Result<Self, String> {
|
||||
// 一度だけ初期化
|
||||
static INIT: std::sync::Once = std::sync::Once::new();
|
||||
INIT.call_once(|| {
|
||||
pyo3::prepare_freethreaded_python();
|
||||
});
|
||||
|
||||
// Python環境の初期化
|
||||
Python::with_gil(|py| {
|
||||
// Python 3.11確認
|
||||
let version = py.version_info();
|
||||
if version.major != 3 || version.minor != 11 {
|
||||
return Err(format!("Python 3.11 required, got {}.{}",
|
||||
version.major, version.minor));
|
||||
}
|
||||
|
||||
let helper = PyHelper::new(py)?;
|
||||
Ok(PythonParserBox {
|
||||
base: BoxBase::new(),
|
||||
py_helper: Arc::new(Mutex::new(helper)),
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
// Python code → JSON AST
|
||||
pub fn parse_to_json(&self, code: &str) -> Result<String, String> {
|
||||
let helper = self.py_helper.lock().unwrap();
|
||||
Python::with_gil(|py| {
|
||||
helper.parse_to_json(py, code)
|
||||
})
|
||||
}
|
||||
|
||||
// JSON AST → Nyash AST(Phase 1機能のみ)
|
||||
pub fn json_to_nyash_ast(&self, json: &str) -> Result<ast::Program, String> {
|
||||
let py_ast: Phase1PythonAst = serde_json::from_str(json)
|
||||
.map_err(|e| format!("JSON parse error: {}", e))?;
|
||||
|
||||
let converter = Phase1Converter::new();
|
||||
converter.convert(py_ast)
|
||||
}
|
||||
|
||||
// 直接実行(関数単位フォールバック)
|
||||
pub fn run(&self, code: &str) -> Result<Box<dyn NyashBox>, String> {
|
||||
// まずJSON ASTを取得
|
||||
let json_ast = self.parse_to_json(code)?;
|
||||
let py_ast: serde_json::Value = serde_json::from_str(&json_ast)?;
|
||||
|
||||
// モジュール内の各関数をチェック
|
||||
let compiler = FunctionCompiler::new();
|
||||
let module_result = compiler.compile_module(&py_ast)?;
|
||||
|
||||
// テレメトリー出力(環境変数で制御)
|
||||
if std::env::var("NYASH_PYTHONPARSER_TELEMETRY").is_ok() {
|
||||
compiler.print_telemetry();
|
||||
}
|
||||
|
||||
// 実行(コンパイル済み関数はMIR、他はCPython)
|
||||
module_result.execute()
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 3. Python側ヘルパー実装
|
||||
```rust
|
||||
// Pythonコードを文字列として埋め込み
|
||||
const PYTHON_HELPER_CODE: &str = r#"
|
||||
import ast
|
||||
import json
|
||||
import sys
|
||||
|
||||
# Python 3.11固定チェック
|
||||
assert sys.version_info[:2] == (3, 11), f"Python 3.11 required, got {sys.version}"
|
||||
|
||||
def ast_to_dict(node):
|
||||
"""Phase 1: 基本的なAST要素のみ変換(エキスパート推奨JSON IR)"""
|
||||
|
||||
result = {
|
||||
"node_type": node.__class__.__name__,
|
||||
"py_version": "3.11",
|
||||
"ast_format": "v1"
|
||||
}
|
||||
|
||||
# 位置情報(エラー診断用)
|
||||
if hasattr(node, 'lineno'):
|
||||
result['lineno'] = node.lineno
|
||||
result['col_offset'] = node.col_offset
|
||||
if hasattr(node, 'end_lineno'):
|
||||
result['end_lineno'] = node.end_lineno
|
||||
result['end_col_offset'] = node.end_col_offset
|
||||
if isinstance(node, ast.Module):
|
||||
return {
|
||||
"type": "Module",
|
||||
"body": [ast_to_dict(stmt) for stmt in node.body]
|
||||
}
|
||||
elif isinstance(node, ast.FunctionDef):
|
||||
# 意味論上重要:デフォルト引数情報を保存
|
||||
args_info = {
|
||||
"args": [arg.arg for arg in node.args.args],
|
||||
"defaults": [ast_to_dict(default) for default in node.args.defaults],
|
||||
"kwonlyargs": [arg.arg for arg in node.args.kwonlyargs],
|
||||
"kw_defaults": [ast_to_dict(d) if d else None for d in node.args.kw_defaults]
|
||||
}
|
||||
result.update({
|
||||
"name": node.name,
|
||||
"args": args_info,
|
||||
"body": [ast_to_dict(stmt) for stmt in node.body],
|
||||
"decorator_list": [], # Phase 1では未対応
|
||||
"support_level": "full" # コンパイル可能
|
||||
})
|
||||
return result
|
||||
elif isinstance(node, ast.Return):
|
||||
return {
|
||||
"type": "Return",
|
||||
"value": ast_to_dict(node.value) if node.value else None
|
||||
}
|
||||
elif isinstance(node, ast.BinOp):
|
||||
return {
|
||||
"type": "BinOp",
|
||||
"op": node.op.__class__.__name__,
|
||||
"left": ast_to_dict(node.left),
|
||||
"right": ast_to_dict(node.right)
|
||||
}
|
||||
elif isinstance(node, ast.Call):
|
||||
return {
|
||||
"type": "Call",
|
||||
"func": ast_to_dict(node.func),
|
||||
"args": [ast_to_dict(arg) for arg in node.args]
|
||||
}
|
||||
elif isinstance(node, ast.Name):
|
||||
return {
|
||||
"type": "Name",
|
||||
"id": node.id
|
||||
}
|
||||
elif isinstance(node, ast.Constant):
|
||||
return {
|
||||
"type": "Constant",
|
||||
"value": node.value
|
||||
}
|
||||
elif isinstance(node, ast.If):
|
||||
return {
|
||||
"type": "If",
|
||||
"test": ast_to_dict(node.test),
|
||||
"body": [ast_to_dict(stmt) for stmt in node.body],
|
||||
"orelse": [ast_to_dict(stmt) for stmt in node.orelse]
|
||||
}
|
||||
elif isinstance(node, ast.For):
|
||||
# 意味論上重要:for/else構文
|
||||
result.update({
|
||||
"target": ast_to_dict(node.target),
|
||||
"iter": ast_to_dict(node.iter),
|
||||
"body": [ast_to_dict(stmt) for stmt in node.body],
|
||||
"orelse": [ast_to_dict(stmt) for stmt in node.orelse], # else節
|
||||
"support_level": "full"
|
||||
})
|
||||
return result
|
||||
|
||||
elif isinstance(node, ast.While):
|
||||
# 意味論上重要:while/else構文
|
||||
result.update({
|
||||
"test": ast_to_dict(node.test),
|
||||
"body": [ast_to_dict(stmt) for stmt in node.body],
|
||||
"orelse": [ast_to_dict(stmt) for stmt in node.orelse], # else節
|
||||
"support_level": "full"
|
||||
})
|
||||
return result
|
||||
|
||||
elif isinstance(node, ast.BoolOp):
|
||||
# 意味論上重要:短絡評価
|
||||
result.update({
|
||||
"op": node.op.__class__.__name__, # And, Or
|
||||
"values": [ast_to_dict(v) for v in node.values],
|
||||
"support_level": "full"
|
||||
})
|
||||
return result
|
||||
else:
|
||||
# Phase 1では未対応(テレメトリー用)
|
||||
return {
|
||||
"node_type": "Unsupported",
|
||||
"original_type": type(node).__name__,
|
||||
"support_level": "fallback",
|
||||
"lineno": getattr(node, 'lineno', -1)
|
||||
}
|
||||
|
||||
def parse_to_json(code):
|
||||
try:
|
||||
tree = ast.parse(code)
|
||||
return json.dumps(ast_to_dict(tree))
|
||||
except Exception as e:
|
||||
return json.dumps({"type": "Error", "message": str(e)})
|
||||
"#;
|
||||
|
||||
struct PyHelper {
|
||||
// Python側のヘルパー関数への参照を保持
|
||||
parse_func: PyObject,
|
||||
}
|
||||
|
||||
impl PyHelper {
|
||||
fn new(py: Python) -> PyResult<Self> {
|
||||
// ヘルパーコードをPythonで実行
|
||||
let helpers = PyModule::from_code(py, PYTHON_HELPER_CODE, "helper.py", "helper")?;
|
||||
let parse_func = helpers.getattr("parse_to_json")?.to_object(py);
|
||||
|
||||
Ok(PyHelper { parse_func })
|
||||
}
|
||||
|
||||
fn parse_to_json(&self, py: Python, code: &str) -> Result<String, String> {
|
||||
match self.parse_func.call1(py, (code,)) {
|
||||
Ok(result) => result.extract::<String>(py)
|
||||
.map_err(|e| format!("Extract error: {}", e)),
|
||||
Err(e) => Err(format!("Parse error: {}", e))
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 4. Phase 1 AST変換器
|
||||
```rust
|
||||
struct Phase1Converter;
|
||||
|
||||
impl Phase1Converter {
|
||||
fn new() -> Self {
|
||||
Phase1Converter
|
||||
}
|
||||
|
||||
fn convert(&self, py_ast: Phase1PythonAst) -> Result<ast::Program, String> {
|
||||
match py_ast {
|
||||
Phase1PythonAst::Module { body } => {
|
||||
let mut items = vec![];
|
||||
for stmt in body {
|
||||
match self.convert_statement(stmt)? {
|
||||
Some(item) => items.push(item),
|
||||
None => {} // 未対応要素はスキップ
|
||||
}
|
||||
}
|
||||
Ok(ast::Program { items })
|
||||
}
|
||||
_ => Err("Expected Module at top level".into())
|
||||
}
|
||||
}
|
||||
|
||||
fn convert_statement(&self, stmt: Phase1PythonAst) -> Result<Option<ast::ProgramItem>, String> {
|
||||
match stmt {
|
||||
Phase1PythonAst::FunctionDef { name, args, body } => {
|
||||
// Python def → Nyash function
|
||||
let params = args.into_iter()
|
||||
.map(|arg| ast::Parameter { name: arg, ty: None })
|
||||
.collect();
|
||||
|
||||
let nyash_body = self.convert_body(body)?;
|
||||
|
||||
Ok(Some(ast::ProgramItem::Function(ast::FunctionDef {
|
||||
name,
|
||||
params,
|
||||
body: nyash_body,
|
||||
return_type: None,
|
||||
})))
|
||||
}
|
||||
Phase1PythonAst::Return { value } => {
|
||||
let expr = value
|
||||
.map(|v| self.convert_expression(v))
|
||||
.transpose()?;
|
||||
|
||||
Ok(Some(ast::ProgramItem::Statement(ast::Statement::Return(expr))))
|
||||
}
|
||||
// 他の文も同様に変換
|
||||
_ => Ok(None) // Phase 1では未対応
|
||||
}
|
||||
}
|
||||
|
||||
fn convert_expression(&self, expr: Phase1PythonAst) -> Result<ast::Expression, String> {
|
||||
match expr {
|
||||
Phase1PythonAst::BinOp { op, left, right } => {
|
||||
let left = Box::new(self.convert_expression(*left)?);
|
||||
let right = Box::new(self.convert_expression(*right)?);
|
||||
|
||||
let op = match op.as_str() {
|
||||
"Add" => ast::BinaryOp::Add,
|
||||
"Sub" => ast::BinaryOp::Sub,
|
||||
"Mul" => ast::BinaryOp::Mul,
|
||||
"Div" => ast::BinaryOp::Div,
|
||||
_ => return Err(format!("Unsupported operator: {}", op))
|
||||
};
|
||||
|
||||
Ok(ast::Expression::BinaryOp { op, left, right })
|
||||
}
|
||||
Phase1PythonAst::Constant { value } => {
|
||||
// Python定数 → Nyashリテラル
|
||||
match value {
|
||||
serde_json::Value::Number(n) => {
|
||||
if let Some(i) = n.as_i64() {
|
||||
Ok(ast::Expression::Integer(i))
|
||||
} else if let Some(f) = n.as_f64() {
|
||||
Ok(ast::Expression::Float(f))
|
||||
} else {
|
||||
Err("Unsupported number type".into())
|
||||
}
|
||||
}
|
||||
serde_json::Value::String(s) => {
|
||||
Ok(ast::Expression::String(s))
|
||||
}
|
||||
serde_json::Value::Bool(b) => {
|
||||
Ok(ast::Expression::Bool(b))
|
||||
}
|
||||
_ => Err("Unsupported constant type".into())
|
||||
}
|
||||
}
|
||||
// 他の式も同様
|
||||
_ => Err("Unsupported expression in Phase 1".into())
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 5. インタープリター統合(src/interpreter/builtins.rs)
|
||||
```rust
|
||||
// ビルトインBox登録に追加
|
||||
pub fn register_builtin_boxes(env: &mut Environment) {
|
||||
// 既存のBox登録...
|
||||
|
||||
// PythonParserBox追加
|
||||
env.register_builtin_box("PythonParserBox", || {
|
||||
match PythonParserBox::new() {
|
||||
Ok(parser) => Arc::new(parser) as Arc<dyn NyashBox>,
|
||||
Err(e) => panic!("Failed to initialize PythonParserBox: {}", e)
|
||||
}
|
||||
});
|
||||
}
|
||||
```
|
||||
|
||||
### 6. 使用例とテストケース
|
||||
```nyash
|
||||
// test_python_parser_phase1.nyash
|
||||
local py = new PythonParserBox()
|
||||
|
||||
// Phase 1: 基本的な関数定義と演算
|
||||
local code = """
|
||||
def add(x, y):
|
||||
return x + y
|
||||
|
||||
def multiply(x, y):
|
||||
return x * y
|
||||
|
||||
def calculate(a, b):
|
||||
sum_val = add(a, b)
|
||||
prod_val = multiply(a, b)
|
||||
return sum_val + prod_val
|
||||
"""
|
||||
|
||||
// パースしてJSON ASTを確認
|
||||
local json_ast = py.parse_to_json(code)
|
||||
print("JSON AST: " + json_ast)
|
||||
|
||||
// Nyash ASTに変換
|
||||
local nyash_ast = py.json_to_nyash_ast(json_ast)
|
||||
print("Conversion successful!")
|
||||
|
||||
// 実行(最初はCPython経由)
|
||||
local result = py.run(code + "\nprint(calculate(10, 5))")
|
||||
```
|
||||
|
||||
## 📊 段階的な実装計画
|
||||
|
||||
### Week 1: 基盤構築
|
||||
- [ ] PythonParserBoxの基本構造
|
||||
- [ ] pyo3統合とPython環境初期化
|
||||
- [ ] parse_to_json基本実装
|
||||
- [ ] エラーハンドリング
|
||||
|
||||
### Week 2: Phase 1変換器
|
||||
- [ ] Phase1PythonAstの定義
|
||||
- [ ] Phase1Converterの実装
|
||||
- [ ] 基本的な文と式の変換
|
||||
- [ ] テストケース作成
|
||||
|
||||
### Week 3: 統合とテスト
|
||||
- [ ] インタープリター統合
|
||||
- [ ] CPython exec経由の実行
|
||||
- [ ] ベンチマーク準備
|
||||
- [ ] ドキュメント整備
|
||||
|
||||
## 🚀 期待される成果
|
||||
|
||||
### Phase 1完了時点で実現できること:
|
||||
1. **基本的なPythonコードの実行**
|
||||
- 関数定義、算術演算、条件分岐、ループ
|
||||
|
||||
2. **Nyash ASTへの変換**
|
||||
- 将来のMIR/JIT最適化への道筋
|
||||
|
||||
3. **統合開発環境**
|
||||
- PythonコードとNyashコードの混在実行
|
||||
|
||||
4. **性能測定基盤**
|
||||
- CPython実行 vs Nyash実行の比較
|
||||
|
||||
## 📡 テレメトリー出力例
|
||||
|
||||
```bash
|
||||
# 環境変数で制御
|
||||
export NYASH_PYTHONPARSER_TELEMETRY=1 # 基本統計
|
||||
export NYASH_PYTHONPARSER_TELEMETRY=2 # 詳細ログ
|
||||
export NYASH_PYTHONPARSER_STRICT=1 # フォールバック時にパニック
|
||||
|
||||
# 実行例
|
||||
./target/release/nyash test_python_parser.nyash
|
||||
|
||||
# 出力
|
||||
[PythonParser] Module: test.py (Python 3.11)
|
||||
Functions: 10 total
|
||||
Compiled: 7 (70%) → Nyash MIR/JIT
|
||||
Fallback: 3 (30%) → CPython exec
|
||||
- async_function: unsupported node 'AsyncFunctionDef' at line 23
|
||||
- generator_func: unsupported node 'Yield' at line 45
|
||||
- decorator_func: unsupported node 'decorator_list' at line 67
|
||||
|
||||
Unsupported Nodes Summary:
|
||||
AsyncFunctionDef: 1
|
||||
Yield: 2
|
||||
ClassDef: 1
|
||||
```
|
||||
|
||||
## 📊 Differential Testingフレームワーク
|
||||
|
||||
```rust
|
||||
// CPythonとNyashの出力比較
|
||||
pub fn differential_test(code: &str) -> TestResult {
|
||||
// CPythonで実行(オラクル)
|
||||
let python_result = Python::with_gil(|py| {
|
||||
capture_python_execution(py, code)
|
||||
})?;
|
||||
|
||||
// Nyashで実行
|
||||
let nyash_result = execute_with_pythonparser(code)?;
|
||||
|
||||
// 結果比較
|
||||
compare_results(python_result, nyash_result)
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
作成日: 2025-08-27
|
||||
Phase 1実装の具体的な手順とエキスパートフィードバック統合
|
||||
@ -0,0 +1,361 @@
|
||||
# PythonParserBox実装計画(統合版)
|
||||
更新日: 2025-08-27
|
||||
|
||||
## 🎯 エキスパートからの統合フィードバック
|
||||
|
||||
### 最重要ポイント(両エキスパートが一致)
|
||||
1. **関数単位のフォールバック戦略**
|
||||
- ファイル全体でなく関数レベルでコンパイル/フォールバックを切り替え
|
||||
- 未対応機能を含む関数はCPython exec、対応済み関数はNyash MIR/JIT
|
||||
|
||||
2. **Python 3.11固定**
|
||||
- AST安定性の確保(3.8 Constant統一、3.10 match/case、3.12位置情報)
|
||||
- `py_version`と`ast_format`をJSON IRに埋め込む
|
||||
|
||||
3. **意味論の正確な実装が最優先**
|
||||
- 最適化より先にPython互換性を確保
|
||||
- 特に: イテレータプロトコル、真偽値判定、スコーピング規則(LEGB)
|
||||
|
||||
4. **GIL管理の最小化**
|
||||
- Python側でJSON生成(`ast.NodeVisitor` + `json.dumps`)
|
||||
- Rust側で解析(GIL外で実行)
|
||||
- `py.allow_threads(|| { ... })`で重い処理をGIL外実行
|
||||
|
||||
5. **テレメトリー重視**
|
||||
- 未対応ノードの記録(`support_level`フィールド)
|
||||
- フォールバック率の計測
|
||||
- ソース位置情報の保持(`lineno/col_offset/end_*`)
|
||||
|
||||
### Differential Testing戦略
|
||||
- **世界中のPythonコードがNyashのテストケース**
|
||||
- CPythonを「オラクル」として使用
|
||||
- 出力、戻り値、例外を比較
|
||||
- Grammar-based fuzzing(Hypothesis活用)
|
||||
|
||||
## 技術的実装方針
|
||||
|
||||
### 1. CPythonパーサー統合(pyo3使用)
|
||||
```rust
|
||||
// Cargo.toml
|
||||
[dependencies]
|
||||
pyo3 = { version = "0.22", features = ["auto-initialize"] }
|
||||
pyo3-numpy = "0.22" // NumPy連携用
|
||||
|
||||
// 初期化(一度だけ)
|
||||
pyo3::prepare_freethreaded_python();
|
||||
|
||||
// Python側ヘルパー(embedded)
|
||||
const PYTHON_HELPER: &str = r#"
|
||||
import ast
|
||||
import json
|
||||
import sys
|
||||
|
||||
def parse_to_json(code, filename="<string>", mode="exec"):
|
||||
tree = ast.parse(code, filename, mode)
|
||||
return json.dumps(ast_to_dict(tree))
|
||||
|
||||
def ast_to_dict(node):
|
||||
result = {}
|
||||
|
||||
# 必須フィールド
|
||||
result['node_type'] = node.__class__.__name__
|
||||
result['py_version'] = f"{sys.version_info.major}.{sys.version_info.minor}"
|
||||
|
||||
# 位置情報(エラー診断用)
|
||||
if hasattr(node, 'lineno'):
|
||||
result['lineno'] = node.lineno
|
||||
result['col_offset'] = node.col_offset
|
||||
if hasattr(node, 'end_lineno'): # Python 3.8+
|
||||
result['end_lineno'] = node.end_lineno
|
||||
result['end_col_offset'] = node.end_col_offset
|
||||
|
||||
# サポートレベル(Nyash側で設定)
|
||||
result['support_level'] = 'unknown'
|
||||
|
||||
# ASTフィールド
|
||||
if isinstance(node, ast.AST):
|
||||
for field in node._fields:
|
||||
value = getattr(node, field)
|
||||
result[field] = ast_to_dict(value)
|
||||
elif isinstance(node, list):
|
||||
return [ast_to_dict(x) for x in node]
|
||||
else:
|
||||
return node
|
||||
|
||||
return result
|
||||
"#;
|
||||
```
|
||||
|
||||
### 2. 最小実装セット(Phase 1: Must-Have)
|
||||
```
|
||||
Phase 1 意味論の必須要素(Codex先生強調):
|
||||
- LEGB + locals/freevars(スコーピング)
|
||||
- デフォルト引数の評価タイミング(定義時)
|
||||
- イテレータベースのfor文
|
||||
- for/else + while/else(Python独特)
|
||||
- Python真偽値判定(__bool__ → __len__)
|
||||
- 短絡評価(and/or)
|
||||
|
||||
Phase 1 AST構造:
|
||||
├─ Module (py_version, ast_format)
|
||||
├─ FunctionDef (name, args, body, decorator_list=[])
|
||||
│ └─ arguments (args, defaults, kwonlyargs=[], kw_defaults=[])
|
||||
├─ Return (value)
|
||||
├─ Assign (targets, value)
|
||||
├─ AugAssign (target, op, value) # +=, -=等
|
||||
└─ Expr (value)
|
||||
|
||||
Phase 1 式:
|
||||
├─ BinOp (left, op, right)
|
||||
│ └─ ops: Add, Sub, Mult, Div, FloorDiv, Mod, Pow
|
||||
├─ Compare (left, ops, comparators)
|
||||
│ └─ ops: Eq, NotEq, Lt, LtE, Gt, GtE, Is, IsNot
|
||||
├─ BoolOp (op, values) # and/or
|
||||
├─ UnaryOp (op, operand) # not, -, +
|
||||
├─ Call (func, args, keywords=[])
|
||||
├─ Name (id, ctx=Load/Store/Del)
|
||||
├─ Constant (value) # Python 3.8+統一
|
||||
└─ IfExp (test, body, orelse) # 三項演算子
|
||||
|
||||
Phase 1 制御フロー:
|
||||
├─ If (test, body, orelse)
|
||||
├─ While (test, body, orelse) # else節対応必須
|
||||
├─ For (target, iter, body, orelse) # else節対応必須
|
||||
├─ Break
|
||||
└─ Continue
|
||||
```
|
||||
|
||||
### 3. 関数単位フォールバック戦略
|
||||
```rust
|
||||
// 関数単位のコンパイル判定
|
||||
pub struct FunctionCompiler {
|
||||
supported_nodes: HashSet<&'static str>,
|
||||
telemetry: CompilationTelemetry,
|
||||
}
|
||||
|
||||
impl FunctionCompiler {
|
||||
pub fn can_compile(&self, func_def: &PythonAst) -> CompileResult {
|
||||
let mut visitor = SupportChecker::new(&self.supported_nodes);
|
||||
visitor.visit(func_def);
|
||||
|
||||
if visitor.has_unsupported() {
|
||||
// CPython execへフォールバック
|
||||
CompileResult::Fallback {
|
||||
reason: visitor.unsupported_nodes(),
|
||||
location: func_def.location(),
|
||||
}
|
||||
} else {
|
||||
// Nyash MIR/JITへコンパイル
|
||||
CompileResult::Compile
|
||||
}
|
||||
}
|
||||
|
||||
pub fn compile_module(&mut self, module: &PythonAst) -> ModuleUnit {
|
||||
let mut units = vec![];
|
||||
|
||||
// モジュールトップレベルはPythonで実行(globals設定)
|
||||
units.push(ExecutionUnit::PythonExec(module.top_level));
|
||||
|
||||
// 各関数を判定
|
||||
for func in module.functions() {
|
||||
match self.can_compile(func) {
|
||||
CompileResult::Compile => {
|
||||
let mir = self.compile_to_mir(func);
|
||||
units.push(ExecutionUnit::NyashFunction(mir));
|
||||
self.telemetry.record_compiled(func.name);
|
||||
}
|
||||
CompileResult::Fallback { reason, location } => {
|
||||
units.push(ExecutionUnit::PythonThunk(func));
|
||||
self.telemetry.record_fallback(func.name, reason, location);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ModuleUnit { units }
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 4. データ共有戦略
|
||||
```rust
|
||||
// NdArrayBox定義
|
||||
pub struct NdArrayBox {
|
||||
base: BoxBase,
|
||||
py_array: Py<PyArray<f64, Dim<[usize; 2]>>>, // Python側の参照保持
|
||||
// 操作時のみGIL取得してArrayViewを取る
|
||||
}
|
||||
|
||||
impl NdArrayBox {
|
||||
pub fn to_view(&self) -> PyResult<ArrayView2<f64>> {
|
||||
Python::with_gil(|py| {
|
||||
let array = self.py_array.as_ref(py);
|
||||
Ok(array.readonly())
|
||||
})
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 4. 実装ロードマップ
|
||||
|
||||
#### Phase 1: パーサー統合(1-2週間)
|
||||
- [ ] pyo3セットアップとPythonParserBox骨格
|
||||
- [ ] Python側parse_to_jsonヘルパー実装
|
||||
- [ ] JSON→Nyash AST最小変換
|
||||
- [ ] run()メソッド(CPython exec委譲)
|
||||
- [ ] 例外変換(PyErr → NyashError)
|
||||
|
||||
#### Phase 2: MIR変換(2-4週間)
|
||||
- [ ] AST→MIR変換器(最小セット)
|
||||
- [ ] 数値演算プリミティブ実装
|
||||
- [ ] スコープ解決(関数ローカル/グローバル)
|
||||
- [ ] 基本的な制御フロー(If/While)
|
||||
|
||||
#### Phase 3: NumPy統合(並行可能)
|
||||
- [ ] pyo3-numpy統合
|
||||
- [ ] NdArrayBox実装
|
||||
- [ ] ゼロコピーベンチマーク
|
||||
- [ ] バッファプロトコル対応
|
||||
|
||||
#### Phase 4: 最適化と拡張
|
||||
- [ ] 型特化とガード最適化
|
||||
- [ ] 例外処理(try/except)
|
||||
- [ ] クラス/メソッド対応
|
||||
- [ ] import統合
|
||||
|
||||
## 性能目標(現実的な見積もり)
|
||||
|
||||
| コードタイプ | 期待される高速化 | 備考 |
|
||||
|------------|----------------|------|
|
||||
| 純Pythonループ | 2-10倍 | 型安定なホットパス |
|
||||
| 関数呼び出し多 | 1.5-3倍 | インライン化効果 |
|
||||
| NumPy処理中心 | 1.0-1.2倍 | 既に最適化済み |
|
||||
| 動的特性多用 | 1.2-3倍 | ガード頻発で限定的 |
|
||||
|
||||
## 実装上の注意点(エキスパート推奨)
|
||||
|
||||
### 意味論の重要な違い(Phase 1で対応必須)
|
||||
|
||||
1. **制御フロー**
|
||||
- `for`文: イテレータプロトコル必須(`__iter__`/`__next__`)
|
||||
- `for/else`, `while/else`: breakしなかった場合のelse実行
|
||||
- 短絡評価: `and`は左がFalseなら右を評価しない
|
||||
|
||||
2. **スコープ規則(LEGB)**
|
||||
```python
|
||||
# Local → Enclosing → Global → Builtins
|
||||
global_var = 1
|
||||
|
||||
def outer():
|
||||
enclosing_var = 2
|
||||
|
||||
def inner():
|
||||
local_var = 3
|
||||
nonlocal enclosing_var # 明示的な宣言
|
||||
global global_var # 明示的な宣言
|
||||
```
|
||||
|
||||
3. **数値演算の違い**
|
||||
- `/`: Python 3では常にfloat(true division)
|
||||
- `//`: floor division(整数除算)
|
||||
- 大整数: デフォルトで無限精度
|
||||
- `is` vs `==`: オブジェクト同一性 vs 値の等価性
|
||||
|
||||
4. **関数定義の罠**
|
||||
```python
|
||||
def f(x, y=[]): # デフォルト引数は定義時に1度だけ評価!
|
||||
y.append(x) # 全呼び出しで同じリストを共有
|
||||
return y
|
||||
```
|
||||
|
||||
### GIL管理のベストプラクティス
|
||||
|
||||
```rust
|
||||
// ❌ 悪い例: GILを長時間保持
|
||||
let result = Python::with_gil(|py| {
|
||||
let ast = parse_python(py, code)?;
|
||||
let json = convert_to_json(py, ast)?; // ここまでGIL必要
|
||||
let nyash_ast = parse_json(&json)?; // GIL不要なのに保持
|
||||
compile_to_mir(nyash_ast)? // GIL不要なのに保持
|
||||
});
|
||||
|
||||
// ✅ 良い例: GILを最小限に
|
||||
let json = Python::with_gil(|py| {
|
||||
let ast = parse_python(py, code)?;
|
||||
convert_to_json(py, ast) // JSON生成まで
|
||||
})?;
|
||||
|
||||
// GIL外で重い処理
|
||||
let nyash_ast = parse_json(&json)?;
|
||||
let mir = compile_to_mir(nyash_ast)?;
|
||||
|
||||
// 必要時のみ再取得
|
||||
Python::with_gil(|py| {
|
||||
py.allow_threads(|| {
|
||||
// 時間のかかるRust処理
|
||||
optimize_mir(mir)
|
||||
})
|
||||
})
|
||||
```
|
||||
|
||||
### テレメトリーとデバッグ
|
||||
|
||||
```rust
|
||||
// 環境変数で制御
|
||||
NYASH_PYTHONPARSER_TELEMETRY=1 # 基本統計
|
||||
NYASH_PYTHONPARSER_TELEMETRY=2 # 詳細ログ
|
||||
NYASH_PYTHONPARSER_STRICT=1 # フォールバック時にパニック(CI用)
|
||||
|
||||
// 出力例
|
||||
[PythonParser] Module: example.py
|
||||
Functions: 10 total
|
||||
Compiled: 7 (70%)
|
||||
Fallback: 3 (30%)
|
||||
- async_function: unsupported node 'AsyncFunctionDef' at line 23
|
||||
- generator_func: unsupported node 'Yield' at line 45
|
||||
- class_method: unsupported node 'ClassDef' at line 67
|
||||
```
|
||||
|
||||
## 次のステップ
|
||||
|
||||
### 即座に開始すべきこと
|
||||
|
||||
1. **Python 3.11環境固定**
|
||||
```bash
|
||||
pyenv install 3.11.9
|
||||
pyenv local 3.11.9
|
||||
```
|
||||
|
||||
2. **最小動作確認**
|
||||
```python
|
||||
# test_minimal.py
|
||||
def add(x, y):
|
||||
return x + y
|
||||
|
||||
result = add(10, 5)
|
||||
print(f"Result: {result}") # → Nyashで15が出力されれば成功!
|
||||
```
|
||||
|
||||
3. **テレメトリー基盤構築**
|
||||
- 未対応ノードの記録システム
|
||||
- フォールバック率の可視化
|
||||
- ソース位置情報の保持
|
||||
|
||||
4. **Differential Testingの準備**
|
||||
- CPythonとの出力比較フレームワーク
|
||||
- 標準出力、戻り値、例外のキャプチャ
|
||||
- テストコーパスの選定
|
||||
|
||||
### 成功の測定基準
|
||||
|
||||
| フェーズ | 目標 | 測定指標 |
|
||||
|---------|------|----------|
|
||||
| Phase 1 | 基本動作 | 簡単な数値計算の70%がコンパイル可能 |
|
||||
| Phase 2 | 実用性 | scikit-learnの基本アルゴリズムが動作 |
|
||||
| Phase 3 | 性能 | 純Pythonループで5倍以上の高速化 |
|
||||
| Phase 4 | 成熟度 | PyPIトップ100の30%が基本動作 |
|
||||
|
||||
## まとめ
|
||||
|
||||
このPythonParserBox実装は、単なる機能追加ではなく、Nyash言語の成熟度を飛躍的に高める戦略的プロジェクト。
|
||||
エキスパートの指摘を踏まえ、関数単位のフォールバック、Python 3.11固定、意味論の正確な実装、
|
||||
GIL最小化、テレメトリー重視で着実に実装を進める。
|
||||
@ -0,0 +1,65 @@
|
||||
# Planning - Python-Hakorune統合計画
|
||||
|
||||
## 📋 概要
|
||||
|
||||
Python-Hakorune統合の計画・設計ドキュメント集です。
|
||||
|
||||
## 📁 ファイル一覧
|
||||
|
||||
### 🌟 最新計画(2025-10-02追加)
|
||||
- **[milestones.md](milestones.md)** ⭐必読 - M0〜M6段階的実装計画(ChatGPT Pro UltraThink)
|
||||
|
||||
### 主要計画書
|
||||
- **[integrated-plan.md](integrated-plan.md)** - ChatGPT5による統合計画(旧Phase 10.5全体計画)
|
||||
- **[python-parser-plan-summary.md](python-parser-plan-summary.md)** - Pythonパーサー統合計画サマリー
|
||||
|
||||
### 設計ドキュメント
|
||||
- **[python-parser-box-design.md](python-parser-box-design.md)** - PythonパーサーBox設計
|
||||
- **[expert-feedback.md](expert-feedback.md)** - GeminiとCodexによるAI専門家フィードバック
|
||||
|
||||
## 🎯 計画の核心
|
||||
|
||||
### Phase 10.5の目的(旧計画)
|
||||
|
||||
1. **ネイティブ基盤固め**
|
||||
- VM/JIT分離(VM=実行、JIT=コンパイル)
|
||||
- AOT/EXEパイプライン確立
|
||||
- クロスプラットフォーム対応
|
||||
|
||||
2. **Python統合**
|
||||
- PyRuntimeBox: Python実行環境
|
||||
- PyObjectBox: Pythonオブジェクト管理
|
||||
- Hakorune ⇄ Python 双方向呼び出し
|
||||
|
||||
### 設計方針
|
||||
|
||||
#### Embedding vs Extending
|
||||
- **Embedding**: HakoruneプロセスにCPythonを埋め込み
|
||||
- **Extending**: Python拡張モジュールとして提供
|
||||
|
||||
#### ABI設計
|
||||
- ハンドル: TLV tag=8(type_id+instance_id)
|
||||
- Pythonオブジェクト: `PyObjectBox` として格納
|
||||
- 変換: Bool/I64/String/Bytes/Handle の相互変換
|
||||
- GIL: birth/invoke/decRef中はGIL確保
|
||||
|
||||
## 📊 実装フェーズ(旧10.5計画)
|
||||
|
||||
| フェーズ | 期間 | 内容 |
|
||||
|---------|------|------|
|
||||
| 10.5a | 1-2日 | Python設計・ABI整合 |
|
||||
| 10.5b | 2-4日 | ネイティブビルド基盤 |
|
||||
| 10.5c | 3-5日 | PyRuntimeBox/PyObjectBox実装 |
|
||||
| 10.5d | 3-5日 | JIT/AOT統合 |
|
||||
| 10.5e | 1週間 | サンプル/テスト/ドキュメント |
|
||||
|
||||
## ⚠️ 現在のステータス
|
||||
|
||||
**保留中** - Phase 15(Hakoruneセルフホスティング)完了後に再開予定
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- [Phase 20 メインREADME](../README.md)
|
||||
- [Parser Integration](../parser-integration/)
|
||||
- [Core Implementation](../core-implementation/)
|
||||
- [Design Documents](../design/)
|
||||
@ -0,0 +1,197 @@
|
||||
# PythonParserBox実装計画 - エキスパートフィードバック
|
||||
日付: 2025-08-27
|
||||
|
||||
## Gemini先生のフィードバック
|
||||
|
||||
### 総評
|
||||
これは非常に野心的で、言語の成熟度を飛躍的に高める可能性を秘めた素晴らしい計画です。Nyashの「Everything is a Box」哲学とPythonエコシステムを融合させるという着眼点に大変興奮しました。
|
||||
|
||||
### 1. 実装計画は技術的に健全か?落とし穴は?
|
||||
|
||||
**技術的健全性:**
|
||||
はい、計画は全体として技術的に非常に健全です。
|
||||
|
||||
* **CPythonパーサーの利用:** `pyo3`経由で`ast.parse()`を利用するのは、Python構文との互換性を100%保証するための最も確実で賢明なアプローチです。
|
||||
* **JSON中間表現(IR):** Python AST (Pythonメモリ空間) と Nyash AST (Rustメモリ空間) の間にJSONを挟むのは、言語間の境界を明確に分離する良い設計です。
|
||||
* **段階的実装とフォールバック:** 未実装機能を`exec()`にフォールバックする戦略は、実用性を保ちながら段階的に実装を進めるための極めて現実的なアプローチです。
|
||||
|
||||
**潜在的な落とし穴:**
|
||||
* **パフォーマンス:** `Python AST → JSON → Nyash AST → Nyash実行`というパイプラインは、特に初期段階では非常に低速になります。
|
||||
* **ASTの複雑性の爆発:** PythonのASTは非常に巨大で、言語バージョンの更新も速いです。
|
||||
* **標準ライブラリの壁:** Pythonの真の力は広範な標準/サードパーティライブラリにあります。`import`文をどう扱うかは最重要課題です。
|
||||
|
||||
### 2. Python AST → Nyash AST変換で注意すべき意味論の違いは?
|
||||
|
||||
* **型システム:** Pythonは動的型付け、Nyashは静的型付けまたはより厳格な型システムを持つと推測
|
||||
* **オブジェクトモデルと可変性:** Pythonのオブジェクトは基本的に可変(mutable)
|
||||
* **スコープとクロージャ:** Pythonの`global`や`nonlocal`の挙動は独特
|
||||
* **特殊メソッド (`__dunder__`):** Pythonの挙動は特殊メソッドで定義される
|
||||
* **組み込み関数:** `len()`, `print()`, `range()`などをどう扱うか
|
||||
|
||||
### 3. Nyashパーサーのバグ検証戦略として効果的か?
|
||||
|
||||
**非常に効果的です。** これは「Differential Testing(差分テスト)」と呼ばれる強力な手法です。
|
||||
* **巨大なテストスイート:** 事実上、世の中にある無数のPythonコードがNyashのテストケースになります。
|
||||
* **微妙なバグの発見:** 手書きの単体テストでは見逃しがちなセマンティクスのバグを発見するのに絶大な効果を発揮します。
|
||||
|
||||
### 4. pyo3統合でのGIL管理のベストプラクティスは?
|
||||
|
||||
* **基本原則:** Pythonオブジェクトに触れるコードは、必ずGILを獲得した状態で実行
|
||||
* **GILの必要期間を最小化する**
|
||||
* **`py.allow_threads`の活用:** 時間がかかり、かつPythonオブジェクトに触れない処理で使用
|
||||
|
||||
### 5. 段階的実装(Phase 1-4)の優先順位は適切か?
|
||||
|
||||
はい、提案されている優先順位は非常に適切です。
|
||||
1. Phase 1: 基本構文 + 変数束縛 + 基本的な式 + プリミティブ型
|
||||
2. Phase 2: list, dict, tuple
|
||||
3. Phase 3: 関数とスコープ
|
||||
4. Phase 4: モジュールとクラス
|
||||
|
||||
**最優先で並行すべきこと:** `exec()`へのフォールバック機構
|
||||
|
||||
### 6. 言語成熟度向上への貢献度をどう評価する?
|
||||
|
||||
**定量的指標:**
|
||||
* ライブラリ互換性カバレッジ
|
||||
* パフォーマンステスト
|
||||
* 発見バグ数
|
||||
|
||||
**定性的指標:**
|
||||
* 表現力の向上
|
||||
* 開発者体験
|
||||
* エコシステムのマイルストーン
|
||||
|
||||
### 結論
|
||||
|
||||
この`PythonParserBox`計画は、単なる機能追加ではなく、**Nyash言語のテスト、デバッグ、そしてエコシステム獲得を同時に加速させる、極めて戦略的な一手**です。
|
||||
|
||||
---
|
||||
|
||||
## Codex先生のフィードバック
|
||||
|
||||
### Overall Verdict
|
||||
- Sound approach: Using CPython's parser via pyo3, lowering via a JSON IR, and gradually replacing exec() with Nyash MIR/JIT is feasible and strategically strong.
|
||||
- Biggest risks: Semantic mismatches at statement/expression boundaries, version skew of Python AST, and boundary-costs between CPython and Nyash during phased rollout.
|
||||
|
||||
### Architectural Pitfalls
|
||||
- **Python version skew:** `ast` schema changes across minors. Pin and encode `py_version` + `ast_format` in the JSON.
|
||||
- **AST stability vs syntax fidelity:** `ast` loses comments and some token distinctions
|
||||
- **Boundary granularity:** Whole-file fallback wastes partial coverage; per-node fallback is unsafe. **The practical unit is per-function.**
|
||||
- **Import system and environment:** Python imports pull arbitrary code
|
||||
- **Error mapping:** Propagate Python exceptions with full traceback
|
||||
- **Performance overhead:** Python AST→JSON→Nyash→MIR is heavy
|
||||
- **Object model mismatch:** Identity (`is`), mutability, truthiness, numeric tower
|
||||
- **Concurrency:** GIL limits parallel parse/exec
|
||||
|
||||
### AST→Nyash Semantics: High-Risk Differences
|
||||
- **Names and scope:**
|
||||
- LEGB resolution; `global`/`nonlocal` behavior; closures and cell variables
|
||||
- Comprehension scopes (separate scope in Python 3)
|
||||
- **Control flow:**
|
||||
- `for` iterates via iterator protocol; `for/else`, `while/else` semantics
|
||||
- Short-circuit truthiness uses Python rules; `__bool__` then `__len__`
|
||||
- **Functions:**
|
||||
- Defaults evaluated at definition time; `*args/**kwargs`
|
||||
- Decorators transform functions at definition time
|
||||
- **Operators and numbers:**
|
||||
- `/` true division; `//` floor division; big integers by default
|
||||
- Operator dispatch via dunder methods; `is` vs `==`
|
||||
|
||||
For Phase 1, the must-haves are: LEGB + locals/freevars, default args timing, iterator-based `for`, `for/else` + `while/else`, Python truthiness and short-circuiting.
|
||||
|
||||
### Fallback Strategy
|
||||
- **Fallback unit: Per-function.** If a function body contains unsupported nodes, compile a "PyThunk" that calls into CPython.
|
||||
- **Boundary types:** Define canonical bridges: `PyAnyBox` in Nyash wrapping `Py<PyAny>`
|
||||
- **Imports and globals:** Execute module top-level in Python; then selectively replace functions
|
||||
|
||||
### pyo3/GIL Best Practices
|
||||
- **Initialization:** Call `pyo3::prepare_freethreaded_python()` once
|
||||
- **GIL usage:**
|
||||
- Use `Python::with_gil(|py| { ... })` for all Python calls
|
||||
- Minimize time under GIL; copy data out promptly
|
||||
- For heavy Rust work, drop GIL: `py.allow_threads(|| { ... })`
|
||||
- **Data transfer:** Prefer building JSON on the Python side
|
||||
- **Versioning:** Pin Python minor version; embed version string in the IR
|
||||
|
||||
### Phasing and Priorities (Refined)
|
||||
- **Phase 1 (Parser + Minimal Semantics):**
|
||||
- Python→JSON exporter with location info
|
||||
- Nyash IR for expressions and basic statements
|
||||
- Semantics fidelity for: iterator protocol, truthiness, scoping
|
||||
- **Fallback per-function for anything else**
|
||||
- **Phase 2-4:** Coverage expansion → Objects/Runtime → MIR/JIT
|
||||
|
||||
### Parser Bug Validation Strategy
|
||||
- **Differential execution:** Curate pairs of semantically equivalent snippets
|
||||
- **Oracle testing:** Run CPython as oracle and compare
|
||||
- **Fuzzing:** Grammar-based fuzzers
|
||||
- **Coverage and gating:** Track node-kind coverage
|
||||
|
||||
### IR/JSON Design Tips
|
||||
- Include: `node_type`, children, `lineno/col_offset`, `py_version`, `ast_format`, `support_level`
|
||||
- Canonicalize: normalize forms, operator names
|
||||
- Determinism: maintain stable field ordering
|
||||
|
||||
### Concrete Recommendations
|
||||
- **Pin to one Python minor (e.g., 3.11 or 3.12)**
|
||||
- **Choose per-function fallback as the core boundary**
|
||||
- **Implement Python truthiness, iterator protocol, and scoping correctly before optimizing**
|
||||
- **Keep the GIL minimal: build the JSON in Python; parse in Rust**
|
||||
- **Telemetry from day one: log unsupported node kinds and fallback counts**
|
||||
- **Start with JSON; plan migration to a compact binary once stable**
|
||||
|
||||
---
|
||||
|
||||
## 統合された重要ポイント
|
||||
|
||||
### 🎯 両エキスパートが一致した最重要事項
|
||||
|
||||
1. **関数単位のフォールバック戦略**
|
||||
- ファイル全体でなく関数レベルでコンパイル/フォールバックを切り替え
|
||||
- 未対応機能を含む関数はCPython exec、対応済み関数はNyash MIR/JIT
|
||||
|
||||
2. **Python バージョン固定**
|
||||
- Python 3.11または3.12に固定
|
||||
- AST安定性の確保とバージョン間の差異回避
|
||||
|
||||
3. **意味論の正確な実装が最優先**
|
||||
- 最適化より先にPython互換性を確保
|
||||
- 特に: イテレータプロトコル、真偽値判定、スコーピング規則
|
||||
|
||||
4. **GIL管理の最小化**
|
||||
- Python側でJSON生成、Rust側で解析
|
||||
- 重い処理はGIL外で実行
|
||||
|
||||
5. **テレメトリーの重要性**
|
||||
- 未対応ノードの記録
|
||||
- フォールバック率の計測
|
||||
- 実行時の統計情報収集
|
||||
|
||||
### 🚨 特に注意すべき意味論の違い
|
||||
|
||||
1. **制御フロー**
|
||||
- for/else, while/else の独特な挙動
|
||||
- forループのイテレータプロトコル
|
||||
|
||||
2. **スコープ規則**
|
||||
- LEGB(Local, Enclosing, Global, Builtins)
|
||||
- global/nonlocal宣言
|
||||
- 内包表記の独立スコープ(Python 3)
|
||||
|
||||
3. **数値演算**
|
||||
- / (true division) vs // (floor division)
|
||||
- デフォルトで大整数
|
||||
- NaN の扱い
|
||||
|
||||
4. **関数定義**
|
||||
- デフォルト引数は定義時に評価
|
||||
- *args/**kwargs の扱い
|
||||
- デコレータの実行順序
|
||||
|
||||
### 📊 成功の測定指標
|
||||
|
||||
1. **カバレッジ**: コンパイル済み vs フォールバック関数の比率
|
||||
2. **性能向上**: 数値計算ベンチマークでの改善率
|
||||
3. **バグ発見数**: Differential Testingで発見されたバグ数
|
||||
4. **エコシステム**: 動作する有名Pythonライブラリの数
|
||||
@ -0,0 +1,244 @@
|
||||
# [Archived] 旧 Phase 10.1 - Python統合計画(ChatGPT5高速開発版)
|
||||
最終更新: 2025-08-27 / 状態: Archived(Phase 10.5 に統合)
|
||||
|
||||
現行の計画は Phase 10.5 のドキュメントに集約しています。最新は以下を参照してください:
|
||||
- Phase 10.5 Index: ./INDEX.md
|
||||
- 10.5a – Python ABI 設計: ./10.5a-ABI-DESIGN.md
|
||||
- 10.5b – ネイティブビルド基盤: ./10.5b-native-build-consolidation.md
|
||||
|
||||
## 🚀 概要:2週間での爆速実装(当時案)
|
||||
|
||||
ChatGPT5の最小Box設計により、元の1ヶ月計画を**2週間**に圧縮。Nyash既存アーキテクチャ(MirBuilder 100%実装済み、HandleRegistry 80%実装済み)を最大活用。
|
||||
|
||||
## 📦 ChatGPT5の6つの必須Box(最小実装)
|
||||
|
||||
### 1. **PythonParserBox** - CPython AST取得(3日)
|
||||
```rust
|
||||
// 既存: pyo3統合済み
|
||||
// 追加: JSON出力とバージョン固定
|
||||
pub struct PythonParserBox {
|
||||
base: BoxBase,
|
||||
py_helper: Arc<Mutex<PyHelper>>,
|
||||
version: String, // "3.11"固定
|
||||
}
|
||||
|
||||
// メソッド(最小限)
|
||||
- parse_to_json(src: String) -> String // ast.parse() → JSON
|
||||
- get_version() -> String // "3.11"
|
||||
```
|
||||
|
||||
### 2. **Py2NyASTBox** - AST変換(3日)
|
||||
```rust
|
||||
// 新規実装
|
||||
pub struct Py2NyASTBox {
|
||||
base: BoxBase,
|
||||
normalizer: AstNormalizer,
|
||||
}
|
||||
|
||||
// メソッド(制御フロー正規化)
|
||||
- convert(json: String) -> NyashAst
|
||||
- normalize_for_else(ast: &mut PyAst) // for/else → if分岐
|
||||
- normalize_comprehensions(ast: &mut PyAst)
|
||||
```
|
||||
|
||||
### 3. **MirBuilderBox** - MIR生成(0日 - 既存活用)
|
||||
```rust
|
||||
// 既存実装100%活用
|
||||
// 追加: Python由来フラグのみ
|
||||
pub struct MirBuilderBox {
|
||||
// 既存フィールド
|
||||
is_python_origin: bool, // 追加
|
||||
}
|
||||
```
|
||||
|
||||
### 4. **BoundaryBox** - 型変換(2日)
|
||||
```rust
|
||||
// Python版のHandleRegistry相当
|
||||
pub struct BoundaryBox {
|
||||
base: BoxBase,
|
||||
handle_registry: Arc<Mutex<HandleRegistry>>, // 既存80%活用
|
||||
}
|
||||
|
||||
// メソッド
|
||||
- py_to_jit(py_val: PyValBox) -> JitValue
|
||||
- jit_to_py(jit_val: JitValue) -> PyValBox
|
||||
- register_handle(obj: Arc<dyn NyashBox>) -> u64
|
||||
```
|
||||
|
||||
### 5. **PyRuntimeBox** - 実行制御(2日)
|
||||
```rust
|
||||
pub struct PyRuntimeBox {
|
||||
base: BoxBase,
|
||||
fallback_stats: FallbackStats,
|
||||
}
|
||||
|
||||
// メソッド(関数単位フォールバック)
|
||||
- execute_function(name: &str, args: Vec<JitValue>) -> JitValue
|
||||
- should_fallback(func_ast: &PyAst) -> bool // Phase1機能判定
|
||||
- fallback_to_cpython(code: &str) -> PyObject
|
||||
```
|
||||
|
||||
### 6. **ObservabilityBox** - 統計収集(1日)
|
||||
```rust
|
||||
// 既存のJIT統計システム(70%実装済み)を拡張
|
||||
pub struct ObservabilityBox {
|
||||
base: BoxBase,
|
||||
stats_collector: StatsCollector,
|
||||
}
|
||||
|
||||
// JSONLフォーマット出力
|
||||
- log_attempt(module: &str, func: &str, compiled: bool, reason: Option<&str>)
|
||||
- output_jsonl() -> String
|
||||
```
|
||||
|
||||
## 🗓️ 実装タイムライン(2週間)
|
||||
|
||||
### Week 1: 基盤実装(7日)
|
||||
- **Day 1-3**: PythonParserBox実装
|
||||
- pyo3統合(既存活用)
|
||||
- Python 3.11固定
|
||||
- JSON出力実装
|
||||
|
||||
- **Day 4-6**: Py2NyASTBox実装
|
||||
- 制御フロー正規化
|
||||
- for/else, while/else変換
|
||||
- Phase1機能のみサポート
|
||||
|
||||
- **Day 7**: ObservabilityBox実装
|
||||
- 既存JIT統計拡張
|
||||
- JSONLフォーマット
|
||||
|
||||
### Week 2: 統合と検証(7日)
|
||||
- **Day 8-9**: BoundaryBox実装
|
||||
- HandleRegistry活用
|
||||
- 型変換ルール確立
|
||||
|
||||
- **Day 10-11**: PyRuntimeBox実装
|
||||
- 関数単位フォールバック
|
||||
- CPython連携
|
||||
|
||||
- **Day 12-13**: 統合テスト
|
||||
- Differential Testing
|
||||
- ベンチマーク実行
|
||||
|
||||
- **Day 14**: ドキュメント・リリース
|
||||
- 使用例作成
|
||||
- パフォーマンス測定
|
||||
|
||||
## 📊 既存アーキテクチャとの整合性
|
||||
|
||||
### 活用率
|
||||
- **MirBuilderBox**: 100%(変更なし)
|
||||
- **HandleRegistry**: 80%(BoundaryBoxで再利用)
|
||||
- **JIT統計**: 70%(ObservabilityBoxで拡張)
|
||||
- **VM/JIT実行**: 100%(そのまま使用)
|
||||
|
||||
### 新規実装
|
||||
- **PythonParserBox**: 30%(pyo3部分は既存)
|
||||
- **Py2NyASTBox**: 100%新規
|
||||
- **PyRuntimeBox**: 100%新規
|
||||
|
||||
## 🎯 Phase 1でサポートする機能(Codex先生推奨)
|
||||
|
||||
### 必須実装
|
||||
1. **LEGB + locals/freevars** - スコーピング規則
|
||||
2. **デフォルト引数の評価タイミング** - 定義時評価
|
||||
3. **イテレータベースのfor文**
|
||||
4. **for/else + while/else**
|
||||
5. **Python真偽値判定**
|
||||
6. **短絡評価**
|
||||
|
||||
### サポートする文
|
||||
- def(関数定義)
|
||||
- if/elif/else
|
||||
- for(else節対応)
|
||||
- while(else節対応)
|
||||
- break/continue
|
||||
- return
|
||||
|
||||
### サポートする式
|
||||
- 算術演算子(+,-,*,/,//,%)
|
||||
- 比較演算子(==,!=,<,>,<=,>=)
|
||||
- 論理演算子(and,or,not)
|
||||
- 関数呼び出し
|
||||
- リテラル(数値/文字列/bool)
|
||||
|
||||
## 📈 成功指標(2週間後)
|
||||
|
||||
### 定量的
|
||||
- **関数コンパイル率**: 70%以上(Phase 1機能)
|
||||
- **実行速度**: 純Pythonループで2倍以上
|
||||
- **メモリ効率**: CPython比50%削減
|
||||
|
||||
### 定性的
|
||||
- **統計可視化**: JSONL形式で全実行を記録
|
||||
- **デバッグ容易性**: 関数単位でフォールバック理由明示
|
||||
- **将来拡張性**: Phase 2-4への明確な道筋
|
||||
|
||||
## 🔧 実装例(最終形)
|
||||
|
||||
```nyash
|
||||
// Nyashから使用
|
||||
local py = new PythonParserBox()
|
||||
local converter = new Py2NyASTBox()
|
||||
local builder = new MirBuilderBox()
|
||||
local runtime = new PyRuntimeBox()
|
||||
local stats = new ObservabilityBox()
|
||||
|
||||
// Pythonコードをコンパイル・実行
|
||||
local code = "def fib(n): return n if n <= 1 else fib(n-1) + fib(n-2)"
|
||||
local json_ast = py.parse_to_json(code)
|
||||
local ny_ast = converter.convert(json_ast)
|
||||
local mir = builder.build(ny_ast)
|
||||
|
||||
// 実行(自動的にJIT/VMで高速化)
|
||||
local result = runtime.execute_function("fib", [10])
|
||||
print(result) // 55
|
||||
|
||||
// 統計出力
|
||||
print(stats.output_jsonl())
|
||||
// {"mod":"test","func":"fib","attempt":1,"jitted":true,"native":true}
|
||||
```
|
||||
|
||||
## 🚨 重要な設計判断
|
||||
|
||||
### 1. 関数単位の境界
|
||||
- ファイル単位ではなく**関数単位**でコンパイル/フォールバック
|
||||
- 未対応機能を含む関数のみCPython実行
|
||||
|
||||
### 2. Python 3.11固定
|
||||
- AST安定性の確保
|
||||
- 将来のバージョンアップは別Phase
|
||||
|
||||
### 3. 箱境界の明確化
|
||||
- 各Boxは単一責任
|
||||
- 相互依存を最小化
|
||||
- テスト可能な粒度
|
||||
|
||||
### 4. 既存資産の最大活用
|
||||
- MirBuilder/VM/JITはそのまま使用
|
||||
- 新規実装は変換層のみ
|
||||
|
||||
## 🎉 期待される成果
|
||||
|
||||
### 即時的効果(2週間後)
|
||||
- Pythonコードの70%がNyashで高速実行
|
||||
- バグ検出力の飛躍的向上(Differential Testing)
|
||||
- 統計による最適化ポイントの可視化
|
||||
|
||||
### 長期的効果
|
||||
- Python→Nyash→Native の世界初パイプライン確立
|
||||
- Nyash言語の成熟度向上
|
||||
- エコシステムの爆発的拡大
|
||||
|
||||
## 📝 次のステップ
|
||||
|
||||
1. **Phase 10.7完了確認** - JIT統計JSONの安定化
|
||||
2. **PythonParserBox実装開始** - pyo3統合から着手
|
||||
3. **テストコーパス準備** - Python標準ライブラリから抜粋
|
||||
|
||||
---
|
||||
|
||||
**作成者**: Claude(Claude Code)
|
||||
**承認者**: ChatGPT5(予定)
|
||||
**開始予定**: Phase 10.7完了直後
|
||||
@ -0,0 +1,602 @@
|
||||
# Python統合マイルストーン(M0〜M6)
|
||||
|
||||
**作成**: 2025-10-02
|
||||
**ソース**: ChatGPT Pro UltraThink Mode
|
||||
**ステータス**: 計画・Phase 15完了後に実装
|
||||
|
||||
---
|
||||
|
||||
## 📋 概要
|
||||
|
||||
Python-Hakorune統合を**段階的に**進めるためのマイルストーン定義です。
|
||||
最小から始めて、機能を段階的に追加していきます。
|
||||
|
||||
---
|
||||
|
||||
## 🎯 M0: PyRuntimeBox の最小化
|
||||
|
||||
### 目的
|
||||
`import("math")/call("sqrt")` が走る最小実装
|
||||
|
||||
### 成果物
|
||||
- [ ] PyRuntimeBoxの基本実装
|
||||
- [ ] PyFunctionBoxの基本実装
|
||||
- [ ] math.sqrtの実行確認
|
||||
|
||||
### 実装内容
|
||||
|
||||
#### PyRuntimeBox(最小版)
|
||||
```rust
|
||||
pub struct PyRuntimeBox {
|
||||
py: GILGuard,
|
||||
modules: HashMap<String, Py<PyModule>>,
|
||||
}
|
||||
|
||||
impl PyRuntimeBox {
|
||||
pub fn init() -> Self {
|
||||
pyo3::prepare_freethreaded_python();
|
||||
let gil = Python::acquire_gil();
|
||||
PyRuntimeBox {
|
||||
py: gil,
|
||||
modules: HashMap::new(),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn import(&mut self, name: &str) -> PyModuleBox {
|
||||
let py = self.py.python();
|
||||
let module = PyModule::import(py, name).unwrap();
|
||||
self.modules.insert(name.to_string(), module.into());
|
||||
PyModuleBox::new(module)
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
#### テストケース
|
||||
```hakorune
|
||||
using "python"
|
||||
|
||||
box Main {
|
||||
flow main() {
|
||||
let py = PyRuntimeBox();
|
||||
let math = py.import("math");
|
||||
let sqrt = math.get("sqrt");
|
||||
let result = sqrt.exec([2.0]);
|
||||
assert(result.to_float() == 1.4142135623730951);
|
||||
py.fini();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Capability/Contract
|
||||
- Capability/Contractは**ログのみ**(観測)
|
||||
- `HAKO_TRACE_EFFECTS=1` で呼び出しログ記録
|
||||
|
||||
### DoD(完了定義)
|
||||
- ✅ math.sqrt(2.0)が正常実行
|
||||
- ✅ 結果が正しい値を返す
|
||||
- ✅ メモリリークなし
|
||||
- ✅ スモークテスト追加
|
||||
|
||||
### 期間
|
||||
**1週間**
|
||||
|
||||
---
|
||||
|
||||
## 🛡️ M1: Capability ゲート
|
||||
|
||||
### 目的
|
||||
**ホワイトリスト**運用開始
|
||||
|
||||
### 成果物
|
||||
- [ ] Capability管理機構
|
||||
- [ ] hako.toml設定サポート
|
||||
- [ ] 違反時のエラーハンドリング
|
||||
|
||||
### 実装内容
|
||||
|
||||
#### hako.toml設定
|
||||
```toml
|
||||
[box.PyRuntimeBox.capabilities]
|
||||
allow = [
|
||||
"py.import:math",
|
||||
"py.import:json",
|
||||
"py.time:monotonic"
|
||||
]
|
||||
deny = [
|
||||
"py.subprocess",
|
||||
"py.net"
|
||||
]
|
||||
enforce = true
|
||||
```
|
||||
|
||||
#### Capability検証
|
||||
```rust
|
||||
impl PyRuntimeBox {
|
||||
pub fn import(&mut self, name: &str) -> Result<PyModuleBox> {
|
||||
// Capability確認
|
||||
if !self.capabilities.allows_import(name) {
|
||||
return Err(CapabilityError::ImportDenied(name.to_string()));
|
||||
}
|
||||
|
||||
// 通常のimport処理
|
||||
// ...
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
#### テストケース
|
||||
```hakorune
|
||||
using "python"
|
||||
|
||||
box Main {
|
||||
flow main() {
|
||||
let py = PyRuntimeBox();
|
||||
|
||||
// OK: 許可されたモジュール
|
||||
let math = py.import("math");
|
||||
|
||||
// ERROR: 拒否されたモジュール
|
||||
try {
|
||||
let subprocess = py.import("subprocess");
|
||||
} catch(e) {
|
||||
assert(e.type == "CapabilityError");
|
||||
}
|
||||
|
||||
py.fini();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### トグル
|
||||
```bash
|
||||
# Dev: 違反時fail-fast
|
||||
HAKO_PLUGIN_CAPS_ENFORCE=1
|
||||
|
||||
# Prod: 違反時警告(継続)
|
||||
HAKO_PLUGIN_CAPS_ENFORCE=0
|
||||
```
|
||||
|
||||
### DoD(完了定義)
|
||||
- ✅ allow/denyリスト動作確認
|
||||
- ✅ 違反時の適切なエラー
|
||||
- ✅ hako.toml読み込み動作
|
||||
- ✅ トグル切り替え動作
|
||||
|
||||
### 期間
|
||||
**1-2週間**
|
||||
|
||||
---
|
||||
|
||||
## ✅ M2: Contract 検証
|
||||
|
||||
### 目的
|
||||
`pre/post` 条件検証の実装
|
||||
|
||||
### 成果物
|
||||
- [ ] Contract検証機構
|
||||
- [ ] pre条件検証(引数チェック)
|
||||
- [ ] post条件検証(返り値チェック)
|
||||
|
||||
### 実装内容
|
||||
|
||||
#### Contract定義
|
||||
```toml
|
||||
[contracts.PyFunctionBox.exec]
|
||||
pre = [
|
||||
"args.len <= 8",
|
||||
"bytes_total <= 1_000_000"
|
||||
]
|
||||
post = [
|
||||
"result.size <= 1_000_000",
|
||||
"no_exception",
|
||||
"allow_none = true"
|
||||
]
|
||||
```
|
||||
|
||||
#### Contract検証(Python側wrapper)
|
||||
```python
|
||||
# hakorune_contract.py
|
||||
def verify_contract(func, pre_conditions, post_conditions):
|
||||
def wrapper(*args, **kwargs):
|
||||
# Pre条件検証
|
||||
if len(args) > 8:
|
||||
raise ContractViolation("args.len > 8")
|
||||
|
||||
total_bytes = sum(sys.getsizeof(a) for a in args)
|
||||
if total_bytes > 1_000_000:
|
||||
raise ContractViolation("bytes_total > 1_000_000")
|
||||
|
||||
# 実行
|
||||
result = func(*args, **kwargs)
|
||||
|
||||
# Post条件検証
|
||||
if sys.getsizeof(result) > 1_000_000:
|
||||
raise ContractViolation("result.size > 1_000_000")
|
||||
|
||||
return result
|
||||
|
||||
return wrapper
|
||||
```
|
||||
|
||||
#### テストケース
|
||||
```hakorune
|
||||
using "python"
|
||||
|
||||
box Main {
|
||||
flow main() {
|
||||
let py = PyRuntimeBox();
|
||||
|
||||
// OK: Contract満たす
|
||||
let math = py.import("math");
|
||||
let sqrt = math.get("sqrt");
|
||||
let r1 = sqrt.exec([2.0]);
|
||||
|
||||
// ERROR: 引数多すぎ
|
||||
try {
|
||||
let r2 = sqrt.exec([1,2,3,4,5,6,7,8,9]);
|
||||
} catch(e) {
|
||||
assert(e.type == "ContractViolation");
|
||||
}
|
||||
|
||||
py.fini();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### DoD(完了定義)
|
||||
- ✅ pre条件違反検出
|
||||
- ✅ post条件違反検出
|
||||
- ✅ ErrorBox化
|
||||
- ✅ トグル切り替え(strict/warn)
|
||||
|
||||
### 期間
|
||||
**2週間**
|
||||
|
||||
---
|
||||
|
||||
## 🎲 M3: Deterministic
|
||||
|
||||
### 目的
|
||||
`random/time/os.urandom` に shims を適用
|
||||
|
||||
### 成果物
|
||||
- [ ] Deterministic shims実装
|
||||
- [ ] random固定化
|
||||
- [ ] time論理クロック化
|
||||
- [ ] スモーク再現性確認
|
||||
|
||||
### 実装内容
|
||||
|
||||
#### Deterministic Random
|
||||
```python
|
||||
# hakorune_deterministic.py
|
||||
class DeterministicRandom:
|
||||
def __init__(self, seed=42):
|
||||
self._rng = random.Random(seed)
|
||||
|
||||
def random(self):
|
||||
return self._rng.random()
|
||||
|
||||
def randint(self, a, b):
|
||||
return self._rng.randint(a, b)
|
||||
|
||||
# モンキーパッチ
|
||||
if os.getenv('HAKO_DETERMINISTIC') == '1':
|
||||
random.random = DeterministicRandom().random
|
||||
```
|
||||
|
||||
#### Logical Clock
|
||||
```python
|
||||
class LogicalClock:
|
||||
def __init__(self):
|
||||
self._tick = 0
|
||||
|
||||
def monotonic(self):
|
||||
self._tick += 1
|
||||
return float(self._tick)
|
||||
|
||||
def time(self):
|
||||
return self.monotonic()
|
||||
|
||||
# モンキーパッチ
|
||||
if os.getenv('HAKO_DETERMINISTIC') == '1':
|
||||
time.monotonic = LogicalClock().monotonic
|
||||
```
|
||||
|
||||
#### テストケース
|
||||
```hakorune
|
||||
using "python"
|
||||
|
||||
box Main {
|
||||
flow main() {
|
||||
let py = PyRuntimeBox();
|
||||
|
||||
// Deterministic mode
|
||||
let random = py.import("random");
|
||||
|
||||
// 同じseedなら同じ結果
|
||||
let r1 = random.get("random").exec([]);
|
||||
let r2 = random.get("random").exec([]);
|
||||
assert(r1 == r2); // Deterministic!
|
||||
|
||||
py.fini();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### トグル
|
||||
```bash
|
||||
# Deterministic モード有効化
|
||||
HAKO_DETERMINISTIC=1
|
||||
HAKO_TRACE_EFFECTS=1 # 効果ログ収集
|
||||
```
|
||||
|
||||
### DoD(完了定義)
|
||||
- ✅ random固定化動作
|
||||
- ✅ time論理クロック動作
|
||||
- ✅ スモーク再現性100%
|
||||
- ✅ トレースログ記録
|
||||
|
||||
### 期間
|
||||
**1-2週間**
|
||||
|
||||
---
|
||||
|
||||
## 🏗️ M4: Type/Instance 反射
|
||||
|
||||
### 目的
|
||||
クラス→`PyTypeBox`、インスタンス→`PyInstanceBox`
|
||||
|
||||
### 成果物
|
||||
- [ ] PyTypeBox実装
|
||||
- [ ] PyInstanceBox実装
|
||||
- [ ] get/setField統一
|
||||
- [ ] call_method統一
|
||||
|
||||
### 実装内容
|
||||
|
||||
#### PyTypeBox
|
||||
```rust
|
||||
pub struct PyTypeBox {
|
||||
py_type: Py<PyType>,
|
||||
}
|
||||
|
||||
impl PyTypeBox {
|
||||
pub fn get_name(&self) -> String {
|
||||
// クラス名取得
|
||||
}
|
||||
|
||||
pub fn get_bases(&self) -> Vec<PyTypeBox> {
|
||||
// 基底クラスリスト
|
||||
}
|
||||
|
||||
pub fn new_instance(&self, args: Vec<Value>) -> PyInstanceBox {
|
||||
// インスタンス化
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
#### PyInstanceBox
|
||||
```rust
|
||||
pub struct PyInstanceBox {
|
||||
py_obj: Py<PyAny>,
|
||||
}
|
||||
|
||||
impl PyInstanceBox {
|
||||
pub fn get_field(&self, name: &str) -> Value {
|
||||
// フィールド取得
|
||||
}
|
||||
|
||||
pub fn set_field(&self, name: &str, value: Value) {
|
||||
// フィールド設定
|
||||
}
|
||||
|
||||
pub fn call_method(&self, name: &str, args: Vec<Value>) -> Value {
|
||||
// メソッド呼び出し
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
#### テストケース
|
||||
```hakorune
|
||||
using "python"
|
||||
|
||||
box Main {
|
||||
flow main() {
|
||||
let py = PyRuntimeBox();
|
||||
|
||||
// クラス取得
|
||||
let code = "
|
||||
class Player:
|
||||
def __init__(self, name):
|
||||
self.name = name
|
||||
self.health = 100
|
||||
|
||||
def heal(self, amount):
|
||||
self.health += amount
|
||||
";
|
||||
py.exec(code);
|
||||
let PlayerClass = py.get("Player"); // PyTypeBox
|
||||
|
||||
// インスタンス化
|
||||
let player = PlayerClass.new_instance(["Alice"]); // PyInstanceBox
|
||||
|
||||
// フィールドアクセス
|
||||
let name = player.get_field("name");
|
||||
assert(name == "Alice");
|
||||
|
||||
// メソッド呼び出し
|
||||
player.call_method("heal", [20]);
|
||||
let health = player.get_field("health");
|
||||
assert(health == 120);
|
||||
|
||||
py.fini();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### DoD(完了定義)
|
||||
- ✅ PyTypeBox動作確認
|
||||
- ✅ PyInstanceBox動作確認
|
||||
- ✅ get/setField統一動作
|
||||
- ✅ call_method統一動作
|
||||
|
||||
### 期間
|
||||
**2-3週間**
|
||||
|
||||
---
|
||||
|
||||
## 🔄 M5: ABI 昇格
|
||||
|
||||
### 目的
|
||||
C ABI→Hakorune ABI(vtable)へPoC
|
||||
|
||||
### 成果物
|
||||
- [ ] Hakorune ABI実装
|
||||
- [ ] vtable生成
|
||||
- [ ] C ABI互換レイヤー
|
||||
- [ ] 段階切り替え確認
|
||||
|
||||
### 実装内容
|
||||
|
||||
#### Hakorune ABI(vtable)
|
||||
```rust
|
||||
#[repr(C)]
|
||||
pub struct HakoruneABI {
|
||||
vtable: *const VTable,
|
||||
data: *mut c_void,
|
||||
}
|
||||
|
||||
#[repr(C)]
|
||||
pub struct VTable {
|
||||
init: extern "C" fn(*mut c_void),
|
||||
fini: extern "C" fn(*mut c_void),
|
||||
invoke: extern "C" fn(*mut c_void, method_id: u32, args: *const TLV) -> TLV,
|
||||
}
|
||||
```
|
||||
|
||||
#### トグル切り替え
|
||||
```bash
|
||||
# C ABI使用
|
||||
HAKO_ABI_VTABLE=0
|
||||
|
||||
# Hakorune ABI使用
|
||||
HAKO_ABI_VTABLE=1
|
||||
HAKO_ABI_STRICT=1 # フォールバック禁止
|
||||
```
|
||||
|
||||
#### テストケース
|
||||
```hakorune
|
||||
using "python"
|
||||
|
||||
box Main {
|
||||
flow main() {
|
||||
// どちらのABIでも同じコードが動く
|
||||
let py = PyRuntimeBox();
|
||||
let math = py.import("math");
|
||||
let sqrt = math.get("sqrt");
|
||||
let result = sqrt.exec([2.0]);
|
||||
assert(result.to_float() == 1.4142135623730951);
|
||||
py.fini();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### DoD(完了定義)
|
||||
- ✅ Hakorune ABI動作確認
|
||||
- ✅ C ABI互換性維持
|
||||
- ✅ トグル切り替え動作
|
||||
- ✅ パフォーマンス劣化なし
|
||||
|
||||
### 期間
|
||||
**3-4週間**
|
||||
|
||||
---
|
||||
|
||||
## 📦 M6: AOT/EXE の包み込み(10.5b連動)
|
||||
|
||||
### 目的
|
||||
Python依存を**スタティック or 埋め込み**方針で詰め、`hako` EXE生成ラインに統合
|
||||
|
||||
### 成果物
|
||||
- [ ] スタティックリンク対応
|
||||
- [ ] 埋め込みPython対応
|
||||
- [ ] EXE生成パイプライン統合
|
||||
- [ ] クロスプラットフォーム確認
|
||||
|
||||
### 実装内容
|
||||
|
||||
#### スタティックリンク
|
||||
```toml
|
||||
# Cargo.toml
|
||||
[dependencies]
|
||||
pyo3 = { version = "0.20", features = ["auto-initialize", "extension-module"] }
|
||||
|
||||
[build-dependencies]
|
||||
pyo3-build-config = "0.20"
|
||||
```
|
||||
|
||||
#### 埋め込みPython
|
||||
```rust
|
||||
// Python標準ライブラリを埋め込み
|
||||
#[cfg(feature = "embed-python")]
|
||||
const PYTHON_STDLIB: &[u8] = include_bytes!("python3.11.zip");
|
||||
```
|
||||
|
||||
#### EXE生成
|
||||
```bash
|
||||
# AOTコンパイル
|
||||
hakorune --backend llvm --embed-python script.hkr -o app
|
||||
|
||||
# 生成されたEXE
|
||||
./app # Python依存なしで実行可能
|
||||
```
|
||||
|
||||
### プラットフォーム対応
|
||||
|
||||
| Platform | Python | 方式 |
|
||||
|----------|--------|------|
|
||||
| Linux | 3.8+ | 動的/静的両対応 |
|
||||
| macOS | 3.8+ | 動的優先 |
|
||||
| Windows | 3.8+ | 埋め込み推奨 |
|
||||
|
||||
### DoD(完了定義)
|
||||
- ✅ Linux EXE生成
|
||||
- ✅ macOS EXE生成
|
||||
- ✅ Windows EXE生成
|
||||
- ✅ Python依存最小化
|
||||
- ✅ サイズ最適化
|
||||
|
||||
### 期間
|
||||
**4-6週間**
|
||||
|
||||
---
|
||||
|
||||
## 📊 全体スケジュール
|
||||
|
||||
| マイルストーン | 期間 | 開始条件 |
|
||||
|--------------|------|---------|
|
||||
| M0: PyRuntimeBox最小化 | 1週間 | Phase 15完了 |
|
||||
| M1: Capabilityゲート | 1-2週間 | M0完了 |
|
||||
| M2: Contract検証 | 2週間 | M1完了 |
|
||||
| M3: Deterministic | 1-2週間 | M2完了 |
|
||||
| M4: Type/Instance反射 | 2-3週間 | M3完了 |
|
||||
| M5: ABI昇格 | 3-4週間 | M4完了 |
|
||||
| M6: AOT/EXE統合 | 4-6週間 | M5完了 |
|
||||
|
||||
**合計**: 約3-5ヶ月
|
||||
|
||||
---
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- [強化版アーキテクチャv2](../design/enhanced-architecture-v2.md) - 設計詳細
|
||||
- [メタ設定例](../design/meta-config-examples.md) - hako.toml設定例
|
||||
- [リスクと対策](../design/risks-and-mitigations.md) - 既知のリスク
|
||||
- [Phase 20 README](../README.md) - 全体概要
|
||||
|
||||
---
|
||||
|
||||
**最終更新**: 2025-10-02
|
||||
**作成者**: ChatGPT Pro (UltraThink Mode)
|
||||
**ステータス**: 計画・Phase 15完了後に実装
|
||||
@ -0,0 +1,207 @@
|
||||
# PythonParserBox設計提案 - CPythonパーサーを使ったPython→Nyash変換
|
||||
|
||||
## 概要
|
||||
CPythonの公式パーサーを活用して、PythonコードをNyashで直接実行可能にする革命的なアプローチ。
|
||||
PythonコードをNyashのAST/MIRに変換し、Nyashの最適化・JITコンパイルの恩恵を受けられるようにする。
|
||||
|
||||
## アーキテクチャ
|
||||
|
||||
### 1. PythonParserBox(ビルトインBox)
|
||||
```nyash
|
||||
// 使用例
|
||||
local py_parser = new PythonParserBox()
|
||||
|
||||
// Pythonコードを直接パース
|
||||
local ast = py_parser.parse("""
|
||||
def calculate(x, y):
|
||||
return x * 2 + y
|
||||
|
||||
result = calculate(10, 5)
|
||||
""")
|
||||
|
||||
// NyashのASTに変換
|
||||
local nyash_ast = py_parser.to_nyash_ast(ast)
|
||||
|
||||
// 直接実行も可能
|
||||
local result = py_parser.run(python_code)
|
||||
```
|
||||
|
||||
### 2. 実装構造
|
||||
```rust
|
||||
pub struct PythonParserBox {
|
||||
base: BoxBase,
|
||||
parser: CPythonParser, // CPythonの公式パーサー使用
|
||||
}
|
||||
|
||||
impl PythonParserBox {
|
||||
// Python → Python AST
|
||||
pub fn parse(&self, code: &str) -> Box<dyn NyashBox> {
|
||||
let py_ast = self.parser.parse_string(code);
|
||||
Box::new(PythonAstBox { ast: py_ast })
|
||||
}
|
||||
|
||||
// Python AST → Nyash AST
|
||||
pub fn to_nyash_ast(&self, py_ast: &PythonAstBox) -> Box<dyn NyashBox> {
|
||||
let converter = AstConverter::new();
|
||||
converter.convert_python_to_nyash(py_ast)
|
||||
}
|
||||
|
||||
// Python AST → MIR(直接変換)
|
||||
pub fn to_mir(&self, py_ast: &PythonAstBox) -> MirModule {
|
||||
let mut builder = MirBuilder::new();
|
||||
for func in py_ast.functions() {
|
||||
self.convert_function_to_mir(&mut builder, func);
|
||||
}
|
||||
builder.build()
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## AST変換マッピング
|
||||
|
||||
### Python → Nyash対応表
|
||||
| Python AST | Nyash AST | 説明 |
|
||||
|------------|-----------|------|
|
||||
| FunctionDef | FunctionDecl | 関数定義 |
|
||||
| BinOp | BinaryOp | 二項演算 |
|
||||
| Call | MethodCall | 関数呼び出し |
|
||||
| Assign | Assignment | 代入 |
|
||||
| If | IfStatement | 条件分岐 |
|
||||
| While/For | LoopStatement | ループ |
|
||||
| Return | ReturnStatement | return文 |
|
||||
| Import | NewBox/LoadPlugin | import → Box化 |
|
||||
|
||||
### 型変換戦略
|
||||
```rust
|
||||
// Python動的型 → Nyash Box
|
||||
match py_value {
|
||||
PyInt(n) => IntegerBox::new(n),
|
||||
PyFloat(f) => FloatBox::new(f),
|
||||
PyStr(s) => StringBox::new(s),
|
||||
PyList(items) => ArrayBox::from_iter(items),
|
||||
PyDict(map) => MapBox::from_iter(map),
|
||||
PyObject(obj) => PythonObjectBox::new(obj), // 変換不能な場合
|
||||
}
|
||||
```
|
||||
|
||||
## MIR生成例
|
||||
|
||||
### Pythonコード
|
||||
```python
|
||||
def calculate(x, y):
|
||||
return x * 2 + y
|
||||
```
|
||||
|
||||
### 生成されるMIR
|
||||
```
|
||||
function calculate(%x, %y) {
|
||||
Load(%1, %x)
|
||||
Const(%2, 2)
|
||||
BinOp(%3, Mul, %1, %2)
|
||||
Load(%4, %y)
|
||||
BinOp(%5, Add, %3, %4)
|
||||
Return(%5)
|
||||
}
|
||||
```
|
||||
|
||||
## 利点
|
||||
|
||||
1. **完全な互換性**: CPython公式パーサーで100%正確なパース
|
||||
2. **統一最適化**: PythonコードもNyashのMIR最適化パイプラインを通る
|
||||
3. **JIT/AOTコンパイル**: PythonコードをネイティブコードにJIT/AOTコンパイル可能
|
||||
4. **段階的移行**: 既存Pythonコードを徐々にNyashに移行
|
||||
5. **デバッグ統一**: Nyashのデバッグツールでpythonコードもデバッグ可能
|
||||
|
||||
## 実装フェーズ
|
||||
|
||||
### Phase 1: 基本パーサー統合
|
||||
- CPythonパーサーのFFIバインディング
|
||||
- parse()メソッドでPython ASTを取得
|
||||
- AST可視化(dump_ast)
|
||||
|
||||
### Phase 2: AST変換
|
||||
- Python AST → Nyash AST変換器
|
||||
- 基本的な文法要素のサポート
|
||||
- 型変換システム
|
||||
|
||||
### Phase 3: MIR直接生成
|
||||
- Python AST → MIR変換
|
||||
- Python特有の最適化(動的型推論等)
|
||||
- ベンチマーク
|
||||
|
||||
### Phase 4: エコシステム統合
|
||||
- NumPy等の主要ライブラリサポート
|
||||
- Python例外 → Nyashエラー変換
|
||||
- async/await対応
|
||||
- GIL管理の自動化
|
||||
|
||||
## 技術的課題と解決策
|
||||
|
||||
### 1. GIL(Global Interpreter Lock)
|
||||
- 解決策: PythonコードはGILスコープ内で実行
|
||||
- 将来: MIR変換後はGILフリーで実行可能
|
||||
|
||||
### 2. Python動的型とNyash Box型のマッピング
|
||||
- 解決策: 実行時型情報を保持するPythonObjectBox
|
||||
- 最適化: よく使う型(int, str等)は専用Boxに変換
|
||||
|
||||
### 3. Pythonモジュールシステム
|
||||
- 解決策: importをNyashのプラグインロードにマッピング
|
||||
- pip packages → Nyashプラグインとして扱う
|
||||
|
||||
## 実用例
|
||||
|
||||
### 機械学習コードの実行
|
||||
```nyash
|
||||
local ml_code = """
|
||||
import numpy as np
|
||||
from sklearn.linear_model import LinearRegression
|
||||
|
||||
# データ準備
|
||||
X = np.array([[1, 1], [1, 2], [2, 2], [2, 3]])
|
||||
y = np.dot(X, np.array([1, 2])) + 3
|
||||
|
||||
# モデル訓練
|
||||
model = LinearRegression()
|
||||
model.fit(X, y)
|
||||
|
||||
# 予測
|
||||
predictions = model.predict(np.array([[3, 5]]))
|
||||
print(f'Prediction: {predictions[0]}')
|
||||
"""
|
||||
|
||||
local py_parser = new PythonParserBox()
|
||||
local result = py_parser.run(ml_code)
|
||||
```
|
||||
|
||||
### Webアプリケーション
|
||||
```nyash
|
||||
local flask_app = """
|
||||
from flask import Flask, jsonify
|
||||
|
||||
app = Flask(__name__)
|
||||
|
||||
@app.route('/api/hello/<name>')
|
||||
def hello(name):
|
||||
return jsonify({'message': f'Hello, {name}!'})
|
||||
|
||||
if __name__ == '__main__':
|
||||
app.run(port=5000)
|
||||
"""
|
||||
|
||||
local py_parser = new PythonParserBox()
|
||||
py_parser.run(flask_app) // FlaskアプリがNyash内で起動
|
||||
```
|
||||
|
||||
## 期待される効果
|
||||
|
||||
1. **パフォーマンス向上**: PythonコードがJITコンパイルされ高速化
|
||||
2. **メモリ効率**: NyashのGC/メモリ管理を活用
|
||||
3. **相互運用性**: Python↔Nyash↔Rust↔JS等の自由な組み合わせ
|
||||
4. **開発効率**: 既存Pythonライブラリをそのまま使える
|
||||
5. **将来性**: PythonコードをネイティブAOTコンパイル可能
|
||||
|
||||
## まとめ
|
||||
|
||||
PythonParserBoxは、Pythonの豊富なエコシステムとNyashの高性能実行エンジンを組み合わせる画期的なアプローチ。
|
||||
CPythonパーサーの信頼性とNyashのMIR/JIT最適化により、Pythonコードをより高速に、より効率的に実行できる。
|
||||
@ -0,0 +1,148 @@
|
||||
# PythonParserBox統合実装計画 - エキスパート評価後の最終版
|
||||
作成日: 2025-08-27
|
||||
|
||||
## 🎯 革命的な3つの価値
|
||||
|
||||
### 1. Pythonエコシステムの即座活用
|
||||
- 既存のPythonライブラリをNyashから直接利用可能
|
||||
- 段階的な移行パスの提供
|
||||
|
||||
### 2. Nyashパーサーのバグ自動検証(Differential Testing)
|
||||
- **世界中のPythonコードがNyashのテストケースに!**
|
||||
- CPythonをオラクルとして使用、出力・戻り値・例外を自動比較
|
||||
- 微妙なセマンティクスバグを大量に発見可能
|
||||
|
||||
### 3. 言語成熟度の飛躍的向上
|
||||
- 実用的なPythonコードでNyashをストレステスト
|
||||
- 発見されたバグ数が成熟度向上の定量的指標
|
||||
|
||||
## 🏆 エキスパート評価サマリー
|
||||
|
||||
### Gemini先生の評価
|
||||
**「非常に野心的で、言語の成熟度を飛躍的に高める可能性を秘めた素晴らしい計画」**
|
||||
|
||||
- 技術的に健全なアプローチ
|
||||
- pyo3経由のCPythonパーサー利用は最も確実
|
||||
- Differential Testingは極めて強力な手法
|
||||
|
||||
### Codex先生の評価
|
||||
**「Sound approach with strategic strength」**
|
||||
|
||||
- 関数単位フォールバックが実用的かつ効果的
|
||||
- Python 3.11固定でAST安定性確保
|
||||
- テレメトリー重視で継続的改善可能
|
||||
|
||||
## 🔑 統合された5つの核心戦略
|
||||
|
||||
### 1. 関数単位フォールバック(両エキスパート一致)
|
||||
```python
|
||||
def supported_function(): # → Nyash MIR/JIT
|
||||
return x + y
|
||||
|
||||
def unsupported_function(): # → CPython exec
|
||||
yield from generator # Phase 1では未対応
|
||||
```
|
||||
|
||||
### 2. Python 3.11固定
|
||||
- AST安定性確保(3.8 Constant統一、3.10 match/case、3.12位置情報)
|
||||
- `py_version`と`ast_format`をJSON IRに埋め込む
|
||||
|
||||
### 3. 意味論の正確な実装優先
|
||||
Phase 1必須要素(Codex先生強調):
|
||||
- LEGB + locals/freevars(スコーピング)
|
||||
- デフォルト引数の評価タイミング(定義時)
|
||||
- イテレータベースのfor文
|
||||
- for/else + while/else(Python独特)
|
||||
- Python真偽値判定(`__bool__` → `__len__`)
|
||||
- 短絡評価(and/or)
|
||||
|
||||
### 4. GIL管理の最小化
|
||||
```rust
|
||||
// GILは最小限に!
|
||||
let json_ast = Python::with_gil(|py| {
|
||||
py_helper.parse_to_json(py, code) // Python側でJSON生成
|
||||
})?;
|
||||
|
||||
// GIL外でRust処理
|
||||
let nyash_ast = py.allow_threads(|| {
|
||||
convert_json_to_nyash(json_ast)
|
||||
});
|
||||
```
|
||||
|
||||
### 5. テレメトリー基盤
|
||||
```bash
|
||||
[PythonParser] Module: example.py (Python 3.11)
|
||||
Functions: 10 total
|
||||
Compiled: 7 (70%)
|
||||
Fallback: 3 (30%)
|
||||
- async_function: unsupported node 'AsyncFunctionDef' at line 23
|
||||
```
|
||||
|
||||
## 📋 実装フェーズ(詳細版)
|
||||
|
||||
### Phase 0: 準備(1週間)
|
||||
- [ ] Python 3.11.9環境固定
|
||||
- [ ] テレメトリー基盤構築
|
||||
- [ ] Differential Testingフレームワーク
|
||||
- [ ] JSON IR仕様策定
|
||||
|
||||
### Phase 1: Core Subset(2週間)
|
||||
- [ ] pyo3統合(prepare_freethreaded_python)
|
||||
- [ ] 関数単位コンパイル判定器
|
||||
- [ ] 基本構文(def/if/for/while/return)
|
||||
- [ ] 意味論必須要素の実装
|
||||
- [ ] CPythonとの出力比較テスト
|
||||
|
||||
### Phase 2: Data Model(3週間)
|
||||
- [ ] 特殊メソッドマッピング
|
||||
- [ ] list/dict/tuple実装
|
||||
- [ ] 演算子オーバーロード
|
||||
|
||||
### Phase 3: Advanced Features(1ヶ月)
|
||||
- [ ] 例外処理(try/except)
|
||||
- [ ] with文、ジェネレータ
|
||||
- [ ] 内包表記、デコレータ
|
||||
|
||||
## 📊 成功の測定基準
|
||||
|
||||
### 定量的指標
|
||||
| 指標 | 目標 | 測定方法 |
|
||||
|------|------|----------|
|
||||
| カバレッジ率 | 70%以上 | コンパイル済み vs フォールバック関数 |
|
||||
| 性能向上 | 2-10倍 | 純Pythonループのベンチマーク |
|
||||
| バグ発見数 | 10+件/Phase | Differential Testing |
|
||||
| エコシステム | 1以上 | 動作する有名ライブラリ数 |
|
||||
|
||||
### マイルストーン
|
||||
- Phase 1: "Hello from Python in Nyash"が動作
|
||||
- Phase 2: scikit-learnの基本アルゴリズムが動作
|
||||
- Phase 3: FlaskのHello Worldが動作
|
||||
- Phase 4: PyPIトップ100の30%が基本動作
|
||||
|
||||
## 🚨 注意すべき意味論の違い(トップ5)
|
||||
|
||||
1. **制御フロー**: for/else, while/else
|
||||
2. **スコープ規則**: LEGB、global/nonlocal
|
||||
3. **数値演算**: / (true division) vs //
|
||||
4. **関数定義**: デフォルト引数は定義時評価
|
||||
5. **真偽値判定**: Pythonの__bool__/__len__ルール
|
||||
|
||||
## 🎉 期待されるインパクト
|
||||
|
||||
### 技術的成果
|
||||
- Pythonエコシステムの活用
|
||||
- Nyashパーサーの品質向上
|
||||
- 性能最適化の実証
|
||||
|
||||
### 戦略的価値
|
||||
- 言語成熟度の飛躍的向上
|
||||
- 開発者コミュニティの拡大
|
||||
- 実用アプリケーション開発の加速
|
||||
|
||||
## 📝 結論
|
||||
|
||||
PythonParserBoxは、単なる機能追加ではなく、**Nyash言語のテスト、デバッグ、エコシステム獲得を同時に加速させる極めて戦略的なプロジェクト**。
|
||||
|
||||
両エキスパートの技術的評価と具体的な実装指針により、実現可能性が確認され、明確な実装パスが定まった。
|
||||
|
||||
**「Everything is Box」哲学を、言語の壁を超えて実現する革命的な一歩。**
|
||||
@ -0,0 +1,263 @@
|
||||
# Testing - テスト計画
|
||||
|
||||
## 📋 概要
|
||||
|
||||
Python-Hakorune統合のテスト計画です。
|
||||
|
||||
## 🎯 テスト戦略
|
||||
|
||||
### テストレベル
|
||||
|
||||
1. **ユニットテスト**
|
||||
- 個別コンポーネントのテスト
|
||||
- 型変換のテスト
|
||||
- エラーハンドリングのテスト
|
||||
|
||||
2. **統合テスト**
|
||||
- Python-Hakorune連携テスト
|
||||
- FFI境界のテスト
|
||||
- GIL管理のテスト
|
||||
|
||||
3. **E2Eテスト**
|
||||
- 実用的なユースケーステスト
|
||||
- パフォーマンステスト
|
||||
- 互換性テスト
|
||||
|
||||
## 🧪 テストケース
|
||||
|
||||
### 1. 基本機能テスト
|
||||
|
||||
#### Python実行
|
||||
```hakorune
|
||||
// test_python_eval.hkr
|
||||
local py = new PyRuntimeBox()
|
||||
local result = py.eval("2 + 3")
|
||||
assert(result.to_int() == 5)
|
||||
```
|
||||
|
||||
#### モジュールインポート
|
||||
```hakorune
|
||||
// test_python_import.hkr
|
||||
local py = new PyRuntimeBox()
|
||||
local math = py.import("math")
|
||||
local pi = math.getattr("pi")
|
||||
assert(pi.to_string() == "3.14159...")
|
||||
```
|
||||
|
||||
#### オブジェクト操作
|
||||
```hakorune
|
||||
// test_python_object.hkr
|
||||
local py = new PyRuntimeBox()
|
||||
local obj = py.eval("{'x': 10, 'y': 20}")
|
||||
local x = obj.getattr("x")
|
||||
assert(x.to_int() == 10)
|
||||
```
|
||||
|
||||
### 2. 型変換テスト
|
||||
|
||||
```hakorune
|
||||
// test_type_conversion.hkr
|
||||
local py = new PyRuntimeBox()
|
||||
|
||||
// Bool変換
|
||||
local py_true = py.eval("True")
|
||||
assert(py_true.to_bool() == true)
|
||||
|
||||
// Int変換
|
||||
local py_int = py.eval("42")
|
||||
assert(py_int.to_int() == 42)
|
||||
|
||||
// String変換
|
||||
local py_str = py.eval("'hello'")
|
||||
assert(py_str.to_string() == "hello")
|
||||
|
||||
// List変換
|
||||
local py_list = py.eval("[1, 2, 3]")
|
||||
// ... ArrayBox への変換テスト
|
||||
```
|
||||
|
||||
### 3. エラーハンドリングテスト
|
||||
|
||||
```hakorune
|
||||
// test_python_error.hkr
|
||||
local py = new PyRuntimeBox()
|
||||
|
||||
// Python例外のキャッチ
|
||||
try {
|
||||
py.eval("1 / 0") // ZeroDivisionError
|
||||
} catch(e) {
|
||||
assert(e.contains("ZeroDivisionError"))
|
||||
}
|
||||
```
|
||||
|
||||
### 4. GIL管理テスト
|
||||
|
||||
```rust
|
||||
// tests/gil_management.rs
|
||||
#[test]
|
||||
fn test_gil_acquisition() {
|
||||
// GILの正しい獲得・解放
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_nested_gil_calls() {
|
||||
// ネストしたPython呼び出し
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_concurrent_access() {
|
||||
// 複数スレッドからのアクセス
|
||||
}
|
||||
```
|
||||
|
||||
### 5. メモリ管理テスト
|
||||
|
||||
```rust
|
||||
// tests/memory_management.rs
|
||||
#[test]
|
||||
fn test_no_memory_leak() {
|
||||
// メモリリークがないことを確認
|
||||
for _ in 0..1000 {
|
||||
let obj = create_python_object();
|
||||
drop(obj);
|
||||
}
|
||||
// メモリ使用量が増加していないことを確認
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_reference_counting() {
|
||||
// Pythonオブジェクトの参照カウント
|
||||
}
|
||||
```
|
||||
|
||||
### 6. パフォーマンステスト
|
||||
|
||||
```rust
|
||||
// benches/python_integration.rs
|
||||
#[bench]
|
||||
fn bench_python_call_overhead(b: &mut Bencher) {
|
||||
// Python呼び出しのオーバーヘッド測定
|
||||
}
|
||||
|
||||
#[bench]
|
||||
fn bench_type_conversion(b: &mut Bencher) {
|
||||
// 型変換のパフォーマンス測定
|
||||
}
|
||||
```
|
||||
|
||||
## 📊 テスト環境
|
||||
|
||||
### サポート対象
|
||||
|
||||
| 環境 | Python | Platform | 備考 |
|
||||
|------|--------|----------|------|
|
||||
| Linux | 3.8+ | x86_64 | 優先 |
|
||||
| macOS | 3.8+ | x86_64, arm64 | 優先 |
|
||||
| Windows | 3.8+ | x86_64 | 後段 |
|
||||
|
||||
### CI/CD統合
|
||||
|
||||
```yaml
|
||||
# .github/workflows/python-integration.yml
|
||||
name: Python Integration Tests
|
||||
|
||||
on: [push, pull_request]
|
||||
|
||||
jobs:
|
||||
test:
|
||||
strategy:
|
||||
matrix:
|
||||
os: [ubuntu-latest, macos-latest, windows-latest]
|
||||
python-version: ['3.8', '3.9', '3.10', '3.11']
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-python@v2
|
||||
with:
|
||||
python-version: ${{ matrix.python-version }}
|
||||
- name: Run tests
|
||||
run: cargo test --features python-integration
|
||||
```
|
||||
|
||||
## 🔧 テストツール
|
||||
|
||||
### 1. ユニットテスト
|
||||
- Cargo test framework
|
||||
- `#[test]` アトリビュート
|
||||
- アサーションマクロ
|
||||
|
||||
### 2. 統合テスト
|
||||
- `tests/` ディレクトリ
|
||||
- E2Eシナリオ
|
||||
|
||||
### 3. ベンチマーク
|
||||
- Criterion.rs
|
||||
- パフォーマンス回帰検出
|
||||
|
||||
### 4. メモリリークチェック
|
||||
- Valgrind
|
||||
- AddressSanitizer
|
||||
- Python memory profiler
|
||||
|
||||
## 📋 テストチェックリスト
|
||||
|
||||
### 基本機能
|
||||
- [ ] Python eval実行
|
||||
- [ ] モジュールインポート
|
||||
- [ ] オブジェクト属性アクセス
|
||||
- [ ] メソッド呼び出し
|
||||
- [ ] 例外ハンドリング
|
||||
|
||||
### 型変換
|
||||
- [ ] bool変換
|
||||
- [ ] int変換
|
||||
- [ ] string変換
|
||||
- [ ] list変換
|
||||
- [ ] dict変換
|
||||
- [ ] None処理
|
||||
|
||||
### FFI境界
|
||||
- [ ] Handle管理
|
||||
- [ ] TLV型変換
|
||||
- [ ] エラー伝搬
|
||||
|
||||
### GIL管理
|
||||
- [ ] GIL獲得・解放
|
||||
- [ ] ネスト呼び出し
|
||||
- [ ] マルチスレッド
|
||||
|
||||
### メモリ管理
|
||||
- [ ] 参照カウント
|
||||
- [ ] リーク検出
|
||||
- [ ] 循環参照処理
|
||||
|
||||
### パフォーマンス
|
||||
- [ ] 呼び出しオーバーヘッド
|
||||
- [ ] 型変換コスト
|
||||
- [ ] メモリ使用量
|
||||
|
||||
### プラットフォーム
|
||||
- [ ] Linux (x86_64)
|
||||
- [ ] macOS (x86_64)
|
||||
- [ ] macOS (arm64)
|
||||
- [ ] Windows (x86_64)
|
||||
|
||||
## ⚠️ 既知の課題
|
||||
|
||||
### 1. GILデッドロック
|
||||
- **問題**: ネスト呼び出しでデッドロックの可能性
|
||||
- **対策**: GIL獲得・解放のログ、タイムアウト検出
|
||||
|
||||
### 2. メモリリーク
|
||||
- **問題**: 参照カウントの管理ミス
|
||||
- **対策**: 定期的なリークチェック、自動テスト
|
||||
|
||||
### 3. プラットフォーム固有問題
|
||||
- **問題**: Python配布形態の違い
|
||||
- **対策**: CI環境での網羅的テスト
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- [Phase 20 メインREADME](../README.md)
|
||||
- [Core Implementation](../core-implementation/)
|
||||
- [Design Documents](../design/)
|
||||
@ -0,0 +1,201 @@
|
||||
# Transpiler - Python→Hakorune トランスパイラー
|
||||
|
||||
## 📋 概要
|
||||
|
||||
PythonコードをHakoruneコードに変換するトランスパイラーの設計・仕様です。
|
||||
|
||||
## 📁 ファイル一覧
|
||||
|
||||
- **[python-to-hakorune-spec.md](python-to-hakorune-spec.md)** - Python→Hakorune変換仕様
|
||||
|
||||
## 🎯 目的
|
||||
|
||||
### トランスパイラーの役割
|
||||
|
||||
1. **構文変換**
|
||||
- Python構文 → Hakorune構文
|
||||
- イディオム変換
|
||||
- スタイル変換
|
||||
|
||||
2. **型注釈の活用**
|
||||
- Pythonの型ヒント → Hakorune型
|
||||
- 型推論の補助
|
||||
- 型安全性の向上
|
||||
|
||||
3. **最適化**
|
||||
- Hakorune向け最適化
|
||||
- 不要なコードの削除
|
||||
- パフォーマンス改善
|
||||
|
||||
## 🔄 変換例
|
||||
|
||||
### 基本構文
|
||||
|
||||
```python
|
||||
# Python
|
||||
class Player:
|
||||
def __init__(self, name: str):
|
||||
self.name = name
|
||||
self.health = 100
|
||||
|
||||
def heal(self, amount: int):
|
||||
self.health += amount
|
||||
```
|
||||
|
||||
```hakorune
|
||||
// Hakorune
|
||||
box Player {
|
||||
name: StringBox
|
||||
health: IntegerBox
|
||||
|
||||
birth(name: StringBox) {
|
||||
me.name = name
|
||||
me.health = integer.create(100)
|
||||
}
|
||||
|
||||
heal(amount: IntegerBox) {
|
||||
me.health = me.health.add(amount)
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 制御構文
|
||||
|
||||
```python
|
||||
# Python
|
||||
for i in range(10):
|
||||
print(i)
|
||||
```
|
||||
|
||||
```hakorune
|
||||
// Hakorune
|
||||
local i = integer.create(0)
|
||||
loop(i.compare("<", 10)) {
|
||||
console.log(i.to_string())
|
||||
i = i.add(1)
|
||||
}
|
||||
```
|
||||
|
||||
### リスト操作
|
||||
|
||||
```python
|
||||
# Python
|
||||
items = [1, 2, 3]
|
||||
items.append(4)
|
||||
```
|
||||
|
||||
```hakorune
|
||||
// Hakorune
|
||||
local items = array.create()
|
||||
items.push(integer.create(1))
|
||||
items.push(integer.create(2))
|
||||
items.push(integer.create(3))
|
||||
items.push(integer.create(4))
|
||||
```
|
||||
|
||||
## 🏗️ アーキテクチャ
|
||||
|
||||
### トランスパイラーのフェーズ
|
||||
|
||||
1. **パース**
|
||||
- Pythonコードをパース
|
||||
- AST生成
|
||||
|
||||
2. **型推論**
|
||||
- 型ヒントの解析
|
||||
- 型推論の実行
|
||||
- 型情報の付与
|
||||
|
||||
3. **変換**
|
||||
- Python AST → Hakorune AST
|
||||
- イディオム変換
|
||||
- 最適化
|
||||
|
||||
4. **コード生成**
|
||||
- Hakorune ASTからコード生成
|
||||
- フォーマット適用
|
||||
- 出力
|
||||
|
||||
### 変換ルール
|
||||
|
||||
| Python構文 | Hakorune構文 | 備考 |
|
||||
|-----------|-------------|------|
|
||||
| `class` | `box` | クラス→Box |
|
||||
| `__init__` | `birth` | コンストラクタ |
|
||||
| `self` | `me` | 自己参照 |
|
||||
| `for ... in range()` | `loop(...)` | ループ |
|
||||
| `if ... elif ... else` | `if ... elif ... else` | 条件分岐 |
|
||||
| `def func()` | `func()` | 関数定義 |
|
||||
| `x = y` | `local x = y` | 変数宣言 |
|
||||
| `list[index]` | `list.get(index)` | 配列アクセス |
|
||||
| `dict[key]` | `dict.get(key)` | 辞書アクセス |
|
||||
|
||||
## 🔧 技術的課題
|
||||
|
||||
### 1. Python固有機能の扱い
|
||||
|
||||
#### サポートする機能
|
||||
- 基本データ型(int, str, list, dict)
|
||||
- クラス・メソッド
|
||||
- 制御構文(if, for, while)
|
||||
- 関数定義
|
||||
|
||||
#### サポートしない/制限する機能
|
||||
- メタクラス
|
||||
- デコレーター(一部のみ)
|
||||
- ジェネレーター
|
||||
- 内包表記(将来対応)
|
||||
- async/await(Phase 15以降)
|
||||
|
||||
### 2. 型推論
|
||||
|
||||
- 型ヒントを優先使用
|
||||
- 未注釈の場合は推論
|
||||
- 推論不可能な場合は`AnyBox`
|
||||
|
||||
### 3. ネーミング変換
|
||||
|
||||
- snake_case → camelCase(オプション)
|
||||
- Python予約語の回避
|
||||
- Hakorune予約語との衝突回避
|
||||
|
||||
## 📊 実装ステータス
|
||||
|
||||
| コンポーネント | ステータス | 備考 |
|
||||
|--------------|----------|------|
|
||||
| 変換仕様 | ✅ 完了 | 設計書完成 |
|
||||
| パーサー統合 | 📅 未実装 | - |
|
||||
| 型推論 | 📅 未実装 | - |
|
||||
| AST変換 | 📅 未実装 | - |
|
||||
| コード生成 | 📅 未実装 | - |
|
||||
|
||||
## 🎯 使用例
|
||||
|
||||
```bash
|
||||
# コマンドライン(将来)
|
||||
hakorune transpile script.py -o script.hkr
|
||||
|
||||
# プログラマティック(将来)
|
||||
local transpiler = new PythonTranspiler()
|
||||
local hakorune_code = transpiler.transpile(python_code)
|
||||
```
|
||||
|
||||
## ⚠️ 制限事項
|
||||
|
||||
1. **完全互換性は保証しない**
|
||||
- Pythonのすべての機能はサポートしない
|
||||
- 一部機能は手動移植が必要
|
||||
|
||||
2. **実行時動的機能**
|
||||
- `eval()`, `exec()` は変換不可
|
||||
- 動的属性追加は制限
|
||||
|
||||
3. **標準ライブラリ**
|
||||
- Python標準ライブラリは自動変換しない
|
||||
- Hakorune equivalent への手動マッピング必要
|
||||
|
||||
## 🔗 関連ドキュメント
|
||||
|
||||
- [Phase 20 メインREADME](../README.md)
|
||||
- [Parser Integration](../parser-integration/)
|
||||
- [Core Implementation](../core-implementation/)
|
||||
@ -0,0 +1,225 @@
|
||||
# Python → Nyashトランスパイラー機能
|
||||
~PythonParserBoxの応用による自動変換~
|
||||
|
||||
## 🎯 概要
|
||||
|
||||
PythonParserBoxでPython AST → Nyash ASTの変換ができるなら、それを**Nyashソースコードとして出力**できる!
|
||||
|
||||
## 🚀 実現可能な機能
|
||||
|
||||
### 1. Python → Nyashファイル変換
|
||||
```python
|
||||
# input.py
|
||||
def calculate(x, y):
|
||||
result = x * 2 + y
|
||||
return result
|
||||
|
||||
for i in range(10):
|
||||
print(calculate(i, 5))
|
||||
```
|
||||
|
||||
↓ 変換
|
||||
|
||||
```nyash
|
||||
# output.nyash
|
||||
function calculate(x, y) {
|
||||
local result
|
||||
result = x * 2 + y
|
||||
return result
|
||||
}
|
||||
|
||||
local i
|
||||
for i in range(0, 10) {
|
||||
print(calculate(i, 5))
|
||||
}
|
||||
```
|
||||
|
||||
### 2. 実装方法
|
||||
|
||||
```rust
|
||||
impl PythonParserBox {
|
||||
// Python → Nyashファイル出力
|
||||
pub fn transpile_to_file(&self, python_code: &str, output_path: &str) -> Result<(), String> {
|
||||
// 1. Python → JSON AST
|
||||
let json_ast = self.parse_to_json(python_code)?;
|
||||
|
||||
// 2. JSON AST → Nyash AST
|
||||
let nyash_ast = self.json_to_nyash_ast(&json_ast)?;
|
||||
|
||||
// 3. Nyash AST → Nyashソースコード
|
||||
let nyash_code = self.ast_to_nyash_source(&nyash_ast)?;
|
||||
|
||||
// 4. ファイルに出力
|
||||
std::fs::write(output_path, nyash_code)?;
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
// AST → Nyashソースコード生成
|
||||
fn ast_to_nyash_source(&self, ast: &NyashAst) -> Result<String, String> {
|
||||
let mut output = String::new();
|
||||
let formatter = NyashFormatter::new();
|
||||
|
||||
for item in &ast.items {
|
||||
formatter.format_item(item, &mut output)?;
|
||||
}
|
||||
|
||||
Ok(output)
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## 📋 使用例
|
||||
|
||||
### コマンドライン版
|
||||
```bash
|
||||
# PythonファイルをNyashに変換
|
||||
nyash-transpile input.py -o output.nyash
|
||||
|
||||
# 標準出力に出力
|
||||
nyash-transpile script.py
|
||||
|
||||
# 部分変換(サポートされる構文のみ)
|
||||
nyash-transpile --partial complex_script.py
|
||||
```
|
||||
|
||||
### Nyashスクリプト内での使用
|
||||
```nyash
|
||||
local transpiler = new PythonParserBox()
|
||||
|
||||
// Pythonコードを読み込み
|
||||
local python_code = FileBox.read("algorithm.py")
|
||||
|
||||
// Nyashに変換
|
||||
local nyash_code = transpiler.to_nyash_source(python_code)
|
||||
|
||||
// ファイルに保存
|
||||
FileBox.write("algorithm.nyash", nyash_code)
|
||||
|
||||
// または直接実行
|
||||
eval(nyash_code)
|
||||
```
|
||||
|
||||
## 🎨 変換マッピング例
|
||||
|
||||
### 基本構文
|
||||
| Python | Nyash |
|
||||
|--------|-------|
|
||||
| `def func():` | `function func() {` |
|
||||
| `if x > 0:` | `if (x > 0) {` |
|
||||
| `for i in range(10):` | `for i in range(0, 10) {` |
|
||||
| `while x < 10:` | `while (x < 10) {` |
|
||||
| `x = 5` | `local x; x = 5` または `x = 5`(スコープによる)|
|
||||
|
||||
### データ型
|
||||
| Python | Nyash |
|
||||
|--------|-------|
|
||||
| `x = 42` | `x = 42` |
|
||||
| `s = "hello"` | `s = "hello"` |
|
||||
| `lst = [1, 2, 3]` | `lst = new ArrayBox([1, 2, 3])` |
|
||||
| `d = {"a": 1}` | `d = new MapBox(); d.set("a", 1)` |
|
||||
|
||||
### 特殊なケース
|
||||
```python
|
||||
# Pythonのfor/else
|
||||
for i in items:
|
||||
if condition:
|
||||
break
|
||||
else:
|
||||
print("No break")
|
||||
```
|
||||
|
||||
```nyash
|
||||
# Nyashでの実装(フラグを使用)
|
||||
local broke = false
|
||||
for i in items {
|
||||
if (condition) {
|
||||
broke = true
|
||||
break
|
||||
}
|
||||
}
|
||||
if (not broke) {
|
||||
print("No break")
|
||||
}
|
||||
```
|
||||
|
||||
## 🌟 利点
|
||||
|
||||
### 1. 段階的移行支援
|
||||
- 既存のPythonプロジェクトを段階的にNyashに移行
|
||||
- 変換されたコードを手動で最適化可能
|
||||
|
||||
### 2. 学習ツールとして
|
||||
- PythonユーザーがNyash構文を学ぶ
|
||||
- 両言語の違いを理解
|
||||
|
||||
### 3. コード生成
|
||||
- Pythonで書いたアルゴリズムをNyashネイティブコードに
|
||||
- より高速な実行のための前処理
|
||||
|
||||
### 4. 逆方向変換の可能性
|
||||
- Nyash → Pythonも将来的に可能
|
||||
- 真のバイリンガル環境
|
||||
|
||||
## ⚠️ 制限事項と課題
|
||||
|
||||
### 1. 完全な互換性は不可能
|
||||
- Pythonの動的機能すべては変換できない
|
||||
- 一部の構文は手動調整が必要
|
||||
|
||||
### 2. 意味論の違い
|
||||
```python
|
||||
# Pythonのデフォルト引数(定義時評価)
|
||||
def f(x, lst=[]):
|
||||
lst.append(x)
|
||||
return lst
|
||||
```
|
||||
|
||||
```nyash
|
||||
// Nyashでは毎回新しいリスト(異なる挙動)
|
||||
function f(x, lst) {
|
||||
if (lst == null) {
|
||||
lst = new ArrayBox()
|
||||
}
|
||||
lst.push(x)
|
||||
return lst
|
||||
}
|
||||
```
|
||||
|
||||
### 3. サポートレベルの明示
|
||||
```nyash
|
||||
// 生成されたファイルのヘッダー
|
||||
// Generated from Python by Nyash Transpiler v1.0
|
||||
// Original file: script.py
|
||||
// Conversion rate: 85% (15/17 functions transpiled)
|
||||
// Manual review recommended for: async_func, generator_func
|
||||
```
|
||||
|
||||
## 📊 実装フェーズ
|
||||
|
||||
### Phase 1.5: 基本トランスパイラ(Phase 1と並行)
|
||||
- [ ] NyashFormatter実装(AST → ソースコード)
|
||||
- [ ] 基本構文の出力(def, if, for, while)
|
||||
- [ ] インデント管理
|
||||
- [ ] コメント保持(可能な範囲で)
|
||||
|
||||
### Phase 2.5: 高度な変換
|
||||
- [ ] クラス → Box変換
|
||||
- [ ] 特殊メソッド → Nyashメソッド
|
||||
- [ ] import文の処理
|
||||
|
||||
### Phase 3.5: ツール化
|
||||
- [ ] コマンドラインツール
|
||||
- [ ] VSCode拡張機能
|
||||
- [ ] オンライン変換ツール
|
||||
|
||||
## 🎉 期待される効果
|
||||
|
||||
1. **Pythonエコシステムの資産をNyashネイティブ化**
|
||||
2. **パフォーマンスクリティカルな部分をNyash/MIR/JITで高速化**
|
||||
3. **両言語間のシームレスな相互運用**
|
||||
4. **Nyashの採用障壁を大幅に下げる**
|
||||
|
||||
---
|
||||
|
||||
これは**PythonParserBoxの価値をさらに高める**素晴らしい応用です!
|
||||
Reference in New Issue
Block a user