diff --git a/Configuration/GlobalAssemblyInfo.cs b/Configuration/GlobalAssemblyInfo.cs index 7a5df8825..9aa91f9d5 100644 --- a/Configuration/GlobalAssemblyInfo.cs +++ b/Configuration/GlobalAssemblyInfo.cs @@ -15,7 +15,7 @@ internal static class RevisionClass public const string Major = "3"; public const string Minor = "1"; public const string Build = "0"; - public const string Revision = "1218"; + public const string Revision = "1223"; public const string MainVersion = Major + "." + Minor; public const string FullVersion = Major + "." + Minor + "." + Build + "." + Revision; diff --git a/Configuration/Version.defs b/Configuration/Version.defs index 83e17eb60..25594fb27 100644 --- a/Configuration/Version.defs +++ b/Configuration/Version.defs @@ -1,4 +1,4 @@ -%MINOR%=1 -%REVISION%=1218 %COREVERSION%=0 +%REVISION%=1223 +%MINOR%=1 %MAJOR%=3 diff --git a/Localization/DefaultLang.resources b/Localization/DefaultLang.resources index ca884233c..49ac4ca6a 100644 Binary files a/Localization/DefaultLang.resources and b/Localization/DefaultLang.resources differ diff --git a/Parsers/PascalABCParserNewSaushkin/ABCPascal.cs b/Parsers/PascalABCParserNewSaushkin/ABCPascal.cs index 04ecb2a6e..3ff6089e6 100644 --- a/Parsers/PascalABCParserNewSaushkin/ABCPascal.cs +++ b/Parsers/PascalABCParserNewSaushkin/ABCPascal.cs @@ -2,7 +2,7 @@ // This CSharp output file generated by Gardens Point LEX // Version: 1.1.3.301 // Machine: SSM -// DateTime: 13.04.2016 11:35:20 +// DateTime: 18.04.2016 14:09:33 // UserName: ????????? // GPLEX input file // GPLEX frame file diff --git a/Parsers/PascalABCParserNewSaushkin/ABCPascal.y b/Parsers/PascalABCParserNewSaushkin/ABCPascal.y index b223e8dc7..acd06c5d4 100644 --- a/Parsers/PascalABCParserNewSaushkin/ABCPascal.y +++ b/Parsers/PascalABCParserNewSaushkin/ABCPascal.y @@ -3654,6 +3654,42 @@ lambda_function_body { $$ = $1; } + | if_stmt + { + $$ = new statement_list($1 as statement, @$); + } + | while_stmt + { + $$ = new statement_list($1 as statement, @$); + } + | repeat_stmt + { + $$ = new statement_list($1 as statement, @$); + } + | for_stmt + { + $$ = new statement_list($1 as statement, @$); + } + | foreach_stmt + { + $$ = new statement_list($1 as statement, @$); + } + | case_stmt + { + $$ = new statement_list($1 as statement, @$); + } + | try_stmt + { + $$ = new statement_list($1 as statement, @$); + } + | lock_stmt + { + $$ = new statement_list($1 as statement, @$); + } + | yield_stmt + { + $$ = new statement_list($1 as statement, @$); + } ; lambda_procedure_body @@ -3665,7 +3701,7 @@ lambda_procedure_body { $$ = $1; } - | if_stmt + | if_stmt { $$ = new statement_list($1 as statement, @$); } diff --git a/Parsers/PascalABCParserNewSaushkin/ABCPascalYacc.cs b/Parsers/PascalABCParserNewSaushkin/ABCPascalYacc.cs index 53a2a0da8..b909af5e7 100644 --- a/Parsers/PascalABCParserNewSaushkin/ABCPascalYacc.cs +++ b/Parsers/PascalABCParserNewSaushkin/ABCPascalYacc.cs @@ -2,9 +2,9 @@ // GPPG version 1.3.6 // Machine: SSM -// DateTime: 13.04.2016 11:35:20 +// DateTime: 18.04.2016 14:09:33 // UserName: ????????? -// Input file +// Input file // options: no-lines gplex @@ -56,7 +56,7 @@ public abstract class ScanBase : AbstractScanner { - // Verbatim content from D:\PascalABC.NET\!PABC_Git\Parsers\PascalABCParserNewSaushkin\ABCPascal.y + // Verbatim content from ABCPascal.y // ��� ���������� ����������� � ����� GPPGParser, �������������� ����� ������, ������������ �������� gppg public syntax_tree_node root; // �������� ���� ��������������� ������ @@ -68,13 +68,13 @@ public partial class GPPGParser: ShiftReduceParser scanner) : base(scanner) { } - // End verbatim content from D:\PascalABC.NET\!PABC_Git\Parsers\PascalABCParserNewSaushkin\ABCPascal.y + // End verbatim content from ABCPascal.y #pragma warning disable 649 private static Dictionary aliasses; #pragma warning restore 649 - private static Rule[] rules = new Rule[796]; - private static State[] states = new State[1267]; + private static Rule[] rules = new Rule[805]; + private static State[] states = new State[1276]; private static string[] nonTerms = new string[] { "parse_goal", "unit_key_word", "assignment", "optional_array_initializer", "attribute_declarations", "ot_visibility_specifier", "one_attribute", "attribute_variable", @@ -150,13 +150,13 @@ public partial class GPPGParser: ShiftReduceParser proc_call + case 784: // lambda_function_body -> if_stmt { CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); } break; - case 785: // lambda_procedure_body -> compound_stmt + case 785: // lambda_function_body -> while_stmt +{ + CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); + } + break; + case 786: // lambda_function_body -> repeat_stmt +{ + CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); + } + break; + case 787: // lambda_function_body -> for_stmt +{ + CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); + } + break; + case 788: // lambda_function_body -> foreach_stmt +{ + CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); + } + break; + case 789: // lambda_function_body -> case_stmt +{ + CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); + } + break; + case 790: // lambda_function_body -> try_stmt +{ + CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); + } + break; + case 791: // lambda_function_body -> lock_stmt +{ + CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); + } + break; + case 792: // lambda_function_body -> yield_stmt +{ + CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); + } + break; + case 793: // lambda_procedure_body -> proc_call +{ + CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); + } + break; + case 794: // lambda_procedure_body -> compound_stmt { CurrentSemanticValue.stn = ValueStack[ValueStack.Depth-1].stn; } break; - case 786: // lambda_procedure_body -> if_stmt + case 795: // lambda_procedure_body -> if_stmt { CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); } break; - case 787: // lambda_procedure_body -> while_stmt + case 796: // lambda_procedure_body -> while_stmt { CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); } break; - case 788: // lambda_procedure_body -> repeat_stmt + case 797: // lambda_procedure_body -> repeat_stmt { CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); } break; - case 789: // lambda_procedure_body -> for_stmt + case 798: // lambda_procedure_body -> for_stmt { CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); } break; - case 790: // lambda_procedure_body -> foreach_stmt + case 799: // lambda_procedure_body -> foreach_stmt { CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); } break; - case 791: // lambda_procedure_body -> case_stmt + case 800: // lambda_procedure_body -> case_stmt { CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); } break; - case 792: // lambda_procedure_body -> try_stmt + case 801: // lambda_procedure_body -> try_stmt { CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); } break; - case 793: // lambda_procedure_body -> lock_stmt + case 802: // lambda_procedure_body -> lock_stmt { CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); } break; - case 794: // lambda_procedure_body -> yield_stmt + case 803: // lambda_procedure_body -> yield_stmt { CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); } break; - case 795: // lambda_procedure_body -> assignment + case 804: // lambda_procedure_body -> assignment { CurrentSemanticValue.stn = new statement_list(ValueStack[ValueStack.Depth-1].stn as statement, CurrentLocationSpan); } diff --git a/Parsers/PascalABCParserNewSaushkin/PABC.tags b/Parsers/PascalABCParserNewSaushkin/PABC.tags index 89f4844fa..3261da1fb 100644 --- a/Parsers/PascalABCParserNewSaushkin/PABC.tags +++ b/Parsers/PascalABCParserNewSaushkin/PABC.tags @@ -34,7 +34,6 @@ - diff --git a/Parsers/PascalABCParserNewSaushkin/PABC.ymc b/Parsers/PascalABCParserNewSaushkin/PABC.ymc index b20934ab4..3066661de 100644 --- a/Parsers/PascalABCParserNewSaushkin/PABC.ymc +++ b/Parsers/PascalABCParserNewSaushkin/PABC.ymc @@ -128,6 +128,8 @@ script= + + diff --git a/ReleaseGenerators/PascalABCNET_version.nsh b/ReleaseGenerators/PascalABCNET_version.nsh index 20bc42797..0baa94258 100644 --- a/ReleaseGenerators/PascalABCNET_version.nsh +++ b/ReleaseGenerators/PascalABCNET_version.nsh @@ -1 +1 @@ -!define VERSION '3.1.0.1218' +!define VERSION '3.1.0.1223' diff --git a/TestSuite/CompilationSamples/LambdaProc1.pas b/TestSuite/CompilationSamples/LambdaProc1.pas new file mode 100644 index 000000000..9265a69c0 --- /dev/null +++ b/TestSuite/CompilationSamples/LambdaProc1.pas @@ -0,0 +1,3 @@ +begin + Arr(1,2,3).ForEach(x -> Print(x)); +end. \ No newline at end of file diff --git a/TestSuite/CompilationSamples/LambdaProc2.pas b/TestSuite/CompilationSamples/LambdaProc2.pas new file mode 100644 index 000000000..31785a18d --- /dev/null +++ b/TestSuite/CompilationSamples/LambdaProc2.pas @@ -0,0 +1,3 @@ +begin + Arr(1,2,3).ForEach(x -> if x>1 then Print(x)); +end. \ No newline at end of file diff --git a/TestSuite/CompilationSamples/PABCSystem.pas b/TestSuite/CompilationSamples/PABCSystem.pas index 4490a483e..dcfd6466d 100644 --- a/TestSuite/CompilationSamples/PABCSystem.pas +++ b/TestSuite/CompilationSamples/PABCSystem.pas @@ -111,7 +111,7 @@ type /// Представляет кортеж Tuple = System.Tuple; - /// Представляет динамический массив + /// Представляет список на базе динамического массива List = System.Collections.Generic.List; /// Представляет базовый класс для реализации интерфейса IComparer @@ -7781,13 +7781,15 @@ end; // ----------------------------------------------------- // Дополнения февраль 2016: Iterate, Step, &Repeat, Cycle -/// Возвращает бесконечную рекуррентную последовательность элементов, задаваемую начальным элементом и функцией next +// Возвращает бесконечную рекуррентную последовательность элементов, задаваемую начальным элементом и функцией next +///-- function Iterate(Self: T; next: T -> T): sequence of T; extensionmethod; begin Result := Iterate&(Self,next); end; -/// Возвращает бесконечную рекуррентную последовательность элементов, задаваемую начальным элементом, следующим за ним элементом и функцией next +// Возвращает бесконечную рекуррентную последовательность элементов, задаваемую начальным элементом, следующим за ним элементом и функцией next +///-- function Iterate(Self,second: T; next: (T,T) -> T): sequence of T; extensionmethod; begin Result := Iterate&(Self,second,next); @@ -7813,7 +7815,8 @@ begin Result := IntNumbersClass.Create().Select(x->x*step+slf); end; -/// Возвращает бесконечную последовательность элементов, совпадающих с данным +// Возвращает бесконечную последовательность элементов, совпадающих с данным +///-- function &Repeat(Self: T): sequence of T; extensionmethod; begin Result := SeqFill(MaxInt,Self); diff --git a/TreeConverter/TreeConversion/syntax_tree_visitor.cs b/TreeConverter/TreeConversion/syntax_tree_visitor.cs index 83fb820d4..ba7001e74 100644 --- a/TreeConverter/TreeConversion/syntax_tree_visitor.cs +++ b/TreeConverter/TreeConversion/syntax_tree_visitor.cs @@ -5934,7 +5934,8 @@ namespace PascalABCCompiler.TreeConverter { expression_node bfcint = make_read_call(si, _method_call.parameters, subloc2); - if (!proc_wait) AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name); + if (!proc_wait) + AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name); switch (mot) { case motivation.expression_evaluation: @@ -6192,7 +6193,8 @@ namespace PascalABCCompiler.TreeConverter else if (SystemLibrary.SystemLibInitializer.IncProcedure.Equal(si)) { expression_node bfcint = make_inc_call(si, _method_call.parameters, subloc2); - if (!proc_wait) AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name); + if (!proc_wait) + AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name); switch (mot) { case motivation.expression_evaluation: @@ -6217,7 +6219,8 @@ namespace PascalABCCompiler.TreeConverter else if (SystemLibrary.SystemLibInitializer.DecProcedure.Equal(si)) { expression_node bfcint = make_dec_call(si, _method_call.parameters, subloc2); - if (!proc_wait) AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name); + if (!proc_wait) + AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name); switch (mot) { case motivation.expression_evaluation: @@ -6374,7 +6377,8 @@ namespace PascalABCCompiler.TreeConverter else if (si == SystemLibrary.SystemLibInitializer.NewProcedure) { expression_node bfcint = make_new_call(si, _method_call.parameters, subloc2); - if (!proc_wait) AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name); + if (!proc_wait) + AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name); switch (mot) { case motivation.expression_evaluation: @@ -6401,7 +6405,8 @@ namespace PascalABCCompiler.TreeConverter //if (convertion_data_and_alghoritms.select_function(convert_expression_list(_method_call.parameters.expressions), si, subloc2) == SystemLibrary.SystemLibInitializer.DisposeProcedure.sym_info) //{ expression_node bfcint = make_dispose_call(si, _method_call.parameters, subloc2); - if (!proc_wait) AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name); + if (!proc_wait) + AddError(subloc2, "FUNCTION_EXPECTED_PROCEDURE_{0}_MEET", (si.sym_info as function_node).name); switch (mot) { case motivation.expression_evaluation: @@ -18372,6 +18377,46 @@ namespace PascalABCCompiler.TreeConverter public override void visit(SyntaxTree.function_lambda_definition _function_lambda_definition) { + // SSM 18/04/16 попытка разрешить x->Print(x) + var stl = _function_lambda_definition.proc_body as SyntaxTree.statement_list; + if (_function_lambda_definition.return_type is lambda_inferred_type && stl != null && stl.list.Count == 1) + { + var ass = (_function_lambda_definition.proc_body as SyntaxTree.statement_list).list[0] as assign; + if (ass != null && ass.to is ident && (ass.to as ident).name.ToLower()=="result") + { + var f = ass.from; + if (f is method_call) + { + var ff = f as method_call; + // Надо посмотреть, как это делается для преобразования типов T(x). А пока так + expression_node qq = null; + delegated_methods dm = null; + try + { + qq = convert_strong(ff.dereferencing_value); + dm = qq.type as delegated_methods; + } + catch + { + // Погасить все исключения. Значит, не вывелось, и в правой части лямбды - не вызов процедуры, а скорее всего приведение типа T(x) + } + if (dm != null && dm.proper_methods != null && dm.proper_methods.Count > 0) + { + if (dm.proper_methods[0].ret_type == null) + { + // Очищаем от Result := + (_function_lambda_definition.proc_body as SyntaxTree.statement_list).list[0] = new procedure_call(ff, ff.source_context); // заменить result := Print(x) на Print(x) + _function_lambda_definition.return_type = null; + } + } + } + } + else // значит, первый и единственный оператор - не присваивание и это лямбда - процедура! + { + _function_lambda_definition.return_type = null; + } + } + _function_lambda_definition.RealSemTypeOfResExpr = null; // После первого присваивания Result она будет содержать тип type_node в правой части Result _function_lambda_definition.RealSemTypeOfResult = null; try diff --git a/bin/Lib/PABCRtl.dll b/bin/Lib/PABCRtl.dll index 7766428ae..273de3327 100644 Binary files a/bin/Lib/PABCRtl.dll and b/bin/Lib/PABCRtl.dll differ diff --git a/bin/Lib/PABCSystem.pas b/bin/Lib/PABCSystem.pas index 40a4abff2..dcfd6466d 100644 --- a/bin/Lib/PABCSystem.pas +++ b/bin/Lib/PABCSystem.pas @@ -111,7 +111,7 @@ type /// Представляет кортеж Tuple = System.Tuple; - /// Представляет список + /// Представляет список на базе динамического массива List = System.Collections.Generic.List; /// Представляет базовый класс для реализации интерфейса IComparer