Register Allocation

  • 어떤 register에 어떤 값을 할당할지 결정하는 것
  • Register allocation
    • 프로그램의 각 포인트에 레지스터 내에 존재할 변수들의 집합을 고르는 것
  • Register assignment
    • 어떤 변수 하나가 존재할 특정 레지스터를 고르는 것
  • 레지스터의 optimal assignment를 찾는 것은 NP-complete 문제
    • Computation 순서에 따라 레지스터가 적게 필요할 수도 있는데, 가장 적은 할당을 찾는 것은 어렵다 (Graph coloring problem으로 환원될 수 있음)
    • 따라서 보통 Brute force로 구현하며, Chaitin’s Algorithm이 대표적

Chaitin’s Alogrithm

Live Variables

  • 어떤 변수 의 값이 flow graph에서 시작지점 부터 시작하여 나오는 어떤 path에서 사용되면 변수 가 특정 포인트 에서 살아있다(live)라고 한다
  • Interference Graph를 만들기 위해서는 프로그램의 모든 포인트에서 살아있는 변수들을 찾는 것이 중요하다
    • 두 개의 변수가 함께 살아있는 경우, 이 둘은 동일한 physical register에 allocation될 수 없음 (==interfere함)
  • Data flow analysis technique을 이용해 찾는다

Interference Graph

  • Interference
    • 변수 a와 b가 동일한 레지스터에 할당될 수 없는 상황
  • Interference graph 에 등장하는 노드들은 temporaries 혹은 symbolic registers 를 나타낸다
  • a와 b를 연결하는 edge가 존재 iff a와 b 사이의 interference가 존재한다
    • 어떤 변수가 미래에 필요한 데이터를 그 시점에 가지고 있으면 해당 변수가 살아있다고 한다
    • Non-move instruction(copy가 아닌 instruction)이 블록 n 내에서 a를 정의하는 경우(a:=…), 모든 에 대해 (a, b) edge를 더한다
    • Move instruction이 c를 a로 옮긴다면(a:=c), 모든 (a, b)를 더한다
    • 살아있는 변수끼리 연결하되, move instruction에 대해서는 예외가 있다 정도로 생각할 수 있을 듯 하다
  • 아래 예시

Graph Coloring

  • K-coloring problem을 아래와 같이 생각 가능
    • Color의 갯수: 레지스터의 갯수 K
    • Vertex: 변수
  • 연결된(Interfere하는) 변수끼리는 같은 color(레지스터)를 할당받으면 안되는 문제이다
    • 즉 graph coloring 문제로 환원 가능하며, 이것이 NP 문제이기 때문에 레지스터 할당 문제는 NP 문제이다
    • 풀기 위해서는 linear approximation algorithm을 이용한다
  • K-coloring 문제 풀이에 실패할 경우, 일부 변수는 메모리에 저장해야 하는데 이를 spiling이라 한다

Simplification

  • G에서 m개의 노드가 K 개보다 적은 이웃을 가지고 있다고 가정하자
  • G-{m}이 K-colorable하다면 G도 마찬가지

Coloring by Simplification

  1. Build) interference graph G를 만든다
  2. Simplify) K보다 더 적은 수의 이웃을 가진 노드를 삭제하고 스택에 넣는다
  3. Spill) Degree가 K보다 큰 노드들만 남았다면, 몇개의 노드를 spilling 표시하고 스택에 넣은 뒤 다시 simplification을 진행한다. (아니면 계속 Simplify 하면 됨)
  4. Select) 스택에서 하나씩 노드를 꺼내 그래프를 재구성하되, spilling 표시가 있는 경우 사용 가능한 color가 있는지 확인하고 없는 경우 실제로 spill 대상으로 표기한다
  5. Start Over) 실제 spill 대상이 있으면 코드를 수정하고 다시 1번으로 간다

1. At the Beginning

Simplification

  • Degree가 4보다 작은 것들을 스택에 넣는다 모든 노드가 K보다 많은 이웃 수를 가지는 Complete graph가 나왔다 Spilling 그랬더니 잘 됐다. 다시 simplification을 진행

스필링 뒤에 reconstruction을 해보고, 컬러링이 안되는 t6은 실제로 스필이라 판단하고 옆과 같이 스필링을 포함한 코드를 재 작성한다 무엇을 spill하는가에 따라 성능이 다른데, 이건 운에 의해 결정된다

Spilling 없이 Simplification에 성공했다

스택을 사용하는 이유: 복잡도가 높은 것에서 낮은 것 순서로 색칠해야 색칠에 성공할 확률이 높기 때문.