4e12e14b85
* GNUmakefile (mini-mes): Add include. * mlibc.c: New file: libc bits for GNUC -nostdlib. * mstart.c: New file: _start for GNUC -nostdlib. * scaffold/cons-mes.c: Remove GNUC libc bits. * scaffold/m.c: Likewise. * scaffold/mini-mes.c: Likewise. * scaffold/t.c: Likewise. * scaffold/tiny-mes.c: Litkewise. * module/language/c99/compiler.mes (libc, i386:libc): Remove. * module/language/c99/compiler.scm * module/mes/libc-i386.mes: Remove assembly bits. (_start): New function. * module/mes/libc-i386.scm: Export it, remove assembly exports. * module/mes/as-i386.mes: New file: assembly bits from libc-i386.mes. * module/mes/as-i386.scm: New file: export them. * module/mes/libc.mes (libc,_start): New functions from compiler.mes. * module/mes/libc.scm: Export them.
224 lines
3.8 KiB
Scheme
224 lines
3.8 KiB
Scheme
;;; -*-scheme-*-
|
|
|
|
;;; Mes --- Maxwell Equations of Software
|
|
;;; Copyright © 2016,2017 Jan Nieuwenhuizen <janneke@gnu.org>
|
|
;;;
|
|
;;; This file is part of Mes.
|
|
;;;
|
|
;;; Mes is free software; you can redistribute it and/or modify it
|
|
;;; under the terms of the GNU General Public License as published by
|
|
;;; the Free Software Foundation; either version 3 of the License, or (at
|
|
;;; your option) any later version.
|
|
;;;
|
|
;;; Mes is distributed in the hope that it will be useful, but
|
|
;;; WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
;;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
;;; GNU General Public License for more details.
|
|
;;;
|
|
;;; You should have received a copy of the GNU General Public License
|
|
;;; along with Mes. If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
;;; Commentary:
|
|
|
|
;;; libc.mes provides a minimal portable C library for mescc.
|
|
|
|
;;; Code:
|
|
|
|
(cond-expand
|
|
(guile-2)
|
|
(guile)
|
|
(mes
|
|
(mes-use-module (nyacc lang c99 parser))
|
|
(mes-use-module (mes libc-i386))))
|
|
|
|
(define _start
|
|
(let* ((argc-argv (i386:_start))
|
|
(ast (with-input-from-string
|
|
(string-append "int _start () {int i;asm(\"" argc-argv "\");i=main ();exit (i);}")
|
|
parse-c99)))
|
|
ast))
|
|
|
|
(define strlen
|
|
(let* ((ast (with-input-from-string
|
|
"
|
|
int
|
|
strlen (char const* s)
|
|
{
|
|
int i = 0;
|
|
while (s[i]) i++;
|
|
return i;
|
|
}
|
|
"
|
|
;;paredit:"
|
|
parse-c99)))
|
|
ast))
|
|
|
|
(define getchar
|
|
(let* ((ast (with-input-from-string
|
|
"
|
|
int g_stdin;
|
|
int
|
|
getchar ()
|
|
{
|
|
char c;
|
|
int r = read (g_stdin, &c, 1);
|
|
//int r = read (0, &c, 1);
|
|
if (r < 1) return -1;
|
|
return c;
|
|
}
|
|
"
|
|
;;paredit:"
|
|
parse-c99)))
|
|
ast))
|
|
|
|
(define putchar
|
|
(let* ((ast (with-input-from-string
|
|
"
|
|
int
|
|
putchar (int c)
|
|
{
|
|
//write (STDOUT, s, strlen (s));
|
|
//int i = write (STDOUT, s, strlen (s));
|
|
write (1, (char*)&c, 1);
|
|
return 0;
|
|
}
|
|
"
|
|
;;paredit:"
|
|
parse-c99)))
|
|
ast))
|
|
|
|
(define eputs
|
|
(let* ((ast (with-input-from-string
|
|
"
|
|
int
|
|
eputs (char const* s)
|
|
{
|
|
//write (STDERR, s, strlen (s));
|
|
//write (2, s, strlen (s));
|
|
int i = strlen (s);
|
|
write (2, s, i);
|
|
return 0;
|
|
}
|
|
"
|
|
;;paredit:"
|
|
parse-c99)))
|
|
ast))
|
|
|
|
(define fputs
|
|
(let* ((ast (with-input-from-string
|
|
"
|
|
int
|
|
fputs (char const* s, int fd)
|
|
{
|
|
int i = strlen (s);
|
|
write (fd, s, i);
|
|
return 0;
|
|
}
|
|
"
|
|
;;paredit:"
|
|
parse-c99)))
|
|
ast))
|
|
|
|
(define puts
|
|
(let* ((ast (with-input-from-string
|
|
"
|
|
int
|
|
puts (char const* s)
|
|
{
|
|
//write (STDOUT, s, strlen (s));
|
|
//int i = write (STDOUT, s, strlen (s));
|
|
int i = strlen (s);
|
|
write (1, s, i);
|
|
return 0;
|
|
}
|
|
"
|
|
;;paredit:"
|
|
parse-c99)))
|
|
ast))
|
|
|
|
(define strcmp
|
|
(let* ((ast (with-input-from-string
|
|
"
|
|
int
|
|
strcmp (char const* a, char const* b)
|
|
{
|
|
while (*a && *b && *a == *b)
|
|
{
|
|
a++;b++;
|
|
}
|
|
return *a - *b;
|
|
}
|
|
"
|
|
;;paredit:"
|
|
parse-c99)))
|
|
ast))
|
|
|
|
(define itoa
|
|
(let* ((ast (with-input-from-string
|
|
"
|
|
char itoa_buf[10];
|
|
|
|
char const*
|
|
itoa (int x)
|
|
{
|
|
//static char itoa_buf[10];
|
|
//char *p = buf+9;
|
|
char *p = itoa_buf;
|
|
p += 9;
|
|
*p-- = 0;
|
|
|
|
//int sign = x < 0;
|
|
int sign;
|
|
sign = x < 0;
|
|
if (sign)
|
|
x = -x;
|
|
|
|
do
|
|
{
|
|
*p-- = '0' + (x % 10);
|
|
x = x / 10;
|
|
} while (x);
|
|
|
|
if (sign)
|
|
*p-- = '-';
|
|
|
|
return p+1;
|
|
}
|
|
"
|
|
;;paredit:"
|
|
parse-c99)))
|
|
ast))
|
|
|
|
;;;;
|
|
|
|
(define assert_fail
|
|
(let* ((ast (with-input-from-string
|
|
"
|
|
void
|
|
assert_fail (char* s)
|
|
{
|
|
eputs (\"assert fail: \");
|
|
eputs (s);
|
|
eputs (\"\n\");
|
|
//*((int*)0) = 0;
|
|
char *fail = s;
|
|
fail = 0;
|
|
*fail = 0;
|
|
}
|
|
"
|
|
;;paredit:"
|
|
parse-c99)))
|
|
ast))
|
|
|
|
(define libc
|
|
(list
|
|
strlen
|
|
getchar
|
|
putchar
|
|
eputs
|
|
fputs
|
|
puts
|
|
strcmp
|
|
itoa
|
|
assert_fail))
|