Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/usr.bin/xlint/lint1 lint: fix result type of _Generic expres...



details:   https://anonhg.NetBSD.org/src/rev/f9807de36d86
branches:  trunk
changeset: 379929:f9807de36d86
user:      rillig <rillig%NetBSD.org@localhost>
date:      Sun Jun 27 20:47:13 2021 +0000

description:
lint: fix result type of _Generic expressions

diffstat:

 tests/usr.bin/xlint/lint1/c11_generic_expression.c   |  14 ++++++----
 tests/usr.bin/xlint/lint1/c11_generic_expression.exp |   7 ++---
 tests/usr.bin/xlint/lint1/msg_345.c                  |   4 +-
 usr.bin/xlint/lint1/cgram.y                          |  26 +++++++++++++++----
 usr.bin/xlint/lint1/externs1.h                       |   5 +++-
 usr.bin/xlint/lint1/lint1.h                          |   8 +++++-
 usr.bin/xlint/lint1/tree.c                           |  18 ++++++++++++-
 7 files changed, 60 insertions(+), 22 deletions(-)

diffs (233 lines):

diff -r 00e748fde672 -r f9807de36d86 tests/usr.bin/xlint/lint1/c11_generic_expression.c
--- a/tests/usr.bin/xlint/lint1/c11_generic_expression.c        Sun Jun 27 19:59:23 2021 +0000
+++ b/tests/usr.bin/xlint/lint1/c11_generic_expression.c        Sun Jun 27 20:47:13 2021 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: c11_generic_expression.c,v 1.2 2021/06/27 19:59:23 rillig Exp $        */
+/*     $NetBSD: c11_generic_expression.c,v 1.3 2021/06/27 20:47:13 rillig Exp $        */
 # 3 "c11_generic_expression.c"
 
 /*
@@ -20,13 +20,14 @@
 const char *
 classify_type_without_default(double var)
 {
+       /* expect-2: argument 'var' unused */
+
        return _Generic(var,
            long double: "long double",
            long long: "long long",
            unsigned: "unsigned"
        );
-       /* expect-7: argument 'var' unused */
-       /* expect-2: type mismatch (pointer to const char) and (double) *//* FIXME */
+       /* expect-1: expects to return value [214] */
 }
 
 /*
@@ -35,14 +36,14 @@ classify_type_without_default(double var
 const char *
 classify_type_with_default(double var)
 {
+       /* expect-2: argument 'var' unused */
+
        return _Generic(var,
            long double: "long double",
            long long: "long long",
            unsigned: "unsigned",
            default: "unknown"
        );
-       /* expect-8: argument 'var' unused */
-       /* expect-2: type mismatch (pointer to const char) and (double) *//* FIXME */
 }
 
 /*
@@ -51,9 +52,10 @@ classify_type_with_default(double var)
 const char *
 classify_char(char c)
 {
+       /* expect-2: argument 'c' unused */
+
        return _Generic(c,
            char: "yes",
            default: 0.0
        );
-       /* expect-1: (pointer to const char) and integer (char) [183] */
 }
diff -r 00e748fde672 -r f9807de36d86 tests/usr.bin/xlint/lint1/c11_generic_expression.exp
--- a/tests/usr.bin/xlint/lint1/c11_generic_expression.exp      Sun Jun 27 19:59:23 2021 +0000
+++ b/tests/usr.bin/xlint/lint1/c11_generic_expression.exp      Sun Jun 27 20:47:13 2021 +0000
@@ -1,5 +1,4 @@
-c11_generic_expression.c(27): error: return value type mismatch (pointer to const char) and (double) [211]
+c11_generic_expression.c(29): warning: function classify_type_without_default expects to return value [214]
 c11_generic_expression.c(21): warning: argument 'var' unused in function 'classify_type_without_default' [231]
-c11_generic_expression.c(43): error: return value type mismatch (pointer to const char) and (double) [211]
-c11_generic_expression.c(36): warning: argument 'var' unused in function 'classify_type_with_default' [231]
-c11_generic_expression.c(57): warning: illegal combination of pointer (pointer to const char) and integer (char) [183]
+c11_generic_expression.c(37): warning: argument 'var' unused in function 'classify_type_with_default' [231]
+c11_generic_expression.c(53): warning: argument 'c' unused in function 'classify_char' [231]
diff -r 00e748fde672 -r f9807de36d86 tests/usr.bin/xlint/lint1/msg_345.c
--- a/tests/usr.bin/xlint/lint1/msg_345.c       Sun Jun 27 19:59:23 2021 +0000
+++ b/tests/usr.bin/xlint/lint1/msg_345.c       Sun Jun 27 20:47:13 2021 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: msg_345.c,v 1.1 2021/06/27 19:10:29 rillig Exp $       */
+/*     $NetBSD: msg_345.c,v 1.2 2021/06/27 20:47:13 rillig Exp $       */
 # 3 "msg_345.c"
 
 // Test for message: generic selection requires C11 or later [345]
@@ -10,5 +10,5 @@ int
 test(int x)
 {
        /* expect+1: generic selection requires C11 or later [345] */
-       return _Generic(x, default: 3);
+       return _Generic(x, default: 3) + x;
 }
diff -r 00e748fde672 -r f9807de36d86 usr.bin/xlint/lint1/cgram.y
--- a/usr.bin/xlint/lint1/cgram.y       Sun Jun 27 19:59:23 2021 +0000
+++ b/usr.bin/xlint/lint1/cgram.y       Sun Jun 27 20:47:13 2021 +0000
@@ -1,5 +1,5 @@
 %{
-/* $NetBSD: cgram.y,v 1.236 2021/06/27 19:10:29 rillig Exp $ */
+/* $NetBSD: cgram.y,v 1.237 2021/06/27 20:47:13 rillig Exp $ */
 
 /*
  * Copyright (c) 1996 Christopher G. Demetriou.  All Rights Reserved.
@@ -35,7 +35,7 @@
 
 #include <sys/cdefs.h>
 #if defined(__RCSID) && !defined(lint)
-__RCSID("$NetBSD: cgram.y,v 1.236 2021/06/27 19:10:29 rillig Exp $");
+__RCSID("$NetBSD: cgram.y,v 1.237 2021/06/27 20:47:13 rillig Exp $");
 #endif
 
 #include <limits.h>
@@ -139,6 +139,7 @@ anonymize(sym_t *s)
        strg_t  *y_string;
        pqinf_t *y_pqinf;
        bool    y_seen_statement;
+       struct generic_association_types *y_types;
 };
 
 %token                 T_LBRACE T_RBRACE T_LBRACK T_RBRACK T_LPAREN T_RPAREN
@@ -338,6 +339,8 @@ anonymize(sym_t *s)
 %type  <y_range>       range
 %type  <y_seen_statement> block_item_list
 %type  <y_seen_statement> block_item
+%type  <y_types>       generic_assoc_list
+%type  <y_types>       generic_association
 
 
 %%
@@ -1685,18 +1688,29 @@ generic_selection:              /* C11 6.5.1.1 */
          T_GENERIC T_LPAREN expr T_COMMA generic_assoc_list T_RPAREN {
                /* generic selection requires C11 or later */
                c11ism(345);
-               $$ = $3;
+               $$ = build_generic_selection($3, $5);
          }
        ;
 
 generic_assoc_list:            /* C11 6.5.1.1 */
          generic_association
-       | generic_assoc_list T_COMMA generic_association
+       | generic_assoc_list T_COMMA generic_association {
+               $3->gat_prev = $1;
+               $$ = $3;
+         }
        ;
 
 generic_association:           /* C11 6.5.1.1 */
-         type_name T_COLON expr
-       | T_DEFAULT T_COLON expr
+         type_name T_COLON expr {
+               $$ = getblk(sizeof(*$$));
+               $$->gat_arg = $1;
+               $$->gat_result = $3;
+         }
+       | T_DEFAULT T_COLON expr {
+               $$ = getblk(sizeof(*$$));
+               $$->gat_arg = NULL;
+               $$->gat_result = $3;
+         }
        ;
 
 do_statement:                  /* C99 6.8.5 */
diff -r 00e748fde672 -r f9807de36d86 usr.bin/xlint/lint1/externs1.h
--- a/usr.bin/xlint/lint1/externs1.h    Sun Jun 27 19:59:23 2021 +0000
+++ b/usr.bin/xlint/lint1/externs1.h    Sun Jun 27 20:47:13 2021 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: externs1.h,v 1.111 2021/06/20 20:59:08 rillig Exp $    */
+/*     $NetBSD: externs1.h,v 1.112 2021/06/27 20:47:13 rillig Exp $    */
 
 /*
  * Copyright (c) 1994, 1995 Jochen Pohl
@@ -208,6 +208,9 @@ extern      tnode_t *expr_new_constant(type_t
 extern tnode_t *new_name_node(sym_t *, int);
 extern tnode_t *new_string_node(strg_t *);
 extern sym_t   *struct_or_union_member(tnode_t *, op_t, sym_t *);
+extern tnode_t *build_generic_selection(const tnode_t *,
+                   struct generic_association_types *);
+
 extern tnode_t *build(op_t, tnode_t *, tnode_t *);
 extern tnode_t *cconv(tnode_t *);
 extern bool    is_typeok_bool_operand(const tnode_t *);
diff -r 00e748fde672 -r f9807de36d86 usr.bin/xlint/lint1/lint1.h
--- a/usr.bin/xlint/lint1/lint1.h       Sun Jun 27 19:59:23 2021 +0000
+++ b/usr.bin/xlint/lint1/lint1.h       Sun Jun 27 20:47:13 2021 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: lint1.h,v 1.106 2021/06/27 08:20:50 rillig Exp $ */
+/* $NetBSD: lint1.h,v 1.107 2021/06/27 20:47:13 rillig Exp $ */
 
 /*
  * Copyright (c) 1996 Christopher G. Demetriou.  All Rights Reserved.
@@ -316,6 +316,12 @@ typedef    struct tnode {
 #define        tn_val          tn_u._tn_val
 #define        tn_string       tn_u._tn_string
 
+struct generic_association_types {
+       type_t *gat_arg;        /* NULL means default or error */
+       tnode_t *gat_result;    /* NULL means error */
+       struct generic_association_types *gat_prev;
+};
+
 /*
  * For nested declarations a stack exists, which holds all information
  * needed for the current level. dcs points to the innermost element of this
diff -r 00e748fde672 -r f9807de36d86 usr.bin/xlint/lint1/tree.c
--- a/usr.bin/xlint/lint1/tree.c        Sun Jun 27 19:59:23 2021 +0000
+++ b/usr.bin/xlint/lint1/tree.c        Sun Jun 27 20:47:13 2021 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: tree.c,v 1.290 2021/06/20 20:48:25 rillig Exp $        */
+/*     $NetBSD: tree.c,v 1.291 2021/06/27 20:47:13 rillig Exp $        */
 
 /*
  * Copyright (c) 1994, 1995 Jochen Pohl
@@ -37,7 +37,7 @@
 
 #include <sys/cdefs.h>
 #if defined(__RCSID) && !defined(lint)
-__RCSID("$NetBSD: tree.c,v 1.290 2021/06/20 20:48:25 rillig Exp $");
+__RCSID("$NetBSD: tree.c,v 1.291 2021/06/27 20:47:13 rillig Exp $");
 #endif
 
 #include <float.h>
@@ -468,6 +468,20 @@ struct_or_union_member(tnode_t *tn, op_t
        return msym;
 }
 
+tnode_t *
+build_generic_selection(const tnode_t *expr,
+                       struct generic_association_types *sel)
+{
+       tnode_t *default_result = NULL;
+
+       for (; sel != NULL; sel = sel->gat_prev)
+               if (expr != NULL && sel->gat_arg == expr->tn_type)
+                       return sel->gat_result;
+               else if (sel->gat_arg == NULL)
+                       default_result = sel->gat_result;
+       return default_result;
+}
+
 /*
  * Create a tree node. Called for most operands except function calls,
  * sizeof and casts.



Home | Main Index | Thread Index | Old Index