mescc: Add 70-array-in-struct-init.c test with fix.

* lib/tests/scaffold/70-array-in-struct-init.c: New file.
* lib/tests/scaffold/70-array-in-struct-init.stdout: New file.
* build-aux/check-mescc.sh (TESTS): Add test.
* module/mescc/compile.scm (array-init-element->data): Recurse for
elements instead of using init->data.  Support array fields.
This commit is contained in:
Jan Nieuwenhuizen 2019-07-20 17:14:55 +02:00
parent 81849edb86
commit 8e01a68357
No known key found for this signature in database
GPG key ID: F3C1A0D9C1D65273
4 changed files with 85 additions and 15 deletions

View file

@ -180,6 +180,7 @@ lib/tests/scaffold/7u-inc-byte-word.c
lib/tests/scaffold/7u-struct-func.c
lib/tests/scaffold/7u-struct-size10.c
lib/tests/scaffold/7u-vstack.c
lib/tests/scaffold/70-array-in-struct-init.c
lib/tests/setjmp/80-setjmp.c
lib/tests/stdio/80-sscanf.c
lib/tests/stdlib/80-qsort.c

View file

@ -0,0 +1,56 @@
/* -*-comment-start: "//";comment-end:""-*-
* GNU Mes --- Maxwell Equations of Software
* Copyright © 2019 Jan (janneke) Nieuwenhuizen <janneke@gnu.org>
*
* This file is part of GNU Mes.
*
* GNU 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.
*
* GNU 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 GNU Mes. If not, see <http://www.gnu.org/licenses/>.
*/
#include <mes/lib.h>
struct foo
{
int field;
int array[3];
};
struct foo foes[] =
{
{10, {11, 12, 13}},
{20, {21, 22}},
{30, {31}},
{40, {41}},
{0}
};
int
main ()
{
for (struct foo *p = foes; p->field; p++)
{
oputs ("{");
oputs (itoa (p->field)); oputs (",");
oputs ("{");
oputs (itoa (p->array[0])); oputs (",");
oputs (itoa (p->array[1])); oputs (",");
oputs (itoa (p->array[2]));
oputs ("}");
oputs ("},\n");
}
oputs ("{0}\n");
oputs ("};\n");
return 0;
}

View file

@ -0,0 +1,6 @@
{10,{11,12,13}},
{20,{21,22,0}},
{30,{31,0,0}},
{40,{41,0,0}},
{0}
};

View file

@ -349,7 +349,7 @@
((bits . ,bits) bits)
(_ (list o))))
(define (struct->init-fields o)
(define (struct->init-fields o) ;; FIXME REMOVEME: non-recursive unroll
(pmatch o
(_ (guard (and (type? o) (eq? (type:type o) 'struct)))
(append-map struct->init-fields (type:description o)))
@ -2230,16 +2230,21 @@
(int->bv type (expr->number info fixed) info))
(int->bv type (expr->number info fixed) info)))
((initzer (initzer-list . ,inits))
(if (structured-type? type)
(cond ((structured-type? type)
(let* ((fields (map cdr (struct->init-fields type)))
(missing (max 0 (- (length fields) (length inits))))
(inits (append inits
(map (const '(fixed "0")) (iota missing)))))
(map (cut init->data <> <> info) fields inits))
(begin
(map (cut array-init-element->data <> <> info) fields inits)))
((c-array? type)
(let* ((missing (max 0 (- (c-array:count type) (length inits))))
(inits (append inits
(map (const '(fixed "0")) (iota missing)))))
(map (cut array-init-element->data (c-array:type type) <> info) inits)))
(else
(stderr "array-init-element->data: oops:~s\n" o)
(stderr "type:~s\n" type)
(error "array-init-element->data: unstructured not supported: " o))))
(error "array-init-element->data: not supported: " o))))
(_ (init->data type o info))
(_ (error "array-init-element->data: not supported: " o))))
@ -2248,7 +2253,8 @@
((initzer (initzer-list . ,inits))
(let ((type (c-array:type type)))
(if (structured-type? type)
(let* ((fields (length (struct->init-fields type))))
(let* ((init-fields (struct->init-fields type)) ;; FIXME
(count (length init-fields)))
(let loop ((inits inits))
(if (null? inits) '()
(let ((init (car inits)))
@ -2256,7 +2262,8 @@
((initzer (initzer-list . ,car-inits))
(append (array-init-element->data type init info)
(loop (cdr inits))))
(_ (let* ((count (min (length inits) fields))
(_
(let* ((count (min (length inits) (length init-fields)))
(field-inits (list-head inits count)))
(append (array-init-element->data type `(initzer-list ,@field-inits) info)
(loop (list-tail inits count))))))))))