~ubuntu-branches/ubuntu/quantal/aspectc++/quantal

« back to all changes in this revision

Viewing changes to Puma/gen-release/step1/src/CSemExpr.cc

  • Committer: Bazaar Package Importer
  • Author(s): Reinhard Tartler
  • Date: 2008-04-10 17:40:52 UTC
  • mfrom: (1.1.2 upstream)
  • Revision ID: james.westby@ubuntu.com-20080410174052-xdnsm7oi8hauyyf1
Tags: 1.0pre4~svn.20080409+dfsg-3
Fix another missing include, this time in Ag++/StdSystem.cc

Show diffs side-by-side

added added

removed removed

Lines of Context:
39
39
// the include cycle problem
40
40
#include "Puma/CSemVisitor.h"
41
41
 
 
42
#include <climits>
42
43
#include <sstream>         /* istringstream */
43
44
#include "Puma/WChar.h"    /* wcslen() */
44
45
#include <ctype.h>         /* isdigit(); isxdigit() */
 
46
#include <string.h>
45
47
using namespace std;
46
48
 
47
49
namespace Puma {
50
52
// print semantic error messages
51
53
 
52
54
#define SEM_MSG(node__,mesg__) \
53
 
  err << node__->token ()->location () << mesg__ << endMessage
 
55
  {if (node__->token ()) err << node__->token ()->location (); err << mesg__ << endMessage;}
54
56
  
55
57
#define SEM_ERROR(node__, mesg__) \
56
58
  SEM_MSG (node__, sev_error << mesg__)
68
70
  SEM_WARNING (node__, \
69
71
    "decimal constant is so large that it is unsigned")
70
72
 
 
73
#define SEM_WARNING__incompatible_assign(node__) \
 
74
  SEM_WARNING (node__, \
 
75
    "assignment from incompatible pointer type")
 
76
 
71
77
#define SEM_ERROR__type_mismatch(node__,where__) \
72
78
  SEM_ERROR (node__, "type mismatch in " << where__)
73
79
 
74
80
#define SEM_ERROR__invalid_op(node__,type__,op__) \
75
81
  SEM_ERROR (node__, "invalid operand to " << type__ << " `" << op__ << "'")
76
82
 
77
 
#define SEM_ERROR__comp_between(node__,what__) \
78
 
  SEM_ERROR (node__, "comparison between " << what__)
 
83
#define SEM_WARNING__comp_between(node__,what__) \
 
84
  SEM_WARNING (node__, "comparison between " << what__)
79
85
 
80
86
#define SEM_ERROR__non_lvalue(node__) \
81
87
  SEM_ERROR (node__, "non-lvalue in assignment")
84
90
  SEM_ERROR (node__, type__ << " object `" << name__->Name () \
85
91
    << "' may not be initialized")
86
92
 
87
 
#define SEM_ERROR__num_args_too(node__,what__,info__) \
88
 
  SEM_ERROR (node__, "too " << what__ << " arguments in call to function `" \
 
93
#define SEM_ERROR__num_args_too(node__,what__,num__,info__) \
 
94
  SEM_ERROR (node__, "too " << what__ << " arguments (" << num__ << ") in call to function `" \
89
95
    << info__->Name () << "'")
90
96
 
91
97
#define SEM_ERROR__invalid_arg(node__,pos__,info__) \
97
103
///////////////////////////////////////////////////////
98
104
 
99
105
 
100
 
 
101
106
CTypeInfo *CSemExpr::resolveExpr (CTree *expr, CTree *base) {
102
 
  const char *id;
103
 
  CTypeInfo *result;
104
 
 
105
 
  id = expr->NodeName ();
106
 
 
107
 
  // call the node type specific resolve function
108
 
  if (!(result = expr->resolve (*this, base))) {
109
 
    SEM_ERROR (expr, "expression expected");
110
 
    result = &CTYPE_UNDEFINED;
111
 
    if (expr->SemValue ())
112
 
      expr->SemValue ()->setTypeRef (result);
 
107
  CTypeInfo *result = expr->Type ();
 
108
 
 
109
  // ensure not to evaluate twice
 
110
  if (! result || result == &CTYPE_UNDEFINED || 
 
111
     expr->IsSimpleName () ||
 
112
     expr->NodeName () == CT_BracedExpr::NodeId ()) {
 
113
    // call the node type specific resolve function
 
114
    if (!(result = expr->resolve (*this, base))) {
 
115
      SEM_ERROR (expr, "expression expected");
 
116
      result = &CTYPE_UNDEFINED;
 
117
      if (expr->SemValue ())
 
118
        expr->SemValue ()->setTypeRef (result);
 
119
    }
113
120
  }
114
121
 
115
 
  // implicit array and function type conversions
116
 
  if (result->isArray () || result->isFunction ()) {
117
 
    if (conv_to_ptr > 0 && ! (conv_to_ptr == 2 && 
118
 
        (id == CT_String::NodeId () || id == CT_WideString::NodeId ()))) {
119
 
      result = result->isArray () ? result->VirtualType ()->BaseType () : result;
120
 
      result = new CTypePointer (result->Duplicate ());
121
 
      cast_to (result, expr, base, false);
122
 
      conv_to_ptr = 1;
123
 
    }
124
 
  } else
125
 
    conv_to_ptr = 1;
126
 
  
 
122
  // implicit lvalue, array and function type conversions
 
123
  result = applyImplicitConv (expr, base, result);
 
124
 
127
125
  return result;
128
126
}
129
127
 
174
172
    result = &CTYPE_CHAR;
175
173
    v = (char)v;
176
174
  } else {                         // integer character constant
177
 
    if (chars > 4)
 
175
    if (chars > 4) {
178
176
      SEM_ERROR (node, "integer character constant too long");
179
 
    else
 
177
    } else {
180
178
      SEM_WARNING (node, "multi-character character constant");
 
179
    }
181
180
    result = &CTYPE_INT; 
182
181
    v = (int)v;
183
182
  }
205
204
    result = &CTYPE_WCHAR_T;
206
205
    v = (wchar_t)v;
207
206
  } else {
208
 
    if (chars > 4)
 
207
    if (chars > 4) {
209
208
      SEM_ERROR (node, "integer character constant too long");
210
 
    else 
 
209
    } else {
211
210
      SEM_WARNING (node, "multi-character character constant");
 
211
    }
212
212
    result = &CTYPE_INT;
213
213
    v = (int)v;
214
214
  }
560
560
  
561
561
  ctp_old = conv_to_ptr;
562
562
  conv_to_ptr = 1;
 
563
  
 
564
  // don't apply lvalue-to-rvalue conversion if left operand of assignment
 
565
  if (oper == TOK_ASSIGN || oper == TOK_MUL_EQ || oper == TOK_DIV_EQ ||
 
566
      oper == TOK_MOD_EQ || oper == TOK_ADD_EQ || oper == TOK_SUB_EQ ||
 
567
      oper == TOK_RSH_EQ || oper == TOK_LSH_EQ || oper == TOK_AND_EQ ||
 
568
      oper == TOK_XOR_EQ || oper == TOK_IOR_EQ)
 
569
    conv_to_ptr = 3; 
563
570
 
564
571
  // resolve operands
565
572
  resolveExpr (node->Son (0), node);
 
573
  if (conv_to_ptr == 3)
 
574
    conv_to_ptr = 1;
566
575
  if (oper == TOK_COMMA)
567
576
    conv_to_ptr = ctp_old;
568
577
  resolveExpr (node->Son (2), node);
624
633
    return apply_binary_op (node, oper);
625
634
  } else if (oper == TOK_PLUS) {
626
635
    if (! (t1->isArithmetic () && isPtrToObj (t2, pos)) &&
627
 
        ! (t2->isArithmetic () && isPtrToObj (t1, pos)))
 
636
        ! (t2->isArithmetic () && isPtrToObj (t1, pos))) {
628
637
      SEM_ERROR__invalid_op (node, "binary", "+");
629
 
    else
 
638
    } else
630
639
      return t1->isPointer () ? t1 : t2;
631
640
  } else { // TOK_MINUS
632
641
    if (! (isPtrToObj (t1, pos) && t2->isInteger ()) &&
633
 
        ! (isPtrToObj (t1, pos) && isPtrToObj (t2, pos) && compatibleBase (t1, t2))) 
 
642
        ! (isPtrToObj (t1, pos) && isPtrToObj (t2, pos) && compatibleBase (t1, t2))) {
634
643
      SEM_ERROR__invalid_op (node, "binary", "-");
635
 
    else                                           /* ptrdiff_t */
 
644
    } else                                           /* ptrdiff_t */
636
645
      return t1->isPointer () && t2->isPointer () ? CTypeInfo::CTYPE_PTRDIFF_T : t1;
637
646
  }
638
647
  return &CTYPE_UNDEFINED;
657
666
  } else {
658
667
    v2 = node->Son (2)->Value () ? node->Son (2)->Value ()->Constant () : 0;
659
668
    if ((oper == TOK_MODULO || oper == TOK_DIV) && v2 && v2->isNull ()) 
660
 
      SEM_ERROR (node, "division by zero");
661
 
    else
662
 
      return apply_binary_op (node, oper);
 
669
      SEM_WARNING (node, "division by zero");
 
670
    return apply_binary_op (node, oper);
663
671
  }
664
672
  return &CTYPE_UNDEFINED;
665
673
}
677
685
  t1 = promote (node->Son (0), node); 
678
686
  t2 = promote (node->Son (2), node);
679
687
 
680
 
  if (! (t1->isInteger () && t2->isInteger ()))
 
688
  if (! (t1->isInteger () && t2->isInteger ())) {
681
689
    SEM_ERROR__invalid_op (node, "binary", op);
682
 
  else {
 
690
  } else {
683
691
    v2 = node->Son (2)->Value () ? node->Son (2)->Value ()->Constant () : 0;
684
692
    if (v2 && v2->isNegative ())
685
693
      SEM_WARNING (node, "negative shift count");
743
751
    if (v1 && v1->isNull ()) // null pointer constant
744
752
      cast_to (l?t2:t1, node->Son (l?0:2), node);
745
753
    else
746
 
      SEM_ERROR__comp_between (node, "pointer and integer");
 
754
      SEM_WARNING__comp_between (node, "pointer and integer");
747
755
  } else if (t1->isPointer () && t2->isPointer () &&
748
756
             (t1->VirtualType ()->BaseType ()->isVoid () || 
749
757
              t2->VirtualType ()->BaseType ()->isVoid ())) {
750
 
    if (! compatibleBase (t1, t2)) {
 
758
    if (*t1 != *t2) {
751
759
      l = t1->VirtualType ()->BaseType ()->isVoid () ? true : false;
752
760
      cast_to (l?t1:t2, node->Son (l?2:0), node);
753
761
    }
754
762
  } else if (t1->isPointer () && t2->isPointer ()) {
755
763
    if (! compatibleBase (t1, t2))
756
 
      SEM_ERROR__comp_between (node, "distinct pointer types");
 
764
      SEM_WARNING__comp_between (node, "distinct pointer types");
757
765
  } else
758
766
    SEM_ERROR__invalid_op (node, "binary", op);
759
767
  return &CTYPE_INT;
771
779
  t1 = promote (node->Son (0), node); 
772
780
  t2 = promote (node->Son (2), node);
773
781
 
774
 
  if (! (t1->isInteger () && t2->isInteger ()))
 
782
  if (! (t1->isInteger () && t2->isInteger ())) {
775
783
    SEM_ERROR__invalid_op (node, "binary", op);
776
 
  else 
 
784
  } else 
777
785
    return apply_binary_op (node, oper);
778
786
  return &CTYPE_UNDEFINED;
779
787
}
791
799
  t1 = promote (node->Son (0), node); 
792
800
  t2 = promote (node->Son (2), node);
793
801
 
794
 
  if (! (t1->isScalar () && t2->isScalar ()))
 
802
  if (! (t1->isScalar () && t2->isScalar ())) {
795
803
    SEM_ERROR__invalid_op (node, "binary", op);
796
 
  else if (t1->isArithmetic () && t2->isArithmetic ()) {
 
804
  } else if (t1->isArithmetic () && t2->isArithmetic ()) {
797
805
    t1 = apply_binary_op (node, oper);
798
806
    v1 = node->Value () ? node->Value ()->Constant () : 0;
799
807
    if (v1 && t1 != &CTYPE_INT) // must have type `int'
825
833
  t2 = node->Son (2)->Type (); 
826
834
  v2 = node->Son (2)->Value () ? node->Son (2)->Value ()->Constant () : 0;
827
835
 
828
 
  if (! isLvalue (node->Son (0))) 
 
836
  if (! isLvalue (node->Son (0))) {
829
837
    SEM_ERROR__non_lvalue (node);
830
 
  else {
 
838
  } else {
831
839
    if (! isModifiable (t1, pos))
832
840
      SEM_WARNING (node, "assignment of unmodifiable location");
833
841
    if (t1->isArithmetic () && t2->isArithmetic ()) {
834
842
      if (oper == TOK_ASSIGN) {
835
 
        if (! compatible (t1, t2))
 
843
        if (*t1 != *t2)
836
844
          cast_to (t1->VirtualType (), node->Son (2), node);
837
845
      } else {
838
846
        if ((oper == TOK_RSH_EQ || oper == TOK_LSH_EQ || 
841
849
            ! (t1->isInteger () && t2->isInteger ()))
842
850
          SEM_ERROR__invalid_op (node, "binary", op);
843
851
        if (v2) {
844
 
          if ((oper == TOK_MOD_EQ || oper == TOK_DIV_EQ) && v2->isNull ())
845
 
            SEM_ERROR (node, "division by zero");
846
 
          else if ((oper == TOK_RSH_EQ || oper == TOK_LSH_EQ) && 
847
 
                   v2->isNegative ())
 
852
          if ((oper == TOK_MOD_EQ || oper == TOK_DIV_EQ) && v2->isNull ()) {
 
853
            SEM_WARNING (node, "division by zero");
 
854
          } else if ((oper == TOK_RSH_EQ || oper == TOK_LSH_EQ) && 
 
855
                   v2->isNegative ()) {
848
856
            SEM_WARNING (node, "negative shift count");
 
857
          }
849
858
        }
850
859
      }
851
860
      return t1->VirtualType ();
852
861
    } else if (oper == TOK_ASSIGN) {
853
 
      if (! (t1->isRecord () && t2->isRecord () && compatible (t1, t2) && 
854
 
             t1->isComplete (pos) && t2->isComplete (pos)) &&
855
 
          ! (t1->isPointer () && t2->isPointer () && 
856
 
             (compatibleBase (t1, t2) ||
857
 
                t1->VirtualType ()->BaseType ()->isVoid () || 
858
 
              t2->VirtualType ()->BaseType ()->isVoid ()) &&
859
 
             (t2->isConst () ? t1->isConst () : true) &&
860
 
             (t2->isVolatile () ? t1->isVolatile () : true) &&
861
 
             (t2->isRestrict () ? t1->isRestrict () : true)) &&
862
 
          ! (t1->isPointer () && t2->isInteger () && v2 && v2->isNull ()) &&
863
 
          ! (t1->VirtualType ()->is_bool () && t2->isPointer ())) 
864
 
        SEM_ERROR__invalid_op (node, "binary", op);
865
 
      else {
866
 
        if (! compatible (t1, t2))
867
 
          cast_to (t1->VirtualType (), node->Son (2), node);
868
 
        return t1->VirtualType ();
869
 
      }
 
862
      if (! compatible (t1, t2, v2)) 
 
863
        SEM_WARNING__incompatible_assign (node);
 
864
      if (*t1 != *t2)
 
865
        cast_to (t1->VirtualType (), node->Son (2), node);
 
866
      return t1->VirtualType ();
870
867
    } else if (oper == TOK_ADD_EQ || oper == TOK_SUB_EQ) {
871
 
      if (! (isPtrToObj (t1, pos) && t2->isInteger ())) 
 
868
      if (! (isPtrToObj (t1, pos) && t2->isInteger ())) { 
872
869
        SEM_ERROR__invalid_op (node, "binary", op);
873
 
      else
 
870
      } else
874
871
        return t1->VirtualType ();
875
872
    } else
876
873
      SEM_ERROR__invalid_op (node, "binary", op);
930
927
  
931
928
  conv_to_ptr = 1;
932
929
 
 
930
  // don't apply lvalue-to-rvalue conversion
 
931
  if (oper == TOK_DECR || oper == TOK_INCR)
 
932
    conv_to_ptr = 3;
 
933
 
933
934
  // resolve operands
934
935
  t1 = resolveExpr (node->Son (1), node); 
935
936
  op1 = node->Son (1);
938
939
    
939
940
  // ++ op1; -- op1
940
941
  if (oper == TOK_DECR || oper == TOK_INCR) {
941
 
    if (! isLvalue (op1)) 
 
942
    if (! isLvalue (op1)) { 
942
943
      SEM_ERROR__non_lvalue (node);
943
 
    else {
944
 
      if (! isModifiable (t1, pos))
945
 
        if (oper == TOK_DECR)
 
944
    } else {
 
945
      if (! isModifiable (t1, pos)) {
 
946
        if (oper == TOK_DECR) {
946
947
          SEM_WARNING (node, "decrement of unmodifiable location");
947
 
        else
 
948
        } else {
948
949
          SEM_WARNING (node, "increment of unmodifiable location");
949
 
      if (! t1->isScalar ())
 
950
        }
 
951
      }
 
952
      if (! t1->isScalar ()) {
950
953
        SEM_ERROR__invalid_op (node, "unary", op);
951
 
      else
 
954
      } else
952
955
        result = t1->VirtualType ();
953
956
    }
954
957
  }
955
958
  // + op1; - op1; ~ op1
956
959
  else if (oper == TOK_PLUS || oper == TOK_MINUS || oper == TOK_TILDE) {
957
960
    t1 = promote (op1, node);
958
 
    if (! t1->isArithmetic () || (oper == TOK_TILDE && ! t1->isInteger ()))
 
961
    if (! t1->isArithmetic () || (oper == TOK_TILDE && ! t1->isInteger ())) {
959
962
      SEM_ERROR__invalid_op (node, "unary", op);
960
 
    else {
 
963
    } else {
961
964
      if (v1) 
962
965
        node->setValue (v1->compute (oper));
963
966
      result = t1;
965
968
  }
966
969
  // ! op1
967
970
  else if (oper == TOK_NOT) {
968
 
    if (! t1->isScalar ())
 
971
    if (! t1->isScalar ()) {
969
972
      SEM_ERROR__invalid_op (node, "unary", op);
970
 
    else {
 
973
    } else {
971
974
      if (v1) {
972
975
        node->setValue (v1->compute (oper));
973
976
        if (t1 != &CTYPE_INT) // must have type `int'
1036
1039
  conv_to_ptr = ctp_old;
1037
1040
  pos = node->Son (1)->token_node ()->Number ();
1038
1041
 
1039
 
  if (! t1->isPointer ())
 
1042
  if (! t1->isPointer ()) {
1040
1043
    SEM_ERROR__invalid_op (node, "unary", "*");
1041
 
  else {
 
1044
  } else {
1042
1045
    if (! isPtrToObj (t1, pos))
1043
1046
      SEM_WARNING (node, "dereferencing pointer to incomplete type");
1044
1047
    result = t1->VirtualType ()->BaseType ();
1069
1072
  oper = node->Son (1)->token ()->type ();
1070
1073
  pos = node->Son (1)->token_node ()->Number ();
1071
1074
  
 
1075
  // don't apply lvalue-to-rvalue conversion
 
1076
  if (oper == TOK_DECR || oper == TOK_INCR)
 
1077
    conv_to_ptr = 3;
 
1078
 
1072
1079
  // resolve operand
1073
1080
  t1 = resolveExpr (node->Son (0), node); 
1074
1081
    
1075
1082
  // postfix in-/decrement: op1 ++; op1 --
1076
 
  if (! isLvalue (node->Son (0))) 
 
1083
  if (! isLvalue (node->Son (0))) { 
1077
1084
    SEM_ERROR__non_lvalue (node);
1078
 
  else {
1079
 
    if (! isModifiable (t1, pos))
1080
 
      if (oper == TOK_DECR)
 
1085
  } else {
 
1086
    if (! isModifiable (t1, pos)) {
 
1087
      if (oper == TOK_DECR) {
1081
1088
        SEM_WARNING (node, "decrement of unmodifiable location");
1082
 
      else
 
1089
      } else {
1083
1090
        SEM_WARNING (node, "increment of unmodifiable location");
1084
 
    if (! t1->isScalar ())
 
1091
      }
 
1092
    }
 
1093
    if (! t1->isScalar ()) {
1085
1094
      SEM_ERROR__invalid_op (node, "unary", op);
1086
 
    else
 
1095
    } else
1087
1096
      result = t1->VirtualType ();
1088
1097
  }
1089
1098
 
1116
1125
  pos = node->Son (0)->token_node ()->Number ();
1117
1126
    
1118
1127
  // array subscripting: op1 [ op2 ]
1119
 
  if (! (isPtrToObj (t1, pos) && t2->isInteger ())) 
 
1128
  if (! (isPtrToObj (t1, pos) && t2->isInteger ())) { 
1120
1129
    SEM_ERROR__invalid_op (node, "array subscript", "[]");
1121
 
  else 
 
1130
  } else 
1122
1131
    result = t1->VirtualType ()->BaseType ();
1123
1132
 
1124
1133
  node->setTypeRef (result);
1154
1163
  }
1155
1164
  
1156
1165
  // sizeof op1; sizeof ( op1 )
1157
 
  if (t1->isFunction () || ! t1->isComplete (pos) ||
1158
 
      (info ? info->TypeInfo ()->TypeBitField () : false)) 
 
1166
  if (t1->isFunction () || (info ? info->TypeInfo ()->TypeBitField () : false)) { 
1159
1167
    SEM_ERROR__invalid_op (node, "unary", "sizeof");
1160
 
  else {
 
1168
  } else {
1161
1169
    result = CTypeInfo::CTYPE_SIZE_T; // size_t
1162
1170
    size = t1->Size (); // size in bits
1163
 
    node->setValue (new CConstant (size / 8, result));
 
1171
    if (size / 8) {
 
1172
      node->setValue (new CConstant (size / 8, result));
 
1173
    }
1164
1174
  }
1165
1175
 
1166
1176
  node->setTypeRef (result);
1222
1232
    else
1223
1233
      result = (l?t2:t3);
1224
1234
  } else if (t2->isPointer () && t3->isPointer ()) {
1225
 
    if (! compatibleBase (t2, t3))
 
1235
    if (! compatibleBase (t2, t3)) {
1226
1236
      SEM_ERROR__type_mismatch (node, "conditional expression");
1227
 
    else if (t2->isConst () != t3->isConst () ||
 
1237
    } else if (t2->isConst () != t3->isConst () ||
1228
1238
             t2->isVolatile () != t3->isVolatile () ||
1229
1239
             t2->isRestrict () != t3->isRestrict ())
1230
1240
      result = new CTypeQualified (t2->VirtualType ()->BaseType ()->Duplicate (), 
1286
1296
  t2 = resolveExpr (node->Expr (), node); 
1287
1297
 
1288
1298
  // cast operator; ( op1 ) op2
1289
 
  if (! (t1 && ((t1->isScalar () && t2->isScalar ()) || t1->isVoid ()))) 
 
1299
  if (! (t1 && ((t1->isScalar () && t2->isScalar ()) || t1->isVoid ()))) { 
1290
1300
    SEM_ERROR (node, "invalid cast");
1291
 
  else {
 
1301
  } else {
1292
1302
    if (*t1 != *t2) {
1293
1303
      // cast constant value if any
1294
1304
      value = node->Expr ()->Value ();
1331
1341
  ctp_old = conv_to_ptr;
1332
1342
  conv_to_ptr = 1;
1333
1343
 
 
1344
  // don't apply lvalue-to-rvalue conversion
 
1345
  if (oper == TOK_DOT)
 
1346
    conv_to_ptr = 3;
 
1347
 
1334
1348
  // resolve operands
1335
1349
  t1 = resolveExpr (node->Son (0), node); 
1336
1350
  conv_to_ptr = ctp_old;
1337
1351
  
1338
1352
  // op1 -> op2
1339
1353
  if (oper == TOK_PTS) {
1340
 
    if (! (isPtrToObj (t1, pos) && t1->VirtualType ()->BaseType ()->isRecord ())) 
 
1354
    if (! (isPtrToObj (t1, pos) && t1->VirtualType ()->BaseType ()->isRecord ())) { 
1341
1355
      SEM_ERROR__invalid_op (node, "binary", "->");
1342
 
    else {
1343
 
      t2 = t1->VirtualType ()->BaseType ();
 
1356
    } else {
 
1357
      t2 = t1->VirtualType ()->BaseType ()->VirtualType ();
1344
1358
      sinfo = t2->TypeRecord ()->Record ();
1345
1359
    }
1346
1360
  // op1 . op2
1347
1361
  } else {
1348
 
    if (! (t1->isRecord () && t1->isComplete (pos))) 
 
1362
    if (! (t1->isRecord () && t1->isComplete (pos))) { 
1349
1363
      SEM_ERROR__invalid_op (node, "binary", ".");
1350
 
    else {
 
1364
    } else {
1351
1365
      t2 = t1->VirtualType ();
1352
1366
      sinfo = t2->TypeRecord ()->Record ();
1353
1367
    }
1377
1391
      
1378
1392
      member->setTypeRef (t2);
1379
1393
      member->Object (info);
 
1394
      node->Object (info);
1380
1395
      if (t2->isConst ()) {
1381
1396
        CT_ExprList *el = info->Init ();
1382
1397
        if (el && el->Value ())
1423
1438
  conv_to_ptr = ctp_old;
1424
1439
  
1425
1440
  // function call: op1 ( op2 , .. )
1426
 
  if (! (t1->isPointer () && t1->VirtualType ()->BaseType ()->isFunction ()))
 
1441
  if (! (t1->isPointer () && t1->VirtualType ()->BaseType ()->isFunction ())) {
1427
1442
    SEM_ERROR (node, "called object is not a function");
1428
 
  else {
 
1443
  } else {
1429
1444
    ftype = t1->VirtualType ()->BaseType ()->VirtualType ()->TypeFunction ();
1430
1445
    result = ftype->ReturnType ();
1431
1446
    ptypes = ftype->ArgTypes ();
1440
1455
        if (pnum) {
1441
1456
          if (ptypes->Entry (0)->isVoid ()) {
1442
1457
            if (anum) 
1443
 
              SEM_ERROR__num_args_too (node, "many", finfo);
1444
 
          } else if (anum < pnum)
1445
 
            SEM_ERROR__num_args_too (node, "few", finfo);
 
1458
              SEM_ERROR__num_args_too (node, "many", anum, finfo);
 
1459
          } else if (anum < (pnum - (ptypes->Entry (pnum-1)->is_ellipsis () ? 1 : 0)))
 
1460
            SEM_ERROR__num_args_too (node, "few", anum, finfo);
1446
1461
        } else
1447
1462
          skip = true;
1448
1463
      } else
1464
1479
        if (! skip) {
1465
1480
          // argument excess
1466
1481
          if (pnum < i+1) { 
1467
 
            SEM_ERROR__num_args_too (node, "many", finfo);
 
1482
            SEM_ERROR__num_args_too (node, "many", (i+1), finfo);
1468
1483
            skip = true;
1469
1484
            continue;
1470
1485
          }
1479
1494
          v = arg->Value () ? arg->Value ()->Constant () : 0;
1480
1495
          if (tp->isScalar ()) {
1481
1496
            if (tp->isArithmetic () && ta->isArithmetic ()) {
1482
 
              if (! compatible (tp, ta))
 
1497
              if (*tp != *ta)
1483
1498
                cast_to (tp->VirtualType (), arg, args);
1484
 
            } else if (! (tp->isPointer () && ta->isPointer () && 
1485
 
                          (compatibleBase (tp, ta) ||
1486
 
                             tp->VirtualType ()->BaseType ()->isVoid () || 
1487
 
                           ta->VirtualType ()->BaseType ()->isVoid ()) &&
1488
 
                          (ta->isConst () ? tp->isConst () : true) &&
1489
 
                          (ta->isVolatile () ? tp->isVolatile () : true) &&
1490
 
                          (ta->isRestrict () ? tp->isRestrict () : true)) &&
1491
 
                       ! (tp->isPointer () && ta->isInteger () && v && v->isNull ()) &&
1492
 
                       ! (tp->VirtualType ()->is_bool () && ta->isPointer ())) {
 
1499
            } else if (! compatible (tp, ta, v)) {
1493
1500
              SEM_ERROR__invalid_arg (arg, i+1, finfo);
1494
 
            } else if (! compatible (tp, ta))
 
1501
            } else if (*tp != *ta)
1495
1502
              cast_to (tp->VirtualType (), arg, args);
1496
1503
          } else if (tp->isRecord ()) {
1497
 
            if (! compatible (tp, ta))
 
1504
            if (! compatible (tp, ta, v))
1498
1505
              SEM_ERROR__invalid_arg (arg, i+1, finfo);
1499
1506
          } else
1500
1507
            SEM_ERROR__invalid_arg (arg, i+1, finfo);
1575
1582
  type = objs.top ().type;
1576
1583
  pos = node->token_node ()->Number ();
1577
1584
  if (type->isVarArray () || (! type->isObject (pos) &&
1578
 
      ! (type->isArray () && ! type->Dimension () && 
 
1585
      ! (type->isArray () && ! type->isComplete () && 
1579
1586
         type->VirtualType ()->BaseType ()->isObject (pos)))) {
1580
 
    if (type->isFunction ())
 
1587
    if (type->isFunction ()) {
1581
1588
      SEM_ERROR__init (node, info, "function-type");
1582
 
    else if (! type->isComplete (pos))
 
1589
    } else if (! type->isComplete (pos)) {
1583
1590
      SEM_ERROR__init (node, info, "incomplete-type");
1584
 
    else
 
1591
    } else {
1585
1592
      SEM_ERROR__init (node, info, "variable-sized");
 
1593
    }
1586
1594
  }    
1587
1595
 
1588
1596
  // init_clause: [=] { init_list }
1736
1744
      return;
1737
1745
    } else {
1738
1746
      size = ++objs.top ().size;
1739
 
      if (type->isFixedArray () && type->Dimension () < size)
 
1747
      if (type->isFixedArray () && type->Dimension () < size) {
1740
1748
        SEM_ERROR (item, "too many elements in fixed-size array initializer");
1741
 
      else if (! type->isFixedArray () && type->Dimension () < size)
 
1749
      } else if (! type->isFixedArray () && type->Dimension () < size)
1742
1750
        type->VirtualType ()->TypeArray ()->Dimension (size);
1743
1751
      pushSubObj (type, obj, objs);
1744
1752
    }
1767
1775
      if (braced)
1768
1776
        return;
1769
1777
    } else { // curr has no members (?)
1770
 
      if (*type == *info->TypeInfo ())
 
1778
      if (*type == *info->TypeInfo ()) {
1771
1779
        SEM_ERROR (item, "too many elements in record initializer");
1772
 
      else {
 
1780
      } else {
1773
1781
        popSubObj (type, curr, obj, objs);
1774
1782
        findNext (item, type, curr, obj, info, objs, braced);
1775
1783
      }
1863
1871
    
1864
1872
  if (type->isScalar ()) {
1865
1873
    if (type->isArithmetic () && t2->isArithmetic ()) {
1866
 
      if (! compatible (type, t2))
 
1874
      if (*type != *t2)
1867
1875
        cast_to (type->VirtualType (), node, base);
1868
 
    } else if (! (type->isPointer () && t2->isPointer () && 
1869
 
                  (compatibleBase (type, t2) ||
1870
 
                     type->VirtualType ()->BaseType ()->isVoid () || 
1871
 
                   t2->VirtualType ()->BaseType ()->isVoid ()) &&
1872
 
                  (t2->isConst () ? type->isConst () : true) &&
1873
 
                  (t2->isVolatile () ? type->isVolatile () : true) &&
1874
 
                  (t2->isRestrict () ? type->isRestrict () : true)) &&
1875
 
               ! (type->isPointer () && t2->isInteger () && v && v->isNull ()) &&
1876
 
               ! (type->VirtualType ()->is_bool () && t2->isPointer ())) {
 
1876
    } else if (! compatible (type, t2, v)) {
1877
1877
      SEM_ERROR (node, "invalid initializer");
1878
 
    } else if (! compatible (type, t2))
 
1878
    } else if (*type != *t2)
1879
1879
      cast_to (type->VirtualType (), node, base);
1880
1880
  } else if (type->isArray ()) {
1881
1881
    t2 = t2->VirtualType ();
1892
1892
    } else 
1893
1893
      SEM_ERROR (node, "invalid initializer");
1894
1894
  } else if (type->isRecord ()) {
1895
 
    if (! compatible (type, t2))
 
1895
    if (! compatible (type, t2, v))
1896
1896
      SEM_ERROR (node, "invalid initializer");
1897
1897
  } else
1898
1898
    SEM_ERROR (node, "invalid initializer");
2025
2025
 
2026
2026
 
2027
2027
 
 
2028
bool CSemExpr::compatible (CTypeInfo *t1, CTypeInfo *t2, CConstant* value) {
 
2029
  t1 = t1->VirtualType ();
 
2030
  t2 = t2->VirtualType ();
 
2031
  
 
2032
  if (t1->isArithmetic () && t2->isArithmetic ()) {
 
2033
    // arithmetic types are compatible
 
2034
    return true;
 
2035
  }
 
2036
  if (t1->is_bool () && t2->isScalar ()) {
 
2037
    // boolean and scalar types are compatible
 
2038
    return true;
 
2039
  }
 
2040
  if ((t1->isPointer () && t2->isInteger ()) ||
 
2041
      (t1->isInteger () && t2->isPointer ())) {
 
2042
    // pointer and integer types are compatible
 
2043
    return true;
 
2044
  } 
 
2045
  if (t1->isPointer () && t2->isPointer ()) {
 
2046
    // null pointer constant is compatible to any pointer
 
2047
    if (value && value->isNull ()) {
 
2048
      return true;
 
2049
    } 
 
2050
    // pointer to void is compatible to pointer to char type
 
2051
    if ((t1->BaseType ()->isVoid () && t2->BaseType ()->VirtualType ()->is_char ()) ||
 
2052
        (t2->BaseType ()->isVoid () && t1->BaseType ()->VirtualType ()->is_char ())) {
 
2053
      return true;
 
2054
    }
 
2055
    // other pointer types are compatible to pointer to void
 
2056
    if (t1->BaseType ()->isVoid ()) {
 
2057
      return true;
 
2058
    }
 
2059
    // base types and qualifier have to be compatible
 
2060
    return compatibleBase (t1, t2) &&
 
2061
      (t2->isConst () ? t1->isConst () : true) &&
 
2062
      (t2->isVolatile () ? t1->isVolatile () : true) &&
 
2063
      (t2->isRestrict () ? t1->isRestrict () : true);
 
2064
  } 
 
2065
  if (t1->isFunction () && t2->isFunction ()) {
 
2066
    // return type and parameter list have to be compatible
 
2067
    // NO FUNCTION PARAMETER PROMOTION AT THE MOMENT
 
2068
    return compatibleBase (t1, t2) &&
 
2069
      t1->TypeFunction ()->ArgTypes ()->Entries () ==
 
2070
      t2->TypeFunction ()->ArgTypes ()->Entries ();
 
2071
  }
 
2072
  if (*t1 == *t2) {
 
2073
    // types are equal
 
2074
    return true; 
 
2075
  }
 
2076
 
 
2077
  return false;
 
2078
}
 
2079
 
 
2080
 
 
2081
CTypeInfo* CSemExpr::applyImplicitConv (CTree* expr, CTree* base, CTypeInfo* type) {
 
2082
  // conv_to_ptr is 0 if argument of address or sizeof expression
 
2083
  // conv_to_ptr is 2 if initializer of array
 
2084
  // conv_to_ptr is 3 if left operand of assignment, ++, --, or . operator
 
2085
  // conv_to_ptr is 1 otherwise
 
2086
  const char *id = expr->NodeName ();
 
2087
 
 
2088
  // implicit array and function type conversions
 
2089
  if (type->isArray () || type->isFunction ()) {
 
2090
    if (conv_to_ptr > 0 && ! (conv_to_ptr == 2 && 
 
2091
        (id == CT_String::NodeId () || id == CT_WideString::NodeId ()))) {
 
2092
      type = type->isArray () ? type->VirtualType ()->BaseType () : type;
 
2093
      type = new CTypePointer (type->Duplicate ());
 
2094
      cast_to (type, expr, base, false);
 
2095
      conv_to_ptr = 1;
 
2096
    }
 
2097
  // implicit lvalue to rvalue conversions
 
2098
  } else if (conv_to_ptr != 3) {
 
2099
    if (type->isQualified ()) {
 
2100
      type = type->UnqualType ()->Duplicate ();
 
2101
      cast_to (type, expr, base, false);
 
2102
    }
 
2103
    conv_to_ptr = 1;
 
2104
  } else 
 
2105
    conv_to_ptr = 1;
 
2106
  
 
2107
  return type;
 
2108
}
 
2109
 
 
2110
 
 
2111
 
2028
2112
CTypeInfo *CSemExpr::cast_to (CTypeInfo *type, CTree *node, CTree *base, bool ref) {
2029
2113
  CT_ImplicitCast *cast;
2030
2114
  CExprValue *value;
2077
2161
    if (info) {
2078
2162
      if (info->ArgumentInfo ()) 
2079
2163
        return true;
 
2164
      if (info->EnumeratorInfo ())
 
2165
        return false;
2080
2166
      type = info->TypeInfo ();
2081
2167
      return type && ! type->isFunction ();
2082
2168
    }
2105
2191
    return true;
2106
2192
//  } else if (id == CT_AddrExpr::NodeId () || 
2107
2193
//             id == CT_CastExpr::NodeId () ||
2108
 
//             id == CT_ImplicitCast::NodeId () ||
2109
2194
//             id == CT_IfThenExpr::NodeId () ||
2110
2195
//             id == CT_SizeofExpr::NodeId () ||
2111
2196
//             id == CT_Integer::NodeId () ||
2115
2200
//             id == CT_Bool::NodeId () ||
2116
2201
//             id == CT_CallExpr::NodeId ()) {
2117
2202
//    return false;
 
2203
  } else if (id == CT_ImplicitCast::NodeId ()) {
 
2204
    return isLvalue (node->Son (0));
2118
2205
  } 
2119
2206
  return false;
2120
2207
}