Схема компиляции с использованием Gambit-C - PullRequest
1 голос
/ 07 ноября 2019

Я использую Ubuntu 18.04 и установил gambc для выполнения скриптов Scheme. gsi отлично работает и может интерпретировать любой файл, который я предоставляю, а REPL также работает как положено.

К сожалению, я не могу понять, как использовать gsc.

http://gambitscheme.org/wiki/index.php/A_Tour_of_Scheme_in_Gambit дает мало информации о том, как использовать gsc для компиляции программы, man gsc больше о gsi и не охватывает все доступные опции (например, опции -o и -cне упоминается на странице man), и все другие источники, которые я смог найти, не сработали для меня.

Позвольте мне подробнее остановиться на этой последней части:

$ cat hello.scm
;#!/usr/local/bin/gsi-script -:d0
;
(define hello-world
        (lambda ()
                (begin (write `Hello-World) (newline) (hello-world))))

(define (main)
        (hello-world))

Затем

$ gsc hello.scm
$ ls
hello.o1  hello.scm
$ ./hello.o1
Segmentation fault (core dumped)

Сбой, как и

$ gsc -c hello.scm
$ ls
hello.c hello.scm
$ gcc -o hello hello.c
/usr/lib/gcc/x86_64-linux-gnu/7/../../../x86_64-linux-gnu/Scrt1.o : In function « _start » :
(.text+0x20) : Undefined reference to « main »
/tmp/ccnDUVi0.o : [30 more lines]
collect2: error: ld returned 1 exit status
  • Выполнение
/* File: "m1.c" */
int power_of_2 (int x) { return 1<<x; }

; File: "m2.scm"
(c-declare "extern int power_of_2 ();")
(define pow2 (c-lambda (int) int "power_of_2"))
(define (twice x) (cons x x))

; File: "m3.scm"
(write (map twice (map pow2 '(1 2 3 4)))) (newline)

$ gsc -c m2.scm        # create m2.c (note: .scm is optional)
$ gsc -c m3.scm        # create m3.c (note: .scm is optional)
$ gsc -link m2.c m3.c  # create the incremental link file m3_.c

$ gsc -obj m1.c m2.c m3.c m3_.c
m1.c:
m2.c:
m3.c:
m3_.c:
$ gcc m1.o m2.o m3.o m3_.o -lgambit -lm -ldl -lutil
$ ./a.out
((2 . 2) (4 . 4) (8 . 8) (16 . 16))

, как предложено http://www.iro.umontreal.ca/~gambit/doc/gambit.html потерпел неудачу в $ gsc -obj m1.c m2.c m3.c m3_.c, сказав, что m3_.c не был определен, и даже игнорируя это, он снова потерпел неудачу в $ gcc m1.o m2.o m3.o m3_.o -lgambit -lm -ldl -lutil с жалобой на то, что -lgambit не был определен. Однако в этом документе объясняется использование опций -o и -c.

Я остановлюсь здесь, но я попытался следовать двум другим учебникам, но ни одна из них не сработала, и я больше не могу их найти.

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

Ответы [ 2 ]

1 голос
/ 07 ноября 2019

В части 3. Компилятор Gambit Scheme упомянутого вами Руководства по Gambit содержит очень информативное описание компилятора и всех его опций.

Если вы хотите скомпилировать исходный файл Scheme hello.scm в исполняемую программу, попробуйте:

gsc -exe hello

Вам не нужно указывать расширение файла. Результирующий исполняемый файл будет иметь то же имя, что и исходный файл, без расширения (поэтому hello.scm -> hello).

0 голосов
/ 07 ноября 2019

Вот то, что я выяснил, в случае, если кто-то еще столкнется с той же проблемой.

  • Несмотря на то, что на странице man она не отображается, опция -exe позволяет создать исполняемый файл.
$ gsc -exe hello.scm
$ ./hello
Hello, World!

Его использование объясняется в Gambit, переносимой реализации схемы , но не в разделе «Компилятор схемы Gambit»! Вместо этого вам придется вернуться к предыдущему абзацу.

  • Как указывал @rsm, $ gsc -exe hello также работает: даже если hello уже скомпилирован, .scm не будетнеобходимо, но есть определенная последовательность команд, которая приведет к сбою этой команды.

Это работает (h правильно скомпилировано):

$ ls
hello.scm
$ gsc -exe -o h hello
$ ls
h  hello.scm

Это работает (h правильно скомпилирован из hello.scm, а не из hello):

$ ls
hello  hello.scm
$ gsc -exe -o h hello
$ ls
h  hello  hello.scm

Но это не удается:

$ ls
hello.scm
$ gsc -c hello.scm
$ ls
hello.c  hello.scm
$ gsc -exe -o h hello
hello_.o:(.data.rel+0x110) : undefined reference to « ____20_hello »
collect2: error: ld returned 1 exit status
*** ERROR IN ##main -- C link failed while linking "/home/hello_.o"
$ ls
hello_.c  hello.c  hello_.o  hello.scm

В случае, когда файл .c стакое же имя уже существует, следует использовать расширение .scm. Хотя в сообщении предлагается ошибка компоновщика, корень проблемы, насколько я могу судить, состоит в том, что файлы C имеют преимущество перед файлами Scheme, когда расширение не указано, что является неожиданным для компилятора Scheme ...

...