Coverage for /pythoncovmergedfiles/medio/medio/usr/local/lib/python3.11/site-packages/pygments/lexers/bitbake.py: 100%

Shortcuts on this page

r m x   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

19 statements  

1""" 

2 pygments.lexers.bitbake 

3 ~~~~~~~~~~~~~~~~~~~~~~~ 

4 

5 Lexer for BitBake recipes, classes, includes and configuration files 

6 used by the Yocto Project / OpenEmbedded build system. 

7 

8 :copyright: Copyright 2006-present by the Pygments team, see AUTHORS. 

9 :license: BSD, see LICENSE for details. 

10""" 

11 

12import re 

13 

14from pygments.lexer import RegexLexer, bygroups, include, using, words 

15from pygments.lexers.python import PythonLexer 

16from pygments.lexers.shell import BashLexer 

17from pygments.token import Comment, Keyword, Name, Operator, Punctuation, \ 

18 String, Text, Whitespace 

19 

20__all__ = ['BitBakeLexer'] 

21 

22# A bare BitBake identifier (variable, function or flag name). Allows the 

23# characters used by OE-Core variable names (digits, ``-``, ``.``, ``+``). 

24_IDENT = r'[A-Za-z_][A-Za-z0-9_\-.+]*' 

25 

26# Optional OE override chain such as ``:append``, ``:remove``, ``:class-target`` 

27# or ``:${PN}-doc``. Anchored so it only consumes ``:foo`` runs and never 

28# eats the leading ``:`` of the ``:=`` assignment operator. 

29_OVERRIDE = r'(?::[A-Za-z0-9_\-.+${}]+)*' 

30 

31# All BitBake variable assignment operators, ordered so that the longer 

32# operators win the regex alternation. 

33_ASSIGN = r'(?:\?\?=|\?=|:=|\+=|=\+|\.=|=\.|=)' 

34 

35 

36class BitBakeLexer(RegexLexer): 

37 """ 

38 Lexer for BitBake recipes, classes, includes and configuration files 

39 used by the Yocto Project and OpenEmbedded build system. 

40 """ 

41 

42 name = 'BitBake' 

43 url = 'https://docs.yoctoproject.org/bitbake/' 

44 aliases = ['bitbake'] 

45 filenames = ['*.bbclass', '*.bbappend'] 

46 mimetypes = ['text/x-bitbake'] 

47 version_added = '2.21' 

48 

49 flags = re.MULTILINE 

50 

51 tokens = { 

52 'root': [ 

53 (r'[ \t]+', Whitespace), 

54 (r'\n', Whitespace), 

55 (r'#.*$', Comment.Single), 

56 

57 # ``python [name]() { ... }`` blocks (also ``fakeroot python``). 

58 # Must be tried before the generic shell function rule so the 

59 # ``python`` keyword is not mistaken for a shell function name. 

60 (r'(^(?:fakeroot[ \t]+)?)(python)((?:[ \t]+' + _IDENT + r')?)' 

61 r'([ \t]*\([ \t]*\)[ \t]*)(\{[ \t]*\n)' 

62 r'((?:.*\n)*?)' 

63 r'(^\}[ \t]*$)', 

64 bygroups(Keyword.Type, Keyword, Name.Function, Text, 

65 Punctuation, using(PythonLexer), Punctuation)), 

66 

67 # Shell task bodies: ``[fakeroot ]name[:override]() { ... }``. 

68 (r'(^(?:fakeroot[ \t]+)?)(' + _IDENT + r')(' + _OVERRIDE + r')' 

69 r'([ \t]*\([ \t]*\)[ \t]*)(\{[ \t]*\n)' 

70 r'((?:.*\n)*?)' 

71 r'(^\}[ \t]*$)', 

72 bygroups(Keyword.Type, Name.Function, Name.Decorator, Text, 

73 Punctuation, using(BashLexer), Punctuation)), 

74 

75 # Top-level python ``def`` blocks; the body is any run of 

76 # indented or blank lines following the signature. 

77 (r'^def[ \t]+' + _IDENT + r'[ \t]*\([^)]*\)[ \t]*:[ \t]*\n' 

78 r'(?:[ \t]+.*\n|\n)+', 

79 using(PythonLexer)), 

80 

81 # ``inherit`` / ``inherit_defer`` / ``include`` / ``include_all`` / 

82 # ``require`` directives. Longer keywords are listed first so the 

83 # regex alternation does not match the shorter prefix. 

84 (r'^(inherit_defer|inherit|include_all|include|require)\b', 

85 Keyword.Namespace, 'include-line'), 

86 

87 # ``addtask`` / ``deltask`` / ``addhandler`` / ``EXPORT_FUNCTIONS``. 

88 (r'^(addtask|deltask|addhandler|EXPORT_FUNCTIONS)\b', 

89 Keyword, 'statement'), 

90 

91 # ``VAR[flag] = "value"`` (varflag assignment). 

92 (r'^(' + _IDENT + r')(\[)(' + _IDENT + r')(\])([ \t]*)(' 

93 + _ASSIGN + r')', 

94 bygroups(Name.Variable, Punctuation, Name.Attribute, 

95 Punctuation, Whitespace, Operator), 

96 'value'), 

97 

98 # ``[export ]VAR[:override...] OP "value"`` assignments. 

99 (r'^(export[ \t]+)?(' + _IDENT + r')(' + _OVERRIDE + r')' 

100 r'([ \t]*)(' + _ASSIGN + r')', 

101 bygroups(Keyword.Type, Name.Variable, Name.Decorator, 

102 Whitespace, Operator), 

103 'value'), 

104 

105 # Anything else: consume runs of "boring" characters in one 

106 # token, then fall back to a single character if needed. 

107 (r'[^\s#${}\[\]:=+?.@\\"\']+', Text), 

108 (r'.', Text), 

109 ], 

110 

111 'include-line': [ 

112 (r'[ \t]+', Whitespace), 

113 (r'\\\n', Text), 

114 (r'\n', Whitespace, '#pop'), 

115 include('interp'), 

116 (r'[^\s$]+', String), 

117 ], 

118 

119 'statement': [ 

120 (r'[ \t]+', Whitespace), 

121 (r'\\\n', Text), 

122 (r'\n', Whitespace, '#pop'), 

123 (words(('after', 'before'), suffix=r'\b'), Keyword), 

124 include('interp'), 

125 (r'[^\s$\\]+', Name), 

126 ], 

127 

128 'value': [ 

129 (r'[ \t]+', Whitespace), 

130 (r'\\\n', String.Escape), 

131 (r'\n', Whitespace, '#pop'), 

132 (r'"', String.Double, 'string-double'), 

133 (r"'", String.Single, 'string-single'), 

134 include('interp'), 

135 (r'[^\s"\'$\\]+', String), 

136 ], 

137 

138 'string-double': [ 

139 (r'\\\n', String.Escape), 

140 (r'\\.', String.Escape), 

141 (r'"', String.Double, '#pop'), 

142 include('interp'), 

143 (r'[^"\\$]+', String.Double), 

144 ], 

145 

146 'string-single': [ 

147 (r'\\\n', String.Escape), 

148 (r'\\.', String.Escape), 

149 (r"'", String.Single, '#pop'), 

150 include('interp'), 

151 (r"[^'\\$]+", String.Single), 

152 ], 

153 

154 'interp': [ 

155 # ``${@ python expression }`` evaluated by BitBake at parse time. 

156 (r'\$\{@', String.Interpol, 'py-interp'), 

157 # ``${VAR}`` variable expansion. 

158 (r'(\$\{)([A-Za-z0-9_\-:.+/]+)(\})', 

159 bygroups(String.Interpol, Name.Variable, String.Interpol)), 

160 ], 

161 

162 'py-interp': [ 

163 (r'\}', String.Interpol, '#pop'), 

164 (r'[^}]+', using(PythonLexer)), 

165 ], 

166 }