Explorar el Código

* if an array constructor is passed to a formaldef parameter, it is passed as a set (if the conversion is possible), resolves #37796

git-svn-id: trunk@46973 -
florian hace 4 años
padre
commit
a628c1c3dd
Se han modificado 4 ficheros con 48 adiciones y 0 borrados
  1. 1 0
      .gitattributes
  2. 2 0
      compiler/htypechk.pas
  3. 7 0
      compiler/ncal.pas
  4. 38 0
      tests/webtbs/tw37796.pp

+ 1 - 0
.gitattributes

@@ -18475,6 +18475,7 @@ tests/webtbs/tw3777.pp svneol=native#text/plain
 tests/webtbs/tw37779.pp svneol=native#text/pascal
 tests/webtbs/tw3778.pp svneol=native#text/plain
 tests/webtbs/tw37780.pp svneol=native#text/plain
+tests/webtbs/tw37796.pp svneol=native#text/pascal
 tests/webtbs/tw3780.pp svneol=native#text/plain
 tests/webtbs/tw37806.pp svneol=native#text/pascal
 tests/webtbs/tw3782.pp svneol=native#text/plain

+ 2 - 0
compiler/htypechk.pas

@@ -1803,6 +1803,7 @@ implementation
                  mayberesettypeconvs;
                  exit;
                end;
+             arrayconstructorn,
              setconstn,
              stringconstn,
              guidconstn :
@@ -2106,6 +2107,7 @@ implementation
                  (tstringdef(def_to).encoding=tstringdef(p.resultdef).encoding) then
                 eq:=te_equal
             end;
+          formaldef,
           setdef :
             begin
               { set can also be a not yet converted array constructor }

+ 7 - 0
compiler/ncal.pas

@@ -1192,6 +1192,13 @@ implementation
                     (parasym.vardef.typ=setdef) then
                    inserttypeconv(left,parasym.vardef);
 
+                 { if an array constructor can be a set and it is passed to
+                   a formaldef, a set must be passed, see also issue #37796 }
+                 if (left.nodetype=arrayconstructorn) and
+                    (parasym.vardef.typ=formaldef) and
+                    (arrayconstructor_can_be_set(left)) then
+                   left:=arrayconstructor_to_set(left,false);
+
                  { set some settings needed for arrayconstructor }
                  if is_array_constructor(left.resultdef) then
                   begin

+ 38 - 0
tests/webtbs/tw37796.pp

@@ -0,0 +1,38 @@
+program tformal;
+{$mode objfpc}
+
+uses
+  sysutils;
+
+type
+  TFontStyle = (
+    fsItalic,
+    fsBold,
+    fsUnderlined,
+    fsStrikeOut
+  );
+  TFontStyles = set of TFontStyle;
+
+var aFS: TFontStyles;
+
+procedure Any(const Anything);
+begin
+  aFS:=aFS+TFontStyles(Anything);
+  Writeln(IntToHex(PLongInt(@Anything)^, 8));
+end;
+
+procedure DoIt;
+begin
+  Any([fsItalic, fsBold]); //unit1.pas(31,25) Error: Variable identifier expected
+  if aFS<>[fsItalic, fsBold] then
+    halt(1);
+  Any(Cardinal([fsItalic, fsBold])); //ok
+end;
+
+begin
+  aFS:=[];
+  writeln(Cardinal(aFS));
+  DoIt;
+  writeln(Cardinal(aFS));
+  writeln('ok');
+end.