Size: a a a

Compiler Development

2021 March 30

PG

Per-Lorean Graph in Compiler Development
Дмитрий К
Есть разные соглашения о вызовах. Где-то вызываемая функция подчищает за собой (восстанавливает регистры), где-то вызывающая, где-то обе - каждая свои регистры. Для простоты интеграции с сишными либами и скорости работы с ними, имеет смысл использовать то же соглашение.
Это то да, но речь идёт о своей виртуальной машине где свои законы.
источник

ДК

Дмитрий К in Compiler Development
Per-Lorean Graph
Это то да, но речь идёт о своей виртуальной машине где свои законы.
И ей совсем не нужен интероп со внешними либами?
источник

Z

Zaner in Compiler Development
Per-Lorean Graph
Полагаю результат «скопировать» к себе вы можете только положив его на стэк.
если это именно реализация стековой вм, то я могу иметь произвольное количество регистров/переменных для этих целей
источник

IN

Ilya Neganov in Compiler Development
А вот в варианте с двумя стеками и отсутствием произвольной адресации - я правильно понимаю, что с параметрами функций придётся играть в ханойские башни? Ну то есть, например, если в функцию передаётся 10 параметров, а самым первым понадобился тот, что на дне, то девять сверху нужно кидать на другой стек или в память?
источник

к

кана in Compiler Development
вот у меня была такая же задача как раз, поэтому отказался от двух стеков

есть: a b c
нужно: a b c a
единственный вариант что я придумал

// a b c |
>r
// a b | c
>r
// a | b c
dup
// a a | b c
r>
// a a b | c
swap
// a b a | c
r>
// a b a c |
swap
// a b c a |



>r >r dup r> swap r> swap

просто чтобы достать первый аргумент (это при условии что в стеке после аргументов ничего нет)
источник

PS

Peter Sovietov in Compiler Development
кана
вот у меня была такая же задача как раз, поэтому отказался от двух стеков

есть: a b c
нужно: a b c a
единственный вариант что я придумал

// a b c |
>r
// a b | c
>r
// a | b c
dup
// a a | b c
r>
// a a b | c
swap
// a b a | c
r>
// a b a c |
swap
// a b c a |



>r >r dup r> swap r> swap

просто чтобы достать первый аргумент (это при условии что в стеке после аргументов ничего нет)
А ссылка выше для кого была? :)

>r over r> swap
источник

к

кана in Compiler Development
ну over это еще добавить надо, речь же не про forth была, а про в принципе два стека без произвольной адресации
источник

PS

Peter Sovietov in Compiler Development
Для произвольной адресации достаточно pick и roll.
источник

IN

Ilya Neganov in Compiler Development
Peter Sovietov
Для произвольной адресации достаточно pick и roll.
Логически - достаточно, но ведь этот pick будет работать за O(N) на ровном месте. Или я что-то упускаю?
источник
2021 March 31

PS

Peter Sovietov in Compiler Development
Ilya Neganov
Логически - достаточно, но ведь этот pick будет работать за O(N) на ровном месте. Или я что-то упускаю?
Необязательно, с roll и линейной логикой получается очень даже интересно. Вспомните классику: https://web.archive.org/web/20200610223140/http://home.pipeline.com/~hbaker1/ForthStack.html
источник

IN

Ilya Neganov in Compiler Development
О, спасибо, почитаю! Не видел эту статью.
источник

K

Kir in Compiler Development
кана
что почитать про то, как генерировать байткод стекового языка для функциональных языков?

написал небольшую вм-ку для стекового языка, вручную переписал функцию, но абсолютно 0 понимания как это сгенерировать. Понимаю как компилировать выражения без переменных, но когда речь доходит до выражений с переменными, которые уже на стеке, то теряюсь


; fib(N) -> fib(N, 1, 1).
; fib(0, _, B) -> B;
; fib(N, A, B) -> fib(N-1, B, A+B).

; A B | C D -- это дата стек [A, B] и return stack [D, C]

fib/1:           ; N |
fib/1[0]:        ; N |
 lit 1          ; N 1 |
 lit 1          ; N 1 1 |
 call fib/3     ; fib/3(N, 1, 1) |
 ret            ; fib/3(N, 1, 1) |

fib/3:
fib/3[0]:        ; N A B |
 rpush          ; N A | B
 rpush          ; N | A B
 dup            ; N N | A B
 rpop           ; N N A | B
 swap           ; N A N | B
 rpop           ; N A N B |
 swap           ; N A B N |
 lit 0          ; N A B N 0 |
 eq             ; N A B [0 или 1] |
 jmpf fib/3[1]  ; N A B
 rpush          ; N A | B
 drop           ; N | B
 drop           ; | B
 rpop           ; B |
 ret            ; B |
fib/3[1]:        ; N A B |
 rpush          ; N A | B
 rpush          ; N | A B
 lit 1          ; N 1 | A B
 sub            ; (N-1) | A B
 rpop           ; (N-1) A | B
 rpop           ; (N-1) A B |
 swap           ; (N-1) B A |
 rpush          ; (N-1) B | A
 dup            ; (N-1) B B | A
 rpop           ; (N-1) B B A |
 swap           ; (N-1) B A B |
 add            ; (N-1) B (A+B) |
 jmp fib/3      ; (N-1) B (A+B) |


rpush/rpop - это return stack, перекидывание из основно стека во вторичный и обратно
источник

K

Kir in Compiler Development
Хотя, оно для компиляции в конкатенативные языки, так что не всякий стековый можно адаптировать
источник

Y

Yury in Compiler Development
источник

M

MrSmith in Compiler Development
Да я читал. Мне их позиция про клиентов тока не очень
источник

M

MrSmith in Compiler Development
Я так и не понял Research с клиентами это как
источник

M

MrSmith in Compiler Development
источник

M

MrSmith in Compiler Development
Смотрю уже минут 5 на граф все понять не могу в чем принципиально от ast отличается исключая направления стрелок и наличия спец блоков
источник

s

suhr in Compiler Development
Хотя бы тем, что это не дерево.
источник

s

suhr in Compiler Development
https://darksi.de/d.sea-of-nodes/ — вот это куда более подробная статья.
источник