xref: /llvm-project/clang/bindings/python/tests/cindex/test_source_range.py (revision 71cfa381ef8c4fe659c67e8b2901d767e10f2aff)
1import os
2
3from clang.cindex import Config, SourceLocation, SourceRange, TranslationUnit
4
5if "CLANG_LIBRARY_PATH" in os.environ:
6    Config.set_library_path(os.environ["CLANG_LIBRARY_PATH"])
7
8import unittest
9
10from .util import get_tu
11
12
13def create_range(tu, line1, column1, line2, column2):
14    return SourceRange.from_locations(
15        SourceLocation.from_position(tu, tu.get_file(tu.spelling), line1, column1),
16        SourceLocation.from_position(tu, tu.get_file(tu.spelling), line2, column2),
17    )
18
19
20class TestSourceRange(unittest.TestCase):
21    def test_contains(self):
22        tu = get_tu(
23            """aaaaa
24aaaaa
25aaaaa
26aaaaa"""
27        )
28        file = tu.get_file(tu.spelling)
29
30        l13 = SourceLocation.from_position(tu, file, 1, 3)
31        l21 = SourceLocation.from_position(tu, file, 2, 1)
32        l22 = SourceLocation.from_position(tu, file, 2, 2)
33        l23 = SourceLocation.from_position(tu, file, 2, 3)
34        l24 = SourceLocation.from_position(tu, file, 2, 4)
35        l25 = SourceLocation.from_position(tu, file, 2, 5)
36        l33 = SourceLocation.from_position(tu, file, 3, 3)
37        l31 = SourceLocation.from_position(tu, file, 3, 1)
38        r22_24 = create_range(tu, 2, 2, 2, 4)
39        r23_23 = create_range(tu, 2, 3, 2, 3)
40        r24_32 = create_range(tu, 2, 4, 3, 2)
41        r14_32 = create_range(tu, 1, 4, 3, 2)
42
43        assert l13 not in r22_24  # Line before start
44        assert l21 not in r22_24  # Column before start
45        assert l22 in r22_24  # Colum on start
46        assert l23 in r22_24  # Column in range
47        assert l24 in r22_24  # Column on end
48        assert l25 not in r22_24  # Column after end
49        assert l33 not in r22_24  # Line after end
50
51        assert l23 in r23_23  # In one-column range
52
53        assert l23 not in r24_32  # Outside range in first line
54        assert l33 not in r24_32  # Outside range in last line
55        assert l25 in r24_32  # In range in first line
56        assert l31 in r24_32  # In range in last line
57
58        assert l21 in r14_32  # In range at start of center line
59        assert l25 in r14_32  # In range at end of center line
60
61        # In range within included file
62        tu2 = TranslationUnit.from_source(
63            "main.c",
64            unsaved_files=[
65                (
66                    "main.c",
67                    """int a[] = {
68#include "numbers.inc"
69};
70""",
71                ),
72                (
73                    "./numbers.inc",
74                    """1,
752,
763,
774
78                 """,
79                ),
80            ],
81        )
82
83        r_curly = create_range(tu2, 1, 11, 3, 1)
84        l_f2 = SourceLocation.from_position(tu2, tu2.get_file("./numbers.inc"), 4, 1)
85        assert l_f2 in r_curly
86