Skip to content

Commit 70949a2

Browse files
tgtakaokacire831
authored andcommitted
Add _Noreturn keyword (#44)
pull #44
1 parent 659eb45 commit 70949a2

14 files changed

+81
-13
lines changed

nregress/c99c11/noreturn/Stop.nc

+3
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
interface Stop {
2+
command _Noreturn void stop_now(int i);
3+
}

nregress/c99c11/noreturn/StopM.nc

+11
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
#include <stdlib.h>
2+
#include <stdnoreturn.h>
3+
4+
module StopM {
5+
provides interface Stop;
6+
} implementation {
7+
command noreturn void Stop.stop_now(int i) {
8+
if (i > 0) exit(i);
9+
// This causes "`noreturn' function doesn return'" compiler warning.
10+
}
11+
}

nregress/c99c11/noreturn/TestP.nc

+17
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
#include <stdio.h>
2+
3+
module TestP {
4+
uses interface Stop;
5+
} implementation {
6+
_Noreturn int warning_if_variable_has_noreturn;
7+
8+
int main() @C() @spontaneous() {
9+
puts("Preparing to stop...");
10+
warning_if_variable_has_noreturn = 0;
11+
call Stop.stop_now(2);
12+
// The following code will not been compiled and executed
13+
// since not_stop_now() is declared as noreturn.
14+
puts("This code is never executed.");
15+
return 3;
16+
}
17+
}

nregress/c99c11/noreturn/test.nc

+5
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
configuration test {
2+
} implementation {
3+
components TestP, StopM;
4+
TestP.Stop -> StopM;
5+
}

nregress/c99c11/run1

+18
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
keep=
2+
if [ -z "$NESC1" ]; then
3+
NESC1=../../../src/nesc1
4+
keep=1
5+
fi
6+
cd $1
7+
cfile=/tmp/c99c11.$$.c
8+
exe=/tmp/c99c11.out.$$
9+
$NESC1 -fnesc-separator=__ test.nc -o $cfile && \
10+
gcc -Wall -g -o $exe $cfile && \
11+
$exe
12+
ok=$?
13+
if [ -z "$keep" ]; then
14+
rm -f $cfile $exe
15+
else
16+
echo C file is $cfile, executable is $exe
17+
fi
18+
exit $ok

nregress/ok/c99c11.noreturn.1

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Preparing to stop...

nregress/ok/c99c11.noreturn.2

+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
In file included from test.nc:3:
2+
In component `TestP':
3+
TestP.nc:6: warning: variable `warning_if_variable_has_noreturn' declared `_Noreturn'
4+
TestP.nc:6:15: warning: variable ‘TestP__warning_if_variable_has_noreturn’ declared ‘_Noreturn’
5+
_Noreturn int warning_if_variable_has_noreturn;
6+
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
7+
StopM.nc: In function ‘StopM__Stop__stop_now’:
8+
StopM.nc:10:1: warning: ‘noreturn’ function does return
9+
}
10+
^

nregress/ok/c99c11.noreturn.exit

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
2

src/c-lex.h

+1
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,7 @@ enum rid
6666
RID_STATIC,
6767
RID_EXTERN,
6868
RID_REGISTER,
69+
RID_NORETURN,
6970
RID_TYPEDEF,
7071
RID_COMMAND,
7172
RID_EVENT,

src/c-parse.gperf

+1
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ __typeof__, TYPEOF, NORID
5050
__volatile, TYPE_QUAL, volatile_qualifier
5151
__volatile__, TYPE_QUAL, volatile_qualifier
5252
__builtin_va_arg, VA_ARG, NORID
53+
_Noreturn, SCSPEC, RID_NORETURN
5354
asm, ASM_KEYWORD, NORID
5455
auto, SCSPEC, RID_AUTO
5556
break, BREAK, NORID

src/c-parse.y

+1-1
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,7 @@ void yyerror();
110110
/* the reserved words */
111111
/* SCO include files test "ASM", so use something else. */
112112
%token <u.itoken> SIZEOF ENUM STRUCT UNION IF ELSE WHILE DO FOR SWITCH CASE DEFAULT
113-
%token <u.itoken> BREAK CONTINUE RETURN GOTO ASM_KEYWORD TYPEOF ALIGNOF
113+
%token <u.itoken> BREAK CONTINUE RETURN GOTO ASM_KEYWORD TYPEOF ALIGNOF NORETURN
114114
%token <u.itoken> ATTRIBUTE EXTENSION LABEL
115115
%token <u.itoken> REALPART IMAGPART VA_ARG OFFSETOF
116116

src/semantics.c

+9-10
Original file line numberDiff line numberDiff line change
@@ -594,27 +594,25 @@ scflags parse_scflags(int specbits)
594594
scf |= scf_async;
595595
if (specbits & 1 << RID_NORACE)
596596
scf |= scf_norace;
597+
if (specbits & 1 << RID_NORETURN)
598+
scf |= scf_noreturn;
597599

598600
return scf;
599601
}
600602

601603
void check_variable_scflags(scflags scf,
602604
location l, const char *kind, const char *name)
603605
{
604-
const char *badqual = NULL;
605-
void (*msg)(location l, const char *format, ...) = error_with_location;
606+
static const char fmt_msg[] = "%s `%s' declared `%s'";
606607

607608
/* default already covered in parse_declarator */
609+
/* gcc just warns inline and _Noreturn for variable. */
608610
if (scf & scf_inline)
609-
{
610-
badqual = "inline";
611-
msg = pedwarn_with_location; /* this is what gcc does */
612-
}
611+
pedwarn_with_location(l, fmt_msg, kind, name, "inline");
612+
if (scf & scf_noreturn)
613+
pedwarn_with_location(l, fmt_msg, kind, name, "_Noreturn");
613614
if (scf & scf_async)
614-
badqual = "async";
615-
616-
if (badqual)
617-
msg(l, "%s `%s' declared `%s'", kind, name, badqual);
615+
error_with_location(l, fmt_msg, kind, name, "async");
618616
}
619617

620618
void check_array_size(expression size, const char *printname)
@@ -3628,6 +3626,7 @@ static char *rid_name_int(int id)
36283626
case RID_TASK: return "task";
36293627
case RID_DEFAULT: return "default";
36303628
case RID_NORACE: return "norace";
3629+
case RID_NORETURN: return "_Noreturn";
36313630
default: assert(0); return NULL;
36323631
}
36333632
}

src/semantics.h

+2-1
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,8 @@ typedef enum {
2828
scf_inline = 1,
2929
scf_default = 2,
3030
scf_async = 4,
31-
scf_norace = 8
31+
scf_norace = 8,
32+
scf_noreturn = 16
3233
} scflags;
3334

3435
/* Predefined __builtin_va_list type */

src/unparse.c

+1-1
Original file line numberDiff line numberDiff line change
@@ -631,7 +631,7 @@ static void prt_prefix(location loc, data_declaration ddecl,
631631
if (pinline)
632632
continue;
633633
break;
634-
case RID_REGISTER: case RID_TYPEDEF:
634+
case RID_REGISTER: case RID_TYPEDEF: case RID_NORETURN:
635635
break;
636636
}
637637
set_location(r->location);

0 commit comments

Comments
 (0)