aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSergey Poznyakoff <gray@gnu.org.ua>2006-09-07 15:41:17 +0000
committerSergey Poznyakoff <gray@gnu.org.ua>2006-09-07 15:41:17 +0000
commitaf5a05d17aaeffb28124198ce64a508449deb75e (patch)
tree4ba390ee8eb27324a8907f6bd417db0d8fcfcd3a
parentc06c96201c375be53db27819d3b4e61305ceecaf (diff)
downloadcflow-af5a05d17aaeffb28124198ce64a508449deb75e.tar.gz
cflow-af5a05d17aaeffb28124198ce64a508449deb75e.tar.bz2
(declare, parse_dcl, parse_knr_dcl): Fix parsing of K&R declarations, broken by modifications on 2005-09-21.
-rw-r--r--src/parser.c124
1 files changed, 64 insertions, 60 deletions
diff --git a/src/parser.c b/src/parser.c
index f1b9d53..30bc9c9 100644
--- a/src/parser.c
+++ b/src/parser.c
@@ -30,13 +30,13 @@ typedef struct {
30void parse_declaration(Ident*, int); 30void parse_declaration(Ident*, int);
31void parse_variable_declaration(Ident*, int); 31void parse_variable_declaration(Ident*, int);
32void parse_function_declaration(Ident*, int); 32void parse_function_declaration(Ident*, int);
33void parse_dcl(Ident*); 33void parse_dcl(Ident*, int maybe_knr);
34void parse_knr_dcl(Ident*); 34void parse_knr_dcl(Ident*);
35void parse_typedef(); 35void parse_typedef();
36void expression(); 36void expression();
37void initializer_list(); 37void initializer_list();
38void func_body(); 38void func_body();
39void declare(Ident*); 39void declare(Ident*, int maybe_knr);
40void declare_type(Ident*); 40void declare_type(Ident*);
41int dcl(Ident*); 41int dcl(Ident*);
42int parmdcl(Ident*); 42int parmdcl(Ident*);
@@ -540,7 +540,7 @@ parse_variable_declaration(Ident *ident, int parm)
540 } 540 }
541 } 541 }
542 again: 542 again:
543 parse_dcl(ident); 543 parse_dcl(ident, 0);
544 544
545 select: 545 select:
546 switch (tok.type) { 546 switch (tok.type) {
@@ -613,58 +613,7 @@ void
613parse_knr_dcl(Ident *ident) 613parse_knr_dcl(Ident *ident)
614{ 614{
615 ident->type_end = -1; 615 ident->type_end = -1;
616 parse_dcl(ident); 616 parse_dcl(ident, !strict_ansi);
617 if (strict_ansi)
618 return;
619
620 switch (tok.type) {
621 case IDENTIFIER:
622 case TYPE:
623 case STRUCT:
624 if (ident->parmcnt >= 0) {
625 /* maybe K&R function definition */
626 int parmcnt, stop;
627 Stackpos sp, new_sp;
628 Ident id;
629
630 mark(sp);
631 parmcnt = 0;
632
633 for (stop = 0; !stop && parmcnt < ident->parmcnt;
634 nexttoken()) {
635 id.type_end = -1;
636 switch (tok.type) {
637 case LBRACE:
638 case LBRACE0:
639 putback();
640 stop = 1;
641 break;
642 case TYPE:
643 case IDENTIFIER:
644 case STRUCT:
645 putback();
646 mark(new_sp);
647 if (dcl(&id) == 0) {
648 parmcnt++;
649 if (tok.type == ',') {
650 do {
651 tos = id.type_end; /* ouch! */
652 restore(new_sp);
653 dcl(&id);
654 } while (tok.type == ',');
655 } else if (tok.type != ';')
656 putback();
657 break;
658 }
659 /* else */
660 /* FALLTHRU */
661 default:
662 restore(sp);
663 return;
664 }
665 }
666 }
667 }
668} 617}
669 618
670void 619void
@@ -717,7 +666,7 @@ parse_typedef()
717} 666}
718 667
719void 668void
720parse_dcl(Ident *ident) 669parse_dcl(Ident *ident, int maybe_knr)
721{ 670{
722 ident->parmcnt = -1; 671 ident->parmcnt = -1;
723 ident->name = NULL; 672 ident->name = NULL;
@@ -725,7 +674,7 @@ parse_dcl(Ident *ident)
725 dcl(ident); 674 dcl(ident);
726 save_stack(); 675 save_stack();
727 if (ident->name) 676 if (ident->name)
728 declare(ident); 677 declare(ident, maybe_knr);
729 else 678 else
730 undo_save_stack(); 679 undo_save_stack();
731} 680}
@@ -947,8 +896,61 @@ func_body()
947 } 896 }
948} 897}
949 898
899int
900get_knr_args(Ident *ident)
901{
902 int parmcnt, stop;
903 Stackpos sp, new_sp;
904 Ident id;
905
906 switch (tok.type) {
907 case IDENTIFIER:
908 case TYPE:
909 case STRUCT:
910 /* maybe K&R function definition */
911
912 mark(sp);
913 parmcnt = 0;
914
915 for (stop = 0; !stop && parmcnt < ident->parmcnt;
916 nexttoken()) {
917 id.type_end = -1;
918 switch (tok.type) {
919 case LBRACE:
920 case LBRACE0:
921 putback();
922 stop = 1;
923 break;
924 case TYPE:
925 case IDENTIFIER:
926 case STRUCT:
927 putback();
928 mark(new_sp);
929 if (dcl(&id) == 0) {
930 parmcnt++;
931 if (tok.type == ',') {
932 do {
933 tos = id.type_end; /* ouch! */
934 restore(new_sp);
935 dcl(&id);
936 } while (tok.type == ',');
937 } else if (tok.type != ';')
938 putback();
939 break;
940 }
941 /* else */
942 /* FALLTHRU */
943 default:
944 restore(sp);
945 return 1;
946 }
947 }
948 }
949 return 0;
950}
951
950void 952void
951declare(Ident *ident) 953declare(Ident *ident, int maybe_knr)
952{ 954{
953 Symbol *sp; 955 Symbol *sp;
954 956
@@ -965,8 +967,10 @@ declare(Ident *ident)
965 sp->arity = -1; 967 sp->arity = -1;
966 return; 968 return;
967 } 969 }
968 970
969 if ((ident->parmcnt >= 0 && !(tok.type == LBRACE || tok.type == LBRACE0)) 971 if ((ident->parmcnt >= 0
972 && (!maybe_knr || get_knr_args(ident) == 0)
973 && !(tok.type == LBRACE || tok.type == LBRACE0 || tok.type == TYPE))
970 || (ident->parmcnt < 0 && ident->storage == ExplicitExternStorage)) { 974 || (ident->parmcnt < 0 && ident->storage == ExplicitExternStorage)) {
971 undo_save_stack(); 975 undo_save_stack();
972 /* add_external()?? */ 976 /* add_external()?? */

Return to:

Send suggestions and report system problems to the System administrator.