Job System移行 Step2-3: ポリゴン分割のSoA/Job System + Burst化 - #35
Merged
Conversation
- DecalMeshの頂点/インデックスバッファ構築をMesh.AllocateWritableMeshData / ApplyAndDisposeWritableMeshDataへ移行し、複数回のSet*呼び出しを単一のApplyに置き換え - スキンメッシュはPosition/Normal/Tangent=stream 0、TexCoord0=stream 1、 BlendWeight/BlendIndices=stream 2の3ストリーム構成(Unityの必須制約。 単一ストリームだとSetVertexBufferParamsが拒否しメッシュが崩壊する) - スキニングウェイトはboneWeightsプロパティではなく頂点属性として格納し、 代入時の頂点バッファ再レイアウトを排除 - Mesh.RecalculateTangents()を廃止し、DecalMeshTangentCalculator(Lengyel法)を新設。 ワーカースレッド内で追記分のみ差分計算するため、メインスレッドのコストが消え デカール積み重ね時も計算量が頂点総数に比例しない - インデックスフォーマットを頂点数に応じてUInt16/UInt32自動選択 (旧実装は暗黙のUInt16固定で65,535頂点超で壊れる潜在バグがあった) - 計測結果(エディタMono・入力8191/生存4849ポリゴン・2回目Launch): アップロード最大0.11→0.09ms、タンジェント計算のワーカー追加分0.08ms、 ワーカー合計は同水準(9.63ms vs 8.65ms)でリグレッションなし Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
デカール分割処理(skinning/broadphase/clip/build)をThreadPoolワーカー1本から Unity Job System(IJobParallelFor)へ移行。段階式のため今回はBurst無効で、 Burst有効化(依存追加)は次ステップ3cに分離。設計基準はUnity 6.x前提。 ## データモデル - ConvexPolygon(class)/Line/BroadPhaseConvexPolygonsDetectionを廃止し、 blittableなSoA(ReceiverConvexPolygonsMesh: NativeArray<float3>等)へ再設計 - Component参照を全種別横断のグローバルcomponentIndexに統一(ジョブからマネージド参照を排除) - per-vertexのworld normalを除去(出力に不使用のデッドデータ)、Lineも廃止し エッジはリング隣接からオンザフライ計算 → per-vertex 252B→68Bでメモリ削減 ## ジョブチェーン - SkinningBroadPhaseJob(三角形単位・並列): スキニング+faceNormal+broadphaseカリング - ConvexPolygonClipJob(三角形単位・並列): 6平面クリップ(SplitAndRemoveByPlane移植) - DecalMeshBuildJob(serial・オフメイン): fan展開+UV+zOffset+タンジェント計算 - コルーチンのフラグポーリングを2段JobHandle.IsCompletedポーリングへ置換 ## 基盤・その他 - package.json: unity 2020.3→6000.0、com.unity.mathematics依存追加 - 受け消滅時のuse-after-free対策(InUseピン)。追記がジョブ完了後のmainスレッドなので 旧ロールバック機構は不要化し削除 - 差分テストで移植の数値等価性を検証(距離・クリップ・タンジェント。旧削除後スタンドアロン化) ## 計測(大きめスキンメッシュ・2回目Launch) - エディタMono: ワーカー計算 9.63ms→1.98ms (約4.9x、Burst無しの並列化のみ) - 実機Pixel 8a(IL2CPP) steady: ワーカー計算 約2.3ms。見た目差分なし・リグレッションなし Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Step 3a(Job並列化・Burst無効)の上に、3ジョブへ[BurstCompile]を付与しBurstを有効化。 - SkinningBroadPhaseJob / ConvexPolygonClipJob / DecalMeshBuildJob に [BurstCompile] - package.json に com.unity.burst 依存、asmdef に Unity.Burst 参照を追加 計測(probe付き有効A/B、Demo_Benchmark、同一ワークロード確認済み): - 実機 Pixel 8a / IL2CPP steady: worker 7.56ms → 4.80ms (~1.58x。clip 1.48x / build 1.65x) - エディタ Mono steady: worker 2.02ms → 0.32ms (6.3x。Monoベースライン比のため実機より大きく出る) - FloatMode未指定(IEEE厳密)で結果はBurst無効と一致、見た目不変 Burst稼働は [BurstDiscard] probe で確定(ONビルド=YES / OFFビルド=NO)。 Burst AOT無効化は Project Settings > Burst AOT Settings で行う(Jobsメニューのトグルは エディタJITのみでAOTビルドに効かない)点に注意。 Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Demo03のエージングテスト(毎回別デカール)は計測を濁らせるため、決定論的な ベンチマークを追加。同一受け(バインドポーズ固定)に同一デカールを、各Launch前に リセットして繰り返すので、全Launchが同一のclip/build仕事量になり Burst on/off を 厳密比較できる。 - Demo_Benchmark シーン(最小構成、実行時にSystem/カメラ/ライト/受けを自動生成) - AirStickerBenchmark.cs: 自己完結ベンチ + [BurstDiscard] による Burst稼働 probe ([AirSticker][Bench] Burst active: YES/NO をログ) - 再生と同時に6回Launch自動実行、launch #2+ を steady-state として読む Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Codex CLIによるセルフレビューで検出した3件を修正(再レビューで指摘なしを確認)。 - (blocker) AirStickerSystem.OnDestroy がジョブ実行中にNativeArrayを破棄しuse-after-free: DecalMeshJobPipeline._lastScheduledHandle を追加し Dispose() 先頭で Complete。 OnDestroy は pipeline.Dispose(=ジョブ完了) → pool.DisposeAll の順で source も安全に破棄。 - (major) 部分フィルで未初期化SoAが登録される: BuildFromReceiverObject 末尾で _writeTriangleCursor == triangleCount を検証し、不一致なら result.Dispose してキャンセル。 - (major) componentIndex不整合(meshFilter index vs meshRenderer基準のComponentByIndex): メッシュ経路をレンダラ駆動化(FillFromMeshRenderers/GetNumPolygonsFromMeshRenderers)し count/fillを一致、meshFilters引数を除去。 Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
# Conflicts: # Assets/AirSticker/Runtime/Scripts/Core/DecalMesh.cs # JobSystemMigrationPlan.md
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
概要
デカール生成パイプライン(skinning / broadphase / clip / build)を ThreadPool ワーカー1本から Unity Job System(SoA + IJobParallelFor)+ Burst へ移行します。Job System 移行計画(
JobSystemMigrationPlan.md)の Step 2・Step 3 を含みます(Step 0/1 は #32/#33 でマージ済み)。含まれるコミット
8d125c1,24d51b8): メッシュアップロードの MeshData API 化、タンジェント計算のワーカー移動f1ea701): ポリゴン分割を SoA + Unity Job System 化(Burst 無効)adcac77): ジョブの Burst 有効化b05068f): クリーン計測用シーン + Burst 稼働 probe主な変更(Step 3)
ConvexPolygon(class)/Line/BroadPhaseConvexPolygonsDetectionを廃止し、blittable な SoA(ReceiverConvexPolygonsMesh:NativeArray<float3>等)へ再設計Component参照を全種別横断のグローバル componentIndex に統一(ジョブからマネージド参照を排除)Line廃止でエッジをオンザフライ計算 → per-vertex 252B→68B でメモリ削減JobHandle.IsCompletedポーリングへ置換ReceiverConvexPolygonsMesh.InUseピン)計測(実機 Pixel 8a / IL2CPP、probe 付き有効 A/B)
FloatMode未指定(IEEE 厳密)で結果は Burst 無効と一致、デモの見た目は不変。Demo_Benchmarkの[BurstDiscard]probe で確定(ON ビルド=YES / OFF ビルド=NO)。Burst AOT 無効化は Project Settings > Burst AOT Settings(Jobs メニューのトグルはエディタ JIT のみで AOT ビルドに効かない)。破壊的変更(→ メジャー 2.0.0 相当。バージョン bump は 3d で対応)
com.unity.mathematics/com.unity.burst(本プロジェクトは元々推移的に保持)ConvexPolygon/Line/BroadPhaseConvexPolygonsDetection/ConvexPolygonInfo検証
Demo_Benchmarkは決定論的クリーン計測(同一受け・バインドポーズ固定・同一デカール・各 Launch 前にリセット)を提供。フォローアップ(このPRに含まない)
package.jsonを 2.0.0 へ、残課題 Feature/doc #2(Demo03 の計測ログ常時 ON)/Feature/gc pools #3(AirStickerPerformanceLogの扱い)、README / README_DEVELOPERS(EN/JA)/ CHANGELOG 更新。🤖 Generated with Claude Code