Подтвердить что ты не робот

Прагматика типизированных промежуточных языков

Одной из тенденций в компиляции является использование типизированных промежуточных языков. Haskell ghc с его промежуточным языком core, вариантом системы F-omega, является примером этой архитектуры [1]. Другим является LLVM, который имеет типичный промежуточный язык в своем ядре [2]. Преимущество этого подхода заключается в том, что ошибки в преобразованиях, составляющих части генератора кода, могут быть обнаружены на ранней стадии. Кроме того, информация о типе может использоваться во время оптимизации и генерации кода.

Для эффективности типизированные IR проверяются по типу, а не выводятся их типы. Чтобы быстро выполнять проверки типов, каждая переменная и каждое связующее несут типы для простой проверки типов.

Однако многие преобразования в конвейере компилятора могут вводить новые переменные. Например, преобразование нормализации K(.) может преобразовать приложение

M(N)

в выражение типа

let x = K(M) in
let y = K(N) in x(y)

Вопрос. Интересно, как компиляторы справляются с проблемой предоставления типов новым переменные. Повторяются ли они в примере выше K(M) и K(N)? Разве это не занимает много времени? И требуется ли окружающая среда? Используют ли они карты из узлов AST для ввода информации, чтобы избежать повторной проверки типов?


4b9b3361