From 11d240e756f48c28664e799fe2f8d442bd4a11b7 Mon Sep 17 00:00:00 2001 From: Jan Nieuwenhuizen Date: Sun, 6 Aug 2017 18:49:19 +0200 Subject: [PATCH] mescc: Tinycc support: struct assign by value. * module/language/c99/compiler.mes (base->ident): Remove. (accu->ident): Use them to support assign of size >4 by value. * scaffold/tests/7h-struct-assign.c: Test it. * make.scm (add-scaffold-test): Build it. * module/mes/as-i386.mes (i386:base->local): Remove. (i386:accu*n->local): (i386:accu*n->label): New functions. * module/mes/as-i386.scm: Export them. * stage0/x86.M1: (mov____%ebx,0x32): (mov____%ebx,0x32(%ebp)): (mov____%ebx,0x8(%ebp)): (mov____%ebx,0x8(%edx)): (mov____%ecx,0x32(%ebp)): (mov____%ecx,0x8(%ebp)): (mov____0x32(%eax),%ebx): (mov____0x32(%eax),%ecx): (mov____0x8(%eax),%ebx): New define. --- make.scm | 3 +- module/language/c99/compiler.mes | 21 +++++++------- module/mes/as-i386.mes | 33 ++++++++++++++++------ module/mes/as-i386.scm | 3 +- scaffold/tests/7h-struct-assign.c | 47 +++++++++++++++++++++++++++++++ stage0/x86.M1 | 10 +++++++ 6 files changed, 95 insertions(+), 22 deletions(-) create mode 100644 scaffold/tests/7h-struct-assign.c diff --git a/make.scm b/make.scm index 8be7ca89..d245149d 100755 --- a/make.scm +++ b/make.scm @@ -166,7 +166,8 @@ exec ${GUILE-guile} --no-auto-compile -L . -L guile -C . -C guile -s "$0" ${1+"$ "7d-cast-char" "7e-struct-array-access" "7f-struct-pointer-arithmetic" - "7g-struct-byte-word-field")) + "7g-struct-byte-word-field" + "7h-struct-assign")) (add-target (group "check-scaffold-tests/7" #:dependencies (filter (target-prefix? "check-scaffold/tests/7") %targets))) diff --git a/module/language/c99/compiler.mes b/module/language/c99/compiler.mes index bd7f914a..02e66bfc 100644 --- a/module/language/c99/compiler.mes +++ b/module/language/c99/compiler.mes @@ -380,16 +380,14 @@ (define (accu->ident info) (lambda (o) - (let ((local (assoc-ref (.locals info) o))) - (if local (wrap-as (i386:accu->local (local:id local))) - (let ((ptr (ident->pointer info o))) - (list (i386:accu->label `(#:address ,o)))))))) - -(define (base->ident info) - (lambda (o) - (let ((local (assoc-ref (.locals info) o))) - (if local (wrap-as (i386:base->local (local:id local))) - (list (i386:base->label `(#:address ,o))))))) + (let* ((local (assoc-ref (.locals info) o)) + (ptr (ident->pointer info o)) + (size (if (= ptr -1) (ident->size info o) + 4))) + (if local (if (<= size 4) (wrap-as (i386:accu->local (local:id local))) + (wrap-as (i386:accu*n->local (local:id local) size))) + (if (<= size 4) (wrap-as (i386:accu->label o)) + (wrap-as (i386:accu*n->label o size))))))) (define (base->ident-address info) (lambda (o) @@ -962,7 +960,8 @@ ((equal? op "<<=") (wrap-as (i386:accu<ident info) name))) + ((p-expr (ident ,name)) + (append-text info ((accu->ident info) name))) ((d-sel (ident ,field) ,p-expr) (let* ((type (p-expr->type info p-expr)) (offset (field-offset info type field)) diff --git a/module/mes/as-i386.mes b/module/mes/as-i386.mes index 0a94de23..3200d5ef 100644 --- a/module/mes/as-i386.mes +++ b/module/mes/as-i386.mes @@ -101,15 +101,18 @@ `(,(if (< (abs n) #x80) `("mov____%eax,0x8(%ebp)" (#:immediate1 ,n)) `("mov____%eax,0x32(%ebp)" (#:immediate ,n)))))) -(define (i386:base->local n) - (or n (error "invalid value: base->local: " n)) - `(("mov____%edx,0x8(%ebp)" ,(- 0 (* 4 n))))) ; mov %edx,-<0xn>(%ebp) - -(define (i386:base->local n) - (or n (error "invalid value: base->local: " n)) - (let ((n (- 0 (* 4 n)))) - `((if (< (abs n) #x80) `("mov____%edx,0x8(%ebp)" (#:immediate1 ,n)) - `("mov____%edx,0x32(%ebp)" (#:immediate ,n)))))) +(define (i386:accu*n->local i n) + (or n (error "invalid value: accu->local: " n)) + (let ((o (- 0 (* 4 i)))) + (let loop ((i 0)) + (if (>= i n) '() ;; FIXME: byte, word-sized + (let ((o (+ o i))) + (append + (if (< (abs o) #x80) `(("mov____0x8(%eax),%ebx" (#:immediate1 ,i)) + ("mov____%ebx,0x8(%ebp)" (#:immediate1 ,o))) + `(("mov____0x8(%eax),%ebx" (#:immediate1 ,i)) + ("mov____%ebx,0x32(%ebp)" (#:immediate ,o)))) + (loop (+ i 4)))))))) (define (i386:local->accu n) (or n (error "invalid value: local->accu: " n)) @@ -223,6 +226,18 @@ (define (i386:accu->label label) `(("mov____%eax,0x32" (#:address ,label)))) ; mov %eax,0x