open ERTL
let lookup uses r =
  try
    Register.Map.find r uses
  with Not_found ->
    0
let count r uses =
  Register.Map.add r (lookup uses r + 1) uses
let examine_instruction _ instruction uses =
  match instruction with
  | INewFrame _
  | IDeleteFrame _
  | ICall _
  | ITailCall _
  | IGoto _
  | IReturn _ ->
      uses
  | IGetHwReg (r, _, _)
  | ISetHwReg (_, r, _)
  | IGetStack (r, _, _)
  | ISetStack (_, r, _)
  | IConst (r, _, _)
  | IGetGlobal (r, _, _)
  | ISetGlobal (_, r, _)
  | IUnBranch (_, r, _, _) ->
      count r uses
  | IUnOp (_, r1, r2, _)
  | ILoad (r1, r2, _, _)
  | IStore (r1, _, r2, _)
  | IBinBranch (_, r1, r2, _, _) ->
      count r1 (count r2 uses)
  | IBinOp (_, r, r1, r2, _) ->
      count r (count r1 (count r2 uses))
let examine_procedure proc =
  let uses =
    Label.Map.fold examine_instruction proc.graph Register.Map.empty
  in
  lookup uses