Пример #1
0
def test_array_notation_rank():
    ''' Check that the _array_notation_rank() utility handles various examples
    of array notation.

    TODO #754 fix test so that 'disable_declaration_check' fixture is not
    required.
    '''
    fake_parent = Schedule()
    processor = Fparser2Reader()
    reader = FortranStringReader("  z1_st(:, 2, :) = ptsu(:, :, 3)")
    fparser2spec = Fortran2003.Assignment_Stmt(reader)
    processor.process_nodes(fake_parent, [fparser2spec])
    assert processor._array_notation_rank(fake_parent[0].lhs) == 2
    reader = FortranStringReader("  z1_st(:, :, 2, :) = ptsu(:, :, :, 3)")
    fparser2spec = Fortran2003.Assignment_Stmt(reader)
    processor.process_nodes(fake_parent, [fparser2spec])
    assert processor._array_notation_rank(fake_parent[1].lhs) == 3
    # We don't support bounds on slices
    reader = FortranStringReader("  z1_st(:, 1:n, 2, :) = ptsu(:, :, :, 3)")
    fparser2spec = Fortran2003.Assignment_Stmt(reader)
    processor.process_nodes(fake_parent, [fparser2spec])
    with pytest.raises(NotImplementedError) as err:
        processor._array_notation_rank(fake_parent[2].lhs)
    assert ("Only array notation of the form my_array(:, :, ...) is "
            "supported." in str(err.value))
Пример #2
0
def test_redundant_empty_only_list():
    ''' Check that we drop 'use's with an empty only list if they become
    redundant. #TODO #11 Check for appropriate logging messages here once
    logging is implemented. '''
    fake_parent = KernelSchedule("dummy_schedule")
    processor = Fparser2Reader()
    # Empty only-list followed by wildcard import
    reader = FortranStringReader("use mod1, only:\n" "use mod1\n")
    fparser2spec = Fortran2003.Specification_Part(reader)
    processor.process_declarations(fake_parent, fparser2spec.content, [])
    csym = fake_parent.symbol_table.lookup("mod1")
    assert csym.wildcard_import
    # Wildcard import followed by empty only-list
    reader = FortranStringReader("use mod2\n" "use mod2, only:\n")
    fparser2spec = Fortran2003.Specification_Part(reader)
    processor.process_declarations(fake_parent, fparser2spec.content, [])
    csym = fake_parent.symbol_table.lookup("mod2")
    assert csym.wildcard_import
    # Empty only-list followed by named import
    reader = FortranStringReader("use mod3, only:\n" "use mod3, only: fred\n")
    fparser2spec = Fortran2003.Specification_Part(reader)
    processor.process_declarations(fake_parent, fparser2spec.content, [])
    sym_table = fake_parent.symbol_table
    csym = sym_table.lookup("mod3")
    assert not csym.wildcard_import
    assert sym_table.imported_symbols(csym)[0].name == "fred"
    # Named import followed by empty only-list
    reader = FortranStringReader("use mod4, only: bob\n" "use mod4, only:\n")
    fparser2spec = Fortran2003.Specification_Part(reader)
    processor.process_declarations(fake_parent, fparser2spec.content, [])
    csym = sym_table.lookup("mod4")
    assert not csym.wildcard_import
    assert sym_table.imported_symbols(csym)[0].name == "bob"
Пример #3
0
def test_derived_type_codeblocks(f2008_parser):
    ''' Check that we create a CodeBlock if we encounter unsupported
    entries in a parse tree describing a derived-type access. We have
    to test with invalid content in two locations. '''
    code = ("subroutine my_sub()\n"
            "  use some_mod, only: my_type\n"
            "  type(my_type), dimension(3) :: var\n"
            "  var(1)%region%subgrid(3)%stop = 1\n"
            "end subroutine my_sub\n")
    processor = Fparser2Reader()
    # First create a valid parse tree.
    reader = FortranStringReader(code)
    fparser2spec = f2008_parser(reader)
    dref = Fortran2003.walk(fparser2spec, Fortran2003.Data_Ref)[0]
    # Now break the Data_Ref instance by modifying its first child. Requesting
    # a subset of items from a tuple appears to generate a new tuple so
    # explicitly create a list and then create a tuple from that.
    item_list = ["hello"] + list(dref.items[1:])
    dref.items = tuple(item_list)
    sched = processor.generate_schedule("my_sub", fparser2spec)
    cblocks = sched.walk(CodeBlock)
    assert len(cblocks) == 1
    assert isinstance(cblocks[0].parent, Assignment)
    # Repeat but this time break the Data_Ref by modifying its second child.
    reader = FortranStringReader(code)
    fparser2spec = f2008_parser(reader)
    dref = Fortran2003.walk(fparser2spec, Fortran2003.Data_Ref)[0]
    dref.items = (dref.items[0], "hello")
    sched = processor.generate_schedule("my_sub", fparser2spec)
    cblocks = sched.walk(CodeBlock)
    assert len(cblocks) == 1
    assert isinstance(cblocks[0].parent, Assignment)
Пример #4
0
def test_c701_no_assumed_size_array(f2003_create):
    '''Test C701 (R701) The type-param-name shall be the name of a type.
    This test cannot be passed without more parse context of things like
    defined types.
    '''
    context = f2003.Type_Declaration_Stmt("INTEGER :: not_a_type")
    with pytest.raises(fparser.two.utils.NoMatchError):
        f2003.Primary('not_a_type', )  # context)
Пример #5
0
def test_c702_no_assumed_size_array(f2003_create):
    '''Test C702 (R701) The designator shall not be a whole assumed-size array.
    This test cannot be passed without more parse context of things like
    defined types.
    '''
    context = f2003.Type_Declaration_Stmt("integer(*) :: assumed_size_array")
    with pytest.raises(fparser.two.utils.NoMatchError):
        f2003.Primary('assumed_size_array', )  # context)
Пример #6
0
def test_prefix_c1240(f2003_create):
    '''Test that an exception is raised if constraint c1240 is broken (at
    most one of each prefix-spec).

    '''
    with pytest.raises(NoMatchError):
        _ = f2003.Prefix("module module")

    with pytest.raises(NoMatchError):
        _ = f2003.Prefix("type(my_type) type(my_type2)")

    with pytest.raises(NoMatchError):
        _ = f2003.Prefix("module type(my_type2) module")
Пример #7
0
def test_broken_use(monkeypatch):
    ''' Check that we raise the expected error if we encounter an unrecognised
    parse tree for a USE statement. '''
    fake_parent = KernelSchedule("dummy_schedule")
    processor = Fparser2Reader()
    reader = FortranStringReader("use some_mod, only:\n")
    fparser2spec = Fortran2003.Specification_Part(reader)
    # Break the parse tree so that instead of ", ONLY:" it has "hello"
    monkeypatch.setattr(
        fparser2spec.content[0], "items",
        [None, None, Fortran2003.Name('my_mod'), 'hello', None])
    with pytest.raises(NotImplementedError) as err:
        processor.process_declarations(fake_parent, fparser2spec.content, [])
    assert "unsupported USE statement: 'USE my_modhello'" in str(err.value)
def test_brackets_array_constructor(left, right):
    ''' Test parsing of array constructor specified with both valid types of
    bracket. '''
    fcode = "array = {0} 1, 2, 3{1}".format(left, right)
    reader = FortranStringReader(fcode)
    ast = Fortran2003.Assignment_Stmt(reader)
    assert isinstance(ast, Fortran2003.Assignment_Stmt)
    assert isinstance(ast.children[2], Fortran2003.Array_Constructor)
    assert isinstance(ast.children[2].children[1], Fortran2003.Ac_Value_List)
    assert "array = {0}1, 2, 3{1}".format(left, right) in str(ast)
    # Invalid content between valid brackets
    fcode = "array = {0}call hello(){1}".format(left, right)
    reader = FortranStringReader(fcode)
    ast = Fortran2003.Assignment_Stmt(reader)
    assert ast is None
Пример #9
0
    def get_integer_variable(self, name):
        ''' Parse the kernel meta-data and find the value of the
        integer variable with the supplied name. Return None if no
        matching variable is found.

        :param str name: the name of the integer variable to find.

        :returns: value of the specified integer variable or None.
        :rtype: str

        :raises ParseError: if the RHS of the assignment is not a Name.

        '''
        # Ensure the Fortran2003 parser is initialised
        _ = ParserFactory().create()

        for statement, _ in fpapi.walk(self._ktype, -1):
            if isinstance(statement, fparser1.typedecl_statements.Integer):
                # fparser only goes down to the statement level. We use
                # fparser2 to parse the statement itself (eventually we'll
                # use fparser2 to parse the whole thing).
                assign = Fortran2003.Assignment_Stmt(statement.entity_decls[0])
                if str(assign.items[0]) == name:
                    if not isinstance(assign.items[2], Fortran2003.Name):
                        raise ParseError(
                            "get_integer_variable: RHS of assignment is not "
                            "a variable name: '{0}'".format(str(assign)))
                    return str(assign.items[2])
        return None
Пример #10
0
def test_get_int_array_section_subscript_err(monkeypatch):
    ''' Check that we raise the appropriate error if the parse tree for the
    LHS of the array declaration is broken. '''
    from fparser.two import Fortran2003
    # First create a valid KernelType object
    ast = parse(DIFF_BASIS, ignore_comments=False)
    ktype = KernelType(ast)
    # Create a valid fparser2 result
    assign = Fortran2003.Assignment_Stmt("gh_evaluator_targets(2) = [1, 2]")
    # Break the array constructor expression by replacing the
    # Section_Subscript_List with a str
    assign.children[0].items = (assign.children[0].items[0], "hello")

    # Use monkeypatch to ensure that that's the result that is returned
    # when we attempt to use fparser2 from within the routine under test

    def my_init(self, _):
        ''' dummy constructor '''
        self.items = assign.items

    monkeypatch.setattr(Fortran2003.Assignment_Stmt, "__init__", my_init)

    with pytest.raises(InternalError) as err:
        _ = ktype.get_integer_array("gh_evaluator_targets")
    assert ("expected array declaration to have a Section_Subscript_List but "
            "found" in str(err.value))
Пример #11
0
def test_get_int_array_constructor_err(monkeypatch):
    ''' Check that we raise the appropriate error if we fail to parse the
    array constructor expression. '''
    from fparser.two import Fortran2003
    # First create a valid KernelType object
    ast = parse(DIFF_BASIS, ignore_comments=False)
    ktype = KernelType(ast)
    # Create a valid fparser2 result
    assign = Fortran2003.Assignment_Stmt("gh_evaluator_targets(2) = [1, 2]")
    # Break the array constructor expression (tuples are immutable so make a
    # new one)
    assign.items[2].items[1].items = tuple(["hello", "goodbye"])

    # Use monkeypatch to ensure that that's the result that is returned
    # when we attempt to use fparser2 from within the routine under test

    def my_init(self, _):
        ''' dummy class '''
        self.items = assign.items

    monkeypatch.setattr(Fortran2003.Assignment_Stmt, "__init__", my_init)
    with pytest.raises(InternalError) as err:
        _ = ktype.get_integer_array("gh_evaluator_targets")
    assert ("Failed to parse array constructor: '[hello, goodbye]'"
            in str(err.value))
def test_implicit_loop_constructor_no_parentheses():
    ''' Test that the parser does not match an implicit loop if the
    surrounding parentheses are missing (R470). '''
    fcode = "(/ival, ival=1, nval, istep/)"
    reader = FortranStringReader(fcode)
    ast = Fortran2003.Array_Constructor(reader)
    assert ast is None
Пример #13
0
def test_handling_literal_precision_2(value, dprecision, intrinsic):
    '''Check that the fparser2 frontend can handle literals with a
    specified precision value.

    TODO #754 fix test so that 'disable_declaration_check' fixture is not
    required.
    '''
    if intrinsic == ScalarType.Intrinsic.CHARACTER:
        code = "x={0}_{1}".format(dprecision, value)
    else:
        code = "x={0}_{1}".format(value, dprecision)
    reader = FortranStringReader(code)
    astmt = Fortran2003.Assignment_Stmt(reader)
    fake_parent = Schedule()
    processor = Fparser2Reader()
    processor.process_nodes(fake_parent, [astmt])
    assert not fake_parent.walk(CodeBlock)
    literal = fake_parent.children[0].children[1]
    assert isinstance(literal, Literal)
    assert literal.datatype.intrinsic == intrinsic
    if intrinsic == ScalarType.Intrinsic.BOOLEAN:
        assert ".{0}.".format(literal.value) == value.lower()
    else:
        assert literal.value == value
    assert isinstance(literal.datatype.precision, int)
    assert literal.datatype.precision == dprecision
Пример #14
0
def assert_subclass_parse(source,
                          base_type,
                          actual_type=None,
                          expected_str=None):
    '''Assert that the given source matches the given ``base_type``
    and optionally the specific type that it should produce.

    :param source: The Fortran source to be parsed.
    :type source: str or :py:class:`FortranReaderBase`
    :param base_type: the base type from which a match is expected to be found
    :type base_type: :py:class:`fortran.two.Fortran2003.Base` subclass
    :param actual_type: The actual type matched by the parser.
    :type actual_type: :py:class:`fortran.two.Fortran2003.Base` subclass
    :param str expected_str: The expected ``str(result)`` of the parsed result

    '''
    obj = f2003.Primary(source)
    # Note: Check that the type exists in the possible types, rather than
    # checking the type is an instance of one of the possible types (and
    # all of its ancestor types). This is a much more targetted test as a
    # result.
    assert type(obj) in possible_subclasses(base_type)

    if actual_type:
        assert isinstance(obj, actual_type)
    else:
        assert isinstance(obj, base_type)

    if expected_str:
        assert expected_str == str(obj)
Пример #15
0
def test_handling_literal_precision_1(value, dprecision, intrinsic):
    '''Check that the fparser2 frontend can handle literals with a
    specified precision kind symbol.

    '''
    if intrinsic == ScalarType.Intrinsic.CHARACTER:
        code = "x={0}_{1}".format(dprecision, value)
    else:
        code = "x={0}_{1}".format(value, dprecision)
    reader = FortranStringReader(code)
    astmt = Fortran2003.Assignment_Stmt(reader)
    fake_parent = Schedule()
    # Ensure the symbol table has an entry for "x"
    fake_parent.symbol_table.add(
        DataSymbol("x", ScalarType(ScalarType.Intrinsic.INTEGER, 4)))
    processor = Fparser2Reader()
    processor.process_nodes(fake_parent, [astmt])
    assert not fake_parent.walk(CodeBlock)
    literal = fake_parent.children[0].children[1]
    assert isinstance(literal, Literal)
    assert literal.datatype.intrinsic == intrinsic
    if intrinsic == ScalarType.Intrinsic.BOOLEAN:
        assert ".{0}.".format(literal.value) == value.lower()
    else:
        assert literal.value == value
    assert isinstance(literal.datatype.precision, DataSymbol)
    assert literal.datatype.precision.name == dprecision
    assert isinstance(literal.datatype.precision.datatype, ScalarType)
    assert (literal.datatype.precision.datatype.intrinsic ==
            ScalarType.Intrinsic.INTEGER)
Пример #16
0
def test_walk_debug(capsys):
    ''' Test the debug output of the walk() utility. '''
    import six
    reader = get_reader("program just_a_test\n"
                        "if(.true.)then\n"
                        "  b = 1\n"
                        "end if\n"
                        "end program just_a_test\n")
    main = Fortran2003.Program(reader)
    _ = walk(main, debug=True)
    stdout, _ = capsys.readouterr()
    if six.PY2:
        # Output of capsys under Python 2 is not the same as under 3
        assert stdout.startswith("('child type = ")
    else:
        assert stdout.startswith("child type = ")
    assert "Main_Program" in stdout
    assert "If_Construct" in stdout
    assert "Assignment" in stdout
    assert "Int_Literal_Constant" in stdout
    assert "End_If_Stmt" in stdout
    # Walk only part of the tree and specify an indent
    if_constructs = walk(main, Fortran2003.If_Construct)
    _ = walk(if_constructs[0], indent=4, debug=True)
    stdout, _ = capsys.readouterr()
    if six.PY2:
        # Output of capsys under Python 2 is not the same as under 3
        assert stdout.startswith("('" + 8 * " " + "child type =")
    else:
        assert stdout.startswith(8 * " " + "child type =")
    assert "Program" not in stdout
Пример #17
0
def test_get_child():
    ''' Test the get_child() utility. '''
    from fparser.two import Fortran2003
    from fparser.two.utils import walk, get_child
    reader = get_reader("program hello\n"
                        "write(*,*) 'hello'\n"
                        "write(*,*) 'goodbye'\n"
                        "end program hello\n")
    main = Fortran2003.Program(reader)
    prog = get_child(main, Fortran2003.Main_Program)
    exe = get_child(prog, Fortran2003.Execution_Part)
    assert isinstance(exe, Fortran2003.Execution_Part)
    write_stmt = get_child(exe, Fortran2003.Write_Stmt)
    # Check that we got the first write and not the second
    assert "goodbye" not in str(write_stmt)
    # The top level has no Io_Control_Spec children
    assert not get_child(main, Fortran2003.Io_Control_Spec)
    # Check functionality when node has children in `items` and
    # not in `content`
    io_nodes = walk(main.content, Fortran2003.Io_Control_Spec)
    assert not hasattr(io_nodes[0], "content")
    io_unit = get_child(io_nodes[0], Fortran2003.Io_Unit)
    assert isinstance(io_unit, Fortran2003.Io_Unit)
    missing = get_child(io_nodes[0], Fortran2003.Execution_Part)
    assert missing is None
Пример #18
0
def test_multi_use_stmt():
    ''' Check that we handle the case where different symbols are imported
    from a module in separate USE statements. '''
    fake_parent = KernelSchedule("dummy_schedule")
    processor = Fparser2Reader()
    reader = FortranStringReader("use my_mod, only: some_var\n"
                                 "use this_mod\n"
                                 "use my_mod, only: var1, var2\n"
                                 "use this_mod, only: var3\n")
    fparser2spec = Fortran2003.Specification_Part(reader)
    processor.process_declarations(fake_parent, fparser2spec.content, [])
    symtab = fake_parent.symbol_table
    csymbols = symtab.containersymbols
    # Although there are 4 use statements, there are only 2 modules
    assert len(csymbols) == 2
    my_mod = symtab.lookup("my_mod")
    assert not my_mod.wildcard_import
    # Check that we have accumulated all imports
    import_list = symtab.imported_symbols(my_mod)
    assert len(import_list) == 3
    names = [sym.name for sym in import_list]
    assert sorted(names) == ["some_var", "var1", "var2"]
    this_mod = symtab.lookup("this_mod")
    assert this_mod.wildcard_import
    names = [sym.name for sym in symtab.imported_symbols(this_mod)]
    assert names == ["var3"]
Пример #19
0
def test_use_stmt():
    ''' Check that SymbolTable entries are correctly created from
    module use statements. '''
    fake_parent = KernelSchedule("dummy_schedule")
    processor = Fparser2Reader()
    reader = FortranStringReader("use my_mod, only: some_var\n"
                                 "use this_mod\n"
                                 "use other_mod, only: var1, var2\n")
    fparser2spec = Fortran2003.Specification_Part(reader)
    processor.process_declarations(fake_parent, fparser2spec.content, [])

    symtab = fake_parent.symbol_table

    for module_name in ["my_mod", "this_mod", "other_mod"]:
        container = symtab.lookup(module_name)
        assert isinstance(container, ContainerSymbol)
        assert container.name == module_name
        # Container reference is not updated until explicitly requested
        assert not container._reference

    for var in ["some_var", "var1", "var2"]:
        assert symtab.lookup(var).name == var

    assert symtab.lookup("some_var").interface.container_symbol \
        == symtab.lookup("my_mod")
    assert symtab.lookup("var2").interface.container_symbol \
        == symtab.lookup("other_mod")
Пример #20
0
def test_parser_caseinsensitive2(monkeypatch):
    '''Check that the test for the existance of a kernel call in a use
    statement is case insensitive.

    '''
    def dummy_func(arg1, arg2, arg3, arg4):
        '''A dummy function used by monkeypatch to override the get_kernel_ast
        function. We don't care about the arguments as we just want to
        raise an exception.

        '''
        # pylint: disable=unused-argument
        raise NotImplementedError("test_parser_caseinsensitive2")

    monkeypatch.setattr("psyclone.parse.kernel.get_kernel_ast", dummy_func)
    from fparser.two import Fortran2003 as f2003
    from fparser.two.parser import ParserFactory
    ParserFactory().create(std="f2003")
    parser = Parser()
    use = f2003.Use_Stmt("use my_mod, only : MY_KERN")
    parser.update_arg_to_module_map(use)
    with pytest.raises(NotImplementedError) as excinfo:
        # We have monkeypatched the function 'get_kernel_ast' to
        # return 'NotImplementedError' with a string associated with
        # this test so we know that we have got to this function if
        # this exception is raised. The case insensitive test we
        # really care about is before this function is called (and it
        # raises a ParseError) so we know that if we don't get a
        # ParseError then all is well.
        parser.create_coded_kernel_call("My_Kern", None)
    # Sanity check that the exception is the monkeypatched one.
    assert str(excinfo.value) == "test_parser_caseinsensitive2"
Пример #21
0
def test_prefix_c1241(f2003_create):
    '''Test that an exception is raised if constraint c1241 is broken
    (elemental and recursive are used together).

    '''
    with pytest.raises(NoMatchError):
        _ = f2003.Prefix("recursive elemental")
Пример #22
0
def test_get_int_array_err1(monkeypatch):
    ''' Tests that we raise the correct error if there is something wrong
    with the assignment statement obtained from fparser2. '''
    from fparser.two import Fortran2003
    # This is difficult as we have to break the result returned by fparser2.
    # We therefore create a valid KernelType object
    ast = fpapi.parse(MDATA, ignore_comments=False)
    ktype = KernelType(ast)
    # Next we create a valid fparser2 result
    my_assign = Fortran2003.Assignment_Stmt("my_array(2) = [1, 2]")
    # Break its `items` property by replacing the Name object with a string
    # (tuples are immutable so make a new one)
    broken_items = tuple(["invalid"] + list(my_assign.items[1:]))

    # Use monkeypatch to ensure that that the Assignment_Stmt that
    # is returned when we attempt to use fparser2 from within the
    # routine under test now has the broken tuple of items.

    def my_init(self, _):
        ''' dummy class '''
        self.items = broken_items
    monkeypatch.setattr(Fortran2003.Assignment_Stmt, "__init__", my_init)

    with pytest.raises(InternalError) as err:
        _ = ktype.get_integer_array("gh_evaluator_targets")
    assert "Unsupported assignment statement: 'invalid = [1, 2]'" in str(err)
Пример #23
0
def test_call_noargs():
    '''Test that fparser2reader transforms a Fortran subroutine call with
    no arguments into the equivalent PSyIR Call node. Also test that a
    new RoutineSymbol is added to the symbol table (with an unresolved
    interface) when one does not already exist. Also test that the
    Call node ast property is set to reference the original fparser2
    call node.

    '''
    reader = FortranStringReader(" call kernel()")
    ast = Fortran2003.Call_Stmt(reader)
    fake_parent = Schedule()
    processor = Fparser2Reader()
    processor.process_nodes(fake_parent, [ast])

    call_node = fake_parent.children[0]
    assert isinstance(call_node, Call)
    assert not call_node.children

    routine_symbol = call_node.routine
    assert isinstance(routine_symbol, RoutineSymbol)
    assert isinstance(routine_symbol.interface, UnresolvedInterface)
    assert routine_symbol.name == "kernel"
    assert routine_symbol in call_node.scope.symbol_table.symbols

    assert (str(call_node)) == "Call[name='kernel']"

    assert call_node.ast == ast
Пример #24
0
def test_parse_derived_type(use_stmt, type_name):
    ''' Check that the fronted correctly creates a DataTypeSymbol of type
    StructureType from the declaration of a derived type. '''
    fake_parent = KernelSchedule("dummy_schedule")
    symtab = fake_parent.symbol_table
    processor = Fparser2Reader()
    reader = FortranStringReader("{0}\n"
                                 "type :: my_type\n"
                                 "  integer :: flag\n"
                                 "  type({1}), private :: grid\n"
                                 "  real, dimension(3) :: posn\n"
                                 "end type my_type\n"
                                 "type(my_type) :: var\n".format(
                                     use_stmt, type_name))
    fparser2spec = Fortran2003.Specification_Part(reader)
    processor.process_declarations(fake_parent, fparser2spec.content, [])
    sym = symtab.lookup("my_type")
    assert isinstance(sym, DataTypeSymbol)
    assert isinstance(sym.datatype, StructureType)
    flag = sym.datatype.lookup("flag")
    assert isinstance(flag.datatype, ScalarType)
    assert flag.visibility == Symbol.Visibility.PUBLIC
    grid = sym.datatype.lookup("grid")
    assert isinstance(grid.datatype, DataTypeSymbol)
    assert isinstance(grid.datatype.datatype, DeferredType)
    assert grid.visibility == Symbol.Visibility.PRIVATE
    posn = sym.datatype.lookup("posn")
    assert isinstance(posn.datatype, ArrayType)
    var = symtab.lookup("var")
    assert var.datatype is sym
def test_nested_implied_do():
    ''' Test C497 - the ac-do-variable of a nested implicit do shall not
    appear as the ac-do-variable of the containing implicit do. '''
    reader = FortranStringReader(
        "(/(JBODY,JBODY=1,SUM((/(JBODY,JBODY=1,4)/)))/)")
    ast = Fortran2003.Array_Constructor(reader)
    assert ast is None
Пример #26
0
def test_fw_codeblock():
    '''Check the FortranWriter class codeblock method correctly
    prints out the Fortran code contained within it.

    '''
    # Generate fparser2 parse tree from Fortran code.
    code = (
        "module test\n"
        "contains\n"
        "subroutine tmp()\n"
        "  integer :: a\n"
        "  a=1\n"
        "end subroutine tmp\n"
        "end module test")
    schedule = create_schedule(code)

    code1 = (
        "print *, 'I am a code block'\n"
        "print *, 'with more than one line'\n")
    _ = ParserFactory().create(std="f2003")
    reader = get_reader(code1)
    statements = Fortran2003.Execution_Part(reader)
    code_block = CodeBlock([statements], parent=schedule)
    schedule.addchild(code_block)

    # Generate Fortran from the PSyIR schedule
    fvisitor = FortranWriter()
    result = fvisitor(schedule)

    assert (
        "    a=1\n"
        "PRINT *, 'I am a code block'\n"
        "    PRINT *, 'with more than one line'\n" in result)
Пример #27
0
def test_zero_size_array_constructor():
    ''' Test that we can parse a valid, zero-size array constructor. '''
    fcode = "integer ::"
    ast = Fortran2003.Ac_Spec(fcode)
    assert isinstance(ast, Fortran2003.Ac_Spec)
    assert isinstance(ast.children[0],
                      Fortran2003.Intrinsic_Type_Spec)
Пример #28
0
def test_call_not_implicit_loop():
    ''' Check we do not incorrectly identify an implicit loop when array
    notation is used in the arguments to a function call. '''
    code = "z3d(1,:,:) =  ptr_sjk( pvtr(:,:,:), btmsk(:,:,jn)*btm30(:,:) )"
    reader = FortranStringReader(code)
    assign = Fortran2003.Assignment_Stmt(reader)
    assert not nemo.NemoImplicitLoop.match(assign)
Пример #29
0
def test_1d_array_not_implicit_loop():
    ''' Check that we do not identify the use of array-notation in 1D loops
    as being implicit loops (since we don't know what the loop is over). '''
    code = "z1d(:) =  1.0d0"
    reader = FortranStringReader(code)
    assign = Fortran2003.Assignment_Stmt(reader)
    assert not nemo.NemoImplicitLoop.match(assign)
Пример #30
0
def test_implied_do_no_match():
    ''' R471 - implied-do-control must contain an "=" and 2 or three integer
    expressions. '''
    reader = FortranStringReader("j=1,2,1")
    assert Fortran2003.Ac_Implied_Do_Control(reader)
    # Missing '='
    reader = FortranStringReader("j+1,2,1")
    assert Fortran2003.Ac_Implied_Do_Control(reader) is None
    # Incorrect number of integer expressions (too many)
    reader = FortranStringReader("j=1,2,1,3")
    assert Fortran2003.Ac_Implied_Do_Control(reader) is None
    # Incorrect number of integer expressions (too few)
    reader = FortranStringReader("j=1")
    assert Fortran2003.Ac_Implied_Do_Control(reader) is None
    # C493 ac-do-variable shall be a named variable
    reader = FortranStringReader("1=1, 2, 1")
    assert Fortran2003.Ac_Implied_Do_Control(reader) is None