diff --git a/CHANGELOG.md b/CHANGELOG.md index 357b4683..27b5bb28 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -26,6 +26,8 @@ ### Fixed +- Fixed end of scope for `CRITICAL` keyword blocks + ([#255](https://github.com/fortran-lang/fortls/issues/255)) - Fixed bug where completion of interfaces in USE ONLY would produce the snippet ([#150](https://github.com/fortran-lang/fortls/issues/150)) - Fixed bug where diagnostic messages were raised for non-existent variables diff --git a/fortls/regex_patterns.py b/fortls/regex_patterns.py index 2a3bd6c4..d6611f30 100644 --- a/fortls/regex_patterns.py +++ b/fortls/regex_patterns.py @@ -40,8 +40,8 @@ class FortranRegularExpressions: SUBMOD: Pattern = compile(r"[ ]*SUBMODULE[ ]*\(", I) END_SMOD: Pattern = compile(r"SUBMODULE", I) END_PRO: Pattern = compile(r"(MODULE)?[ ]*PROCEDURE", I) - BLOCK: Pattern = compile(r"[ ]*([a-z_]\w*[ ]*:[ ]*)?BLOCK(?!\w)", I) - END_BLOCK: Pattern = compile(r"BLOCK", I) + BLOCK: Pattern = compile(r"[ ]*([a-z_]\w*[ ]*:[ ]*)?BLOCK|CRITICAL(?!\w)", I) + END_BLOCK: Pattern = compile(r"BLOCK|CRITICAL", I) DO: Pattern = compile(r"[ ]*(?:[a-z_]\w*[ ]*:[ ]*)?DO([ ]+[0-9]*|$)", I) END_DO: Pattern = compile(r"DO", I) WHERE: Pattern = compile(r"[ ]*WHERE[ ]*\(", I) @@ -64,7 +64,7 @@ class FortranRegularExpressions: INT: Pattern = compile(r"[ ]*(ABSTRACT)?[ ]*INTERFACE[ ]*(\w*)", I) END_INT: Pattern = compile(r"INTERFACE", I) END_WORD: Pattern = compile( - r"[ ]*END[ ]*(DO|WHERE|IF|BLOCK|ASSOCIATE|SELECT" + r"[ ]*END[ ]*(DO|WHERE|IF|BLOCK|CRITICAL|ASSOCIATE|SELECT" r"|TYPE|ENUM|MODULE|SUBMODULE|PROGRAM|INTERFACE" r"|SUBROUTINE|FUNCTION|PROCEDURE|FORALL)?([ ]+(?!\W)|$)", I, diff --git a/test/test_server_diagnostics.py b/test/test_server_diagnostics.py index bd4b4631..44c254d3 100644 --- a/test/test_server_diagnostics.py +++ b/test/test_server_diagnostics.py @@ -428,3 +428,15 @@ def test_attribute_and_variable_name_collision(): errcode, results = run_request(string, ["-n", "1"]) assert errcode == 0 assert results[1]["diagnostics"] == [] + + +def test_critical_scope(): + """Test that critical scopes are correctly parsed.""" + string = write_rpc_request(1, "initialize", {"rootPath": str(test_dir / "diag")}) + file_path = str(test_dir / "diag" / "tst_critical.f90") + string += write_rpc_notification( + "textDocument/didOpen", {"textDocument": {"uri": file_path}} + ) + errcode, results = run_request(string, ["-n", "1"]) + assert errcode == 0 + assert results[1]["diagnostics"] == [] diff --git a/test/test_source/diag/test_critical.f90 b/test/test_source/diag/test_critical.f90 new file mode 100644 index 00000000..819dbbf5 --- /dev/null +++ b/test/test_source/diag/test_critical.f90 @@ -0,0 +1,7 @@ +program test_critical + implicit none + if (.true.) then + critical + end critical + end if +end program test_critical