7
7
8
8
import json
9
9
import os
10
+ import re
10
11
import subprocess as sp
11
12
import sys
12
13
from dataclasses import dataclass
68
69
"libm/src/math/arch/intrinsics.rs" ,
69
70
]
70
71
72
+ # libm PR CI takes a long time and doesn't need to run unless relevant files have been
73
+ # changed. Anything matching this regex pattern will trigger a run.
74
+ TRIGGER_LIBM_PR_CI = ".*(libm|musl).*"
75
+
71
76
TYPES = ["f16" , "f32" , "f64" , "f128" ]
72
77
73
78
@@ -116,7 +121,6 @@ class FunctionDef(TypedDict):
116
121
type : str
117
122
118
123
119
- @dataclass
120
124
class Context :
121
125
gh_ref : str | None
122
126
changed : list [Path ]
@@ -142,7 +146,7 @@ def _init_change_list(self):
142
146
# the PR number), and sets this as `GITHUB_REF`.
143
147
ref = self .gh_ref
144
148
eprint (f"using ref `{ ref } `" )
145
- if ref is None or "merge" not in ref :
149
+ if not self . is_pr () :
146
150
# If the ref is not for `merge` then we are not in PR CI
147
151
eprint ("No diff available for ref" )
148
152
return
@@ -170,6 +174,10 @@ def _init_change_list(self):
170
174
)
171
175
self .changed = [Path (p ) for p in textlist .splitlines ()]
172
176
177
+ def is_pr (self ) -> bool :
178
+ """Check if we are looking at a PR rather than a push."""
179
+ return self .gh_ref is not None and "merge" in self .gh_ref
180
+
173
181
@staticmethod
174
182
def _ignore_file (fname : str ) -> bool :
175
183
return any (fname .startswith (pfx ) for pfx in IGNORE_FILES )
@@ -196,7 +204,16 @@ def changed_routines(self) -> dict[str, list[str]]:
196
204
197
205
return ret
198
206
199
- def make_workflow_output (self ) -> str :
207
+ def may_skip_libm_ci (self ) -> bool :
208
+ """If this is a PR and no libm files were changed, allow skipping libm
209
+ jobs."""
210
+
211
+ if self .is_pr ():
212
+ return all (not re .match (TRIGGER_LIBM_PR_CI , str (f )) for f in self .changed )
213
+
214
+ return False
215
+
216
+ def emit_workflow_output (self ):
200
217
"""Create a JSON object a list items for each type's changed files, if any
201
218
did change, and the routines that were affected by the change.
202
219
"""
@@ -216,9 +233,10 @@ def make_workflow_output(self) -> str:
216
233
eprint ("Skipping all extensive tests" )
217
234
218
235
changed = self .changed_routines ()
219
- ret = []
236
+ matrix = []
220
237
total_to_test = 0
221
238
239
+ # Figure out which extensive tests need to run
222
240
for ty in TYPES :
223
241
ty_changed = changed .get (ty , [])
224
242
ty_to_test = [] if skip_tests else ty_changed
@@ -230,9 +248,14 @@ def make_workflow_output(self) -> str:
230
248
"to_test" : "," .join (ty_to_test ),
231
249
}
232
250
233
- ret .append (item )
234
- output = json .dumps ({"matrix" : ret }, separators = ("," , ":" ))
235
- eprint (f"output: { output } " )
251
+ matrix .append (item )
252
+
253
+ ext_matrix = json .dumps ({"extensive_matrix" : matrix }, separators = ("," , ":" ))
254
+ may_skip = str (self .may_skip_libm_ci ()).lower ()
255
+ print (f"extensive_matrix={ ext_matrix } " )
256
+ print (f"may_skip_libm_ci={ may_skip } " )
257
+ eprint (f"extensive_matrix={ ext_matrix } " )
258
+ eprint (f"may_skip_libm_ci={ may_skip } " )
236
259
eprint (f"total extensive tests: { total_to_test } " )
237
260
238
261
if error_on_many_tests and total_to_test > MANY_EXTENSIVE_THRESHOLD :
@@ -242,8 +265,6 @@ def make_workflow_output(self) -> str:
242
265
)
243
266
exit (1 )
244
267
245
- return output
246
-
247
268
248
269
def locate_baseline (flags : list [str ]) -> None :
249
270
"""Find the most recent baseline from CI, download it if specified.
@@ -398,8 +419,7 @@ def main():
398
419
match sys .argv [1 :]:
399
420
case ["generate-matrix" ]:
400
421
ctx = Context ()
401
- output = ctx .make_workflow_output ()
402
- print (f"matrix={ output } " )
422
+ ctx .emit_workflow_output ()
403
423
case ["locate-baseline" , * flags ]:
404
424
locate_baseline (flags )
405
425
case ["check-regressions" , * args ]:
0 commit comments