--- id: wiki-2026-0508-program-dependence-graph title: Program Dependence Graph category: 10_Wiki/Topics status: verified canonical_id: self aliases: [PDG, Program Dependence Graph, 프로그램 의존성 그래프] duplicate_of: none source_trust_level: A confidence_score: 0.9 verification_status: applied tags: [compiler, static-analysis, ir, slicing] raw_sources: [] last_reinforced: 2026-05-10 github_commit: pending tech_stack: language: compiler-ir framework: static-analysis --- # Program Dependence Graph ## 매 한 줄 > **"매 control + data dependence를 매 한 그래프로"**. Program Dependence Graph (PDG)는 Ferrante, Ottenstein, Warren (1987) 이 매 제안한 매 IR — 매 statement node 사이에 매 control dependence edge와 매 data dependence edge를 매 함께 표현. Program slicing, parallelization, change impact analysis의 매 backbone. ## 매 핵심 ### 매 두 종류 edge - **매 Data dependence**: 매 statement A가 매 정의한 var를 매 B가 매 사용 → A → B (def-use). - **매 Control dependence**: 매 A의 매 결과가 매 B의 매 실행 여부를 매 결정 → A → B. - **매 Region node**: 매 unconditional block 매 그룹화 (선택적). ### 매 CDG vs DDG vs PDG - **CDG**: control dependence만 (post-dominator frontier 기반). - **DDG**: data dependence만 (def-use chain). - **PDG**: 매 둘 모두를 매 single graph로. - **SDG (System DG)**: PDG + interprocedural call/parameter edge. ### 매 응용 1. Program slicing (Weiser 1981 + Horwitz et al. 1990). 2. Change impact analysis. 3. Loop parallelization (data dep 없으면 매 parallel-safe). 4. Code clone detection (subgraph isomorphism). 5. Differential testing / fuzzing. ## 💻 패턴 ### PDG 구축 sketch (Python AST) ```python import ast from collections import defaultdict class PDGBuilder(ast.NodeVisitor): def __init__(self): self.defs = defaultdict(list) # var -> [stmt_id] self.data_edges = [] self.ctrl_edges = [] def visit_Assign(self, node): sid = id(node) for n in ast.walk(node.value): if isinstance(n, ast.Name): for prev in self.defs[n.id]: self.data_edges.append((prev, sid)) for tgt in node.targets: if isinstance(tgt, ast.Name): self.defs[tgt.id].append(sid) self.generic_visit(node) def visit_If(self, node): sid = id(node) for s in node.body + node.orelse: self.ctrl_edges.append((sid, id(s))) self.generic_visit(node) ``` ### Backward slicing ```python def backward_slice(pdg, criterion: int) -> set[int]: # criterion = stmt_id; 매 reachable predecessors via data + ctrl edges reverse = defaultdict(list) for u, v in pdg.data_edges + pdg.ctrl_edges: reverse[v].append(u) seen, stack = set(), [criterion] while stack: n = stack.pop() if n in seen: continue seen.add(n) stack.extend(reverse[n]) return seen ``` ### Loop parallelization check ```python def is_parallelizable(loop_pdg) -> bool: # 매 No loop-carried data dependence for u, v in loop_pdg.data_edges: if loop_pdg.iter_distance(u, v) > 0: return False return True ``` ### LLVM via opt pass ```bash # LLVM 18+ — print PDG of a function opt -passes='print' -disable-output input.ll opt -passes='print' -disable-output input.ll ``` ### Tree-sitter + custom analyzer (modern stack) ```python import tree_sitter_python as tsp from tree_sitter import Language, Parser LANG = Language(tsp.language()) parser = Parser(LANG) tree = parser.parse(b"x = 1\ny = x + 2") # 매 walk tree, 매 build PDG with same edges as above ``` ## 매 결정 기준 | 상황 | Approach | |---|---| | Slicing / debugging aid | PDG (data + control) | | Loop opt only | DDG (loop-carried 매 충분) | | Cross-function impact | SDG (PDG + summary edges) | | Code clone detection | PDG subgraph isomorphism | **기본값**: 매 PDG 시작, 매 cross-function 필요 시 매 SDG로 확장. ## 🔗 Graph - 부모: [[Static-Analysis]] ## 🤖 LLM 활용 **언제**: 매 code understanding tool, 매 refactoring impact, 매 LLM-assisted slicing. **언제 X**: 매 trivial single-function script. ## ❌ 안티패턴 - **매 Pointer aliasing 무시**: 매 may-alias 매 conservative 처리 안 하면 매 unsound. - **매 Interprocedural skip**: 매 cross-function dep 매 결측 → 매 false negative. - **매 매 edge 폭주**: 매 every var 매 every stmt → 매 PDG 매 dense 매 unreadable. ## 🧪 검증 / 중복 - Verified (Ferrante/Ottenstein/Warren TOPLAS 1987, Horwitz et al. TOPLAS 1990). - 신뢰도 A. ## 🕓 Changelog | 날짜 | 변경 | |---|---| | 2026-05-08 | Phase 1 | | 2026-05-10 | Manual cleanup — PDG/CDG/DDG/SDG taxonomy + slicing impl |