xref: /aosp_15_r20/external/swiftshader/docs/Regres.md (revision 03ce13f70fcc45d86ee91b7ee4cab1936a95046e)
1*03ce13f7SAndroid Build Coastguard Worker# Regres - SwiftShader automated testing
2*03ce13f7SAndroid Build Coastguard Worker
3*03ce13f7SAndroid Build Coastguard Worker## Introduction
4*03ce13f7SAndroid Build Coastguard Worker
5*03ce13f7SAndroid Build Coastguard WorkerRegres is a collection of tools to perform [dEQP](https://github.com/KhronosGroup/VK-GL-CTS)
6*03ce13f7SAndroid Build Coastguard Workerpresubmit and continuous integration testing and code coverage evaluation for
7*03ce13f7SAndroid Build Coastguard WorkerSwiftShader.
8*03ce13f7SAndroid Build Coastguard Worker
9*03ce13f7SAndroid Build Coastguard WorkerRegres provides:
10*03ce13f7SAndroid Build Coastguard Worker
11*03ce13f7SAndroid Build Coastguard Worker* [Presubmit testing](#presubmit-testing) - An automatic Vulkan
12*03ce13f7SAndroid Build Coastguard Worker  dEQP test run for each Gerrit patchset put up for review.
13*03ce13f7SAndroid Build Coastguard Worker* [Continuous integration testing](#daily-run-continuous-integration-testing) -
14*03ce13f7SAndroid Build Coastguard Worker  A Vulkan dEQP test run performed against the `master` branch each night. \
15*03ce13f7SAndroid Build Coastguard Worker  This nightly run also produces code coverage information which can be viewed at
16*03ce13f7SAndroid Build Coastguard Worker  [swiftshader-regres.github.io/swiftshader-coverage](https://swiftshader-regres.github.io/swiftshader-coverage/).
17*03ce13f7SAndroid Build Coastguard Worker* [Local dEQP test runner](#local-dEQP-test-runner) Provides a local tool for
18*03ce13f7SAndroid Build Coastguard Worker  efficiently running a number of dEQP tests based wildcard or regex name
19*03ce13f7SAndroid Build Coastguard Worker  matching.
20*03ce13f7SAndroid Build Coastguard Worker
21*03ce13f7SAndroid Build Coastguard WorkerThe Regres source root directory is at [`<swiftshader>/tests/regres/`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/).
22*03ce13f7SAndroid Build Coastguard Worker
23*03ce13f7SAndroid Build Coastguard Worker## Presubmit testing
24*03ce13f7SAndroid Build Coastguard Worker
25*03ce13f7SAndroid Build Coastguard WorkerRegres monitors changes that have been [put up for review with Gerrit](https://swiftshader-review.googlesource.com/q/status:open).
26*03ce13f7SAndroid Build Coastguard Worker
27*03ce13f7SAndroid Build Coastguard WorkerOnce a new [qualifying](#qualifying) patchset has been found, regres will
28*03ce13f7SAndroid Build Coastguard Workercheckout, build and test the change against the parent changelist. \
29*03ce13f7SAndroid Build Coastguard WorkerAny differences in results are reported as a review comment on the change
30*03ce13f7SAndroid Build Coastguard Worker[[example]](https://swiftshader-review.googlesource.com/c/SwiftShader/+/46369/5#message-4f09ea3e6d01ed94ae26183c8b6c547c90492c12).
31*03ce13f7SAndroid Build Coastguard Worker
32*03ce13f7SAndroid Build Coastguard Worker### Qualifying
33*03ce13f7SAndroid Build Coastguard Worker
34*03ce13f7SAndroid Build Coastguard WorkerAs Regres may be running externally authored code on Google hardware,
35*03ce13f7SAndroid Build Coastguard WorkerRegres will only test a change if it is authored by or reviewed by a Googler.
36*03ce13f7SAndroid Build Coastguard Worker
37*03ce13f7SAndroid Build Coastguard WorkerOnly the most recent patchset of a change will be tested. If a new patchset is
38*03ce13f7SAndroid Build Coastguard Workerpushed while the previous is currently being tested, then testing will continue
39*03ce13f7SAndroid Build Coastguard Workerto completion and the previous patchsets will be posted, and the new patchset
40*03ce13f7SAndroid Build Coastguard Workerwill be queued for testing.
41*03ce13f7SAndroid Build Coastguard Worker
42*03ce13f7SAndroid Build Coastguard Worker### Prioritization
43*03ce13f7SAndroid Build Coastguard Worker
44*03ce13f7SAndroid Build Coastguard WorkerAt the time of writing a Regres presubmit run takes a little over 20 minutes to
45*03ce13f7SAndroid Build Coastguard Workercomplete, and there is a single Regres machine servicing all changes.
46*03ce13f7SAndroid Build Coastguard WorkerTo keep Regres responsive, changes are prioritized based on their 'readiness to
47*03ce13f7SAndroid Build Coastguard Workerland', which is determined by the change's `Kokoro-Presubmit`, `Code-Review` and
48*03ce13f7SAndroid Build Coastguard Worker`Presubmit-Ready` Gerrit labels.
49*03ce13f7SAndroid Build Coastguard Worker
50*03ce13f7SAndroid Build Coastguard Worker### Test Filtering
51*03ce13f7SAndroid Build Coastguard Worker
52*03ce13f7SAndroid Build Coastguard WorkerBy default, Regres will run all the test lists declared in the
53*03ce13f7SAndroid Build Coastguard Worker[`<swiftshader>/tests/regres/ci-tests.json`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/ci-tests.json) file.\
54*03ce13f7SAndroid Build Coastguard WorkerAs new functionally is being implemented, the test lists in `ci-tests.json` may
55*03ce13f7SAndroid Build Coastguard Workerreference known-passing test lists updated by the [daily run](#daily-run-continuous-integration-testing),
56*03ce13f7SAndroid Build Coastguard Workerso that failing tests for incomplete functionality are skipped, but tests that
57*03ce13f7SAndroid Build Coastguard Workerpass for new functionality *are tested* to ensure they do not regres.
58*03ce13f7SAndroid Build Coastguard Worker
59*03ce13f7SAndroid Build Coastguard WorkerAdditional tests names found in the files referenced by
60*03ce13f7SAndroid Build Coastguard Worker[`<swiftshader>/tests/regres/full-tests.json`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/full-tests.json)
61*03ce13f7SAndroid Build Coastguard Workercan be explicitly included in the change's presubmit run
62*03ce13f7SAndroid Build Coastguard Workerby including a line in the change description with the signature:
63*03ce13f7SAndroid Build Coastguard Worker
64*03ce13f7SAndroid Build Coastguard Worker```text
65*03ce13f7SAndroid Build Coastguard WorkerTest: <dEQP-test-pattern>
66*03ce13f7SAndroid Build Coastguard Worker```
67*03ce13f7SAndroid Build Coastguard Worker
68*03ce13f7SAndroid Build Coastguard Worker`<dEQP-test-pattern>` can be a single dEQP test name, or you can use wildcards
69*03ce13f7SAndroid Build Coastguard Worker[as documented here](https://golang.org/pkg/path/filepath/#Match).
70*03ce13f7SAndroid Build Coastguard Worker
71*03ce13f7SAndroid Build Coastguard WorkerYou can repeat `Test:` as many times as you like. `Tests:` is also acccepted.
72*03ce13f7SAndroid Build Coastguard Worker
73*03ce13f7SAndroid Build Coastguard Worker[For example](https://swiftshader-review.googlesource.com/c/SwiftShader/+/26574):
74*03ce13f7SAndroid Build Coastguard Worker
75*03ce13f7SAndroid Build Coastguard Worker```text
76*03ce13f7SAndroid Build Coastguard WorkerAdd support for OpLogicalEqual, OpLogicalNotEqual
77*03ce13f7SAndroid Build Coastguard Worker
78*03ce13f7SAndroid Build Coastguard WorkerTest: dEQP-VK.glsl.operator.bool_compare.*
79*03ce13f7SAndroid Build Coastguard WorkerTest: dEQP-VK.glsl.operator.binary_operator.equal.*
80*03ce13f7SAndroid Build Coastguard WorkerTest: dEQP-VK.glsl.operator.binary_operator.not_equal.*
81*03ce13f7SAndroid Build Coastguard WorkerBug: b/126870789
82*03ce13f7SAndroid Build Coastguard WorkerChange-Id: I9d33444d67792274d8027b7d1632235533cfc079
83*03ce13f7SAndroid Build Coastguard Worker```
84*03ce13f7SAndroid Build Coastguard Worker
85*03ce13f7SAndroid Build Coastguard Worker## Daily-run continuous integration testing
86*03ce13f7SAndroid Build Coastguard Worker
87*03ce13f7SAndroid Build Coastguard WorkerOnce a day, regres will also test another set of tests from [`<swiftshader>/tests/regres/full-tests.json`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/full-tests.json),
88*03ce13f7SAndroid Build Coastguard Workerand post the test result lists as a Gerrit changelist
89*03ce13f7SAndroid Build Coastguard Worker[[example]](https://swiftshader-review.googlesource.com/c/SwiftShader/+/46448).
90*03ce13f7SAndroid Build Coastguard Worker
91*03ce13f7SAndroid Build Coastguard WorkerThe daily run also performs code coverage instrumentation per dEQP test,
92*03ce13f7SAndroid Build Coastguard Workerautomatically uploading the results of all the dEQP tests to the viewer at
93*03ce13f7SAndroid Build Coastguard Worker[swiftshader-regres.github.io/swiftshader-coverage](https://swiftshader-regres.github.io/swiftshader-coverage/).
94*03ce13f7SAndroid Build Coastguard Worker
95*03ce13f7SAndroid Build Coastguard Worker## Local dEQP test runner
96*03ce13f7SAndroid Build Coastguard Worker
97*03ce13f7SAndroid Build Coastguard WorkerRegres also provides a multi-threaded, [process sandboxed](#process-sandboxing),
98*03ce13f7SAndroid Build Coastguard Workerlocal dEQP test runner with a wild-card / regex based test name matcher.
99*03ce13f7SAndroid Build Coastguard Worker
100*03ce13f7SAndroid Build Coastguard WorkerThe local test runner can be run with:
101*03ce13f7SAndroid Build Coastguard Worker
102*03ce13f7SAndroid Build Coastguard Worker[`<swiftshader>/tests/regres/run_testlist.sh`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/run_testlist.sh) `--deqp-vk=<path to deqp-vk> [--filter=<test name filter>]`
103*03ce13f7SAndroid Build Coastguard Worker
104*03ce13f7SAndroid Build Coastguard Worker`<test name filter>` can be a single dEQP test name, or you can use wildcards
105*03ce13f7SAndroid Build Coastguard Worker[as documented here](https://golang.org/pkg/path/filepath/#Match).
106*03ce13f7SAndroid Build Coastguard WorkerAlternatively, start with a `/` to use a regex filter.
107*03ce13f7SAndroid Build Coastguard Worker
108*03ce13f7SAndroid Build Coastguard WorkerOther useful flags:
109*03ce13f7SAndroid Build Coastguard Worker
110*03ce13f7SAndroid Build Coastguard Worker```text
111*03ce13f7SAndroid Build Coastguard Worker  -limit int
112*03ce13f7SAndroid Build Coastguard Worker        only run a maximum of this number of tests
113*03ce13f7SAndroid Build Coastguard Worker  -no-results
114*03ce13f7SAndroid Build Coastguard Worker        disable generation of results.json file
115*03ce13f7SAndroid Build Coastguard Worker  -output string
116*03ce13f7SAndroid Build Coastguard Worker        path to an output JSON results file (default "results.json")
117*03ce13f7SAndroid Build Coastguard Worker  -shuffle
118*03ce13f7SAndroid Build Coastguard Worker        shuffle tests
119*03ce13f7SAndroid Build Coastguard Worker  -test-list string
120*03ce13f7SAndroid Build Coastguard Worker        path to a test list file (default "vk-master-PASS.txt")
121*03ce13f7SAndroid Build Coastguard Worker```
122*03ce13f7SAndroid Build Coastguard Worker
123*03ce13f7SAndroid Build Coastguard WorkerRun [`<swiftshader>/tests/regres/run_testlist.sh`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/run_testlist.sh) with `--help` to see all available flags.
124*03ce13f7SAndroid Build Coastguard Worker
125*03ce13f7SAndroid Build Coastguard Worker## Process sandboxing
126*03ce13f7SAndroid Build Coastguard Worker
127*03ce13f7SAndroid Build Coastguard WorkerRegres will run each dEQP test in a separate process to prevent state
128*03ce13f7SAndroid Build Coastguard Workerleakage between tests.
129*03ce13f7SAndroid Build Coastguard Worker
130*03ce13f7SAndroid Build Coastguard WorkerTests are run concurrently, and crashing processes will not take down the test
131*03ce13f7SAndroid Build Coastguard Workerrunner.
132*03ce13f7SAndroid Build Coastguard Worker
133*03ce13f7SAndroid Build Coastguard WorkerSome dEQP tests are known to perform excessive memory allocations (i.e. keep
134*03ce13f7SAndroid Build Coastguard Workerallocating until no more can be claimed from the OS). \
135*03ce13f7SAndroid Build Coastguard WorkerIn order to prevent a single test starving other test processes of memory, each
136*03ce13f7SAndroid Build Coastguard Workerprocess is restricted to a fraction of the system's memory using [linux resource limits](https://man7.org/linux/man-pages/man2/getrlimit.2.html).
137*03ce13f7SAndroid Build Coastguard Worker
138*03ce13f7SAndroid Build Coastguard WorkerTests may also deadlock, so each test process has a time limit before they are
139*03ce13f7SAndroid Build Coastguard Workerautomatically killed.
140*03ce13f7SAndroid Build Coastguard Worker
141*03ce13f7SAndroid Build Coastguard Worker## Implementation details
142*03ce13f7SAndroid Build Coastguard Worker
143*03ce13f7SAndroid Build Coastguard Worker### Presubmit & daily run process
144*03ce13f7SAndroid Build Coastguard Worker
145*03ce13f7SAndroid Build Coastguard WorkerRegres runs until stopped, and will:
146*03ce13f7SAndroid Build Coastguard Worker
147*03ce13f7SAndroid Build Coastguard Worker* Download a known compatible version of Clang to a cache directory. This will
148*03ce13f7SAndroid Build Coastguard Worker  be used for all compilation stages below.
149*03ce13f7SAndroid Build Coastguard Worker* Periodically poll Gerrit for recently opened changes
150*03ce13f7SAndroid Build Coastguard Worker* Periodically query Gerrit for details about each tracked change, determining
151*03ce13f7SAndroid Build Coastguard Worker  [whether it should be tested](#qualifying), and determine its current
152*03ce13f7SAndroid Build Coastguard Worker  [priority](#prioritization).
153*03ce13f7SAndroid Build Coastguard Worker* A qualifying change with the highest priority will be picked, and the
154*03ce13f7SAndroid Build Coastguard Worker  following is performed for the change:
155*03ce13f7SAndroid Build Coastguard Worker  1. The change is `git fetch`ed into a temporary directory.
156*03ce13f7SAndroid Build Coastguard Worker  2. If not already cached, the dEQP version described in the
157*03ce13f7SAndroid Build Coastguard Worker     change's [`<swiftshader>/tests/regres/deqp.json`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/deqp.json) file is downloaded and built the into a cached directory.
158*03ce13f7SAndroid Build Coastguard Worker  3. The source for the change is built into a temporary build directory.
159*03ce13f7SAndroid Build Coastguard Worker  4. The built dEQP binaries are used to test the change. The full test results
160*03ce13f7SAndroid Build Coastguard Worker     are stored in a cached directory.
161*03ce13f7SAndroid Build Coastguard Worker  5. If the parent change's test results aren't already cached, then steps 3 and
162*03ce13f7SAndroid Build Coastguard Worker     4 are repeated for the parent change.
163*03ce13f7SAndroid Build Coastguard Worker  6. The results of the two changes are diffed, and the results of the diff are
164*03ce13f7SAndroid Build Coastguard Worker     posted to the change as a Gerrit review comment.
165*03ce13f7SAndroid Build Coastguard Worker* The above is repeated until it is time to perform a daily run, upon which:
166*03ce13f7SAndroid Build Coastguard Worker  1. The `HEAD` change of `master` is fetched into a temporary directory.
167*03ce13f7SAndroid Build Coastguard Worker  2. If not already cached, the dEQP version described in the
168*03ce13f7SAndroid Build Coastguard Worker     change's [`<swiftshader>/tests/regres/deqp.json`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/deqp.json) file is downloaded and built the into a cached directory.
169*03ce13f7SAndroid Build Coastguard Worker  3. The `HEAD` change is built into a temporary directory, optionally with code
170*03ce13f7SAndroid Build Coastguard Worker     coverage instrumenting.
171*03ce13f7SAndroid Build Coastguard Worker  4. The build dEQP binaries are used to test the change.  The full test results
172*03ce13f7SAndroid Build Coastguard Worker     are stored in a cached directory, and the each test is binned by status and
173*03ce13f7SAndroid Build Coastguard Worker     written to the [`<swiftshader>/tests/regres/testlists`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/testlists) directory.
174*03ce13f7SAndroid Build Coastguard Worker  5. A new Gerrit change is created containing the updated test lists and put up
175*03ce13f7SAndroid Build Coastguard Worker     for review, along with a summary of test result changes [[example]](https://swiftshader-review.googlesource.com/c/SwiftShader/+/46448).
176*03ce13f7SAndroid Build Coastguard Worker     If there's an existing daily test change up for review then this is reused
177*03ce13f7SAndroid Build Coastguard Worker     instead of creating another.
178*03ce13f7SAndroid Build Coastguard Worker  6. If the build included code coverage instrumentation, then the coverage
179*03ce13f7SAndroid Build Coastguard Worker     results are collated from all test runs, processed and compressed, and
180*03ce13f7SAndroid Build Coastguard Worker     uploaded to [github.com/swiftshader-regres/swiftshader-coverage](https://github.com/swiftshader-regres/swiftshader-coverage)
181*03ce13f7SAndroid Build Coastguard Worker     which is immediately reflected at [swiftshader-regres.github.io/swiftshader-coverage](https://swiftshader-regres.github.io/swiftshader-coverage).
182*03ce13f7SAndroid Build Coastguard Worker     This process is [described in more detail below](#code-coverage).
183*03ce13f7SAndroid Build Coastguard Worker  7. Stages 3 - 5 are repeated for both the LLVM and Subzero backends.
184*03ce13f7SAndroid Build Coastguard Worker
185*03ce13f7SAndroid Build Coastguard Worker### Caching
186*03ce13f7SAndroid Build Coastguard Worker
187*03ce13f7SAndroid Build Coastguard WorkerThe cache directory is heavily used to avoid duplicated work. For example, it
188*03ce13f7SAndroid Build Coastguard Workeris common for patchsets to be repeatedly pushed with the same parent change, so
189*03ce13f7SAndroid Build Coastguard Workerthe test results of the parent can be calculated once and stored. A tested
190*03ce13f7SAndroid Build Coastguard Workerpatchset that is merged into master would also be cached when used as a parent
191*03ce13f7SAndroid Build Coastguard Workerof another change.
192*03ce13f7SAndroid Build Coastguard Worker
193*03ce13f7SAndroid Build Coastguard WorkerThe cache needs to consider more than just the change identifier as the
194*03ce13f7SAndroid Build Coastguard Workercache-key for storing and retrieving data. Both the test lists and version of
195*03ce13f7SAndroid Build Coastguard WorkerdEQP used are dictated by the change being tested, and so both used as part of
196*03ce13f7SAndroid Build Coastguard Workerthe cache key.
197*03ce13f7SAndroid Build Coastguard Worker
198*03ce13f7SAndroid Build Coastguard Worker### Vulkan Loader usage
199*03ce13f7SAndroid Build Coastguard Worker
200*03ce13f7SAndroid Build Coastguard WorkerApplications make use of the Vulkan API by loading the [Vulkan Loader](https://github.com/KhronosGroup/Vulkan-Loader)
201*03ce13f7SAndroid Build Coastguard Workerlibrary (`libvulkan.so.1` on Linux), which enumerates available Vulkan
202*03ce13f7SAndroid Build Coastguard Workerimplementations (typically GPUs and their drivers) before an actual 'instance'
203*03ce13f7SAndroid Build Coastguard Workeris created to communicate with a specific Installable Client Driver (ICD).
204*03ce13f7SAndroid Build Coastguard Worker
205*03ce13f7SAndroid Build Coastguard WorkerHowever, SwiftShader can build into libvulkan.so.1 itself, which implements the
206*03ce13f7SAndroid Build Coastguard Workersame API entry functions as the Vulkan Loader. Regres by default will make dEQP
207*03ce13f7SAndroid Build Coastguard Workerload this SwiftShader library instead of the system's Vulkan Loader. It ensures
208*03ce13f7SAndroid Build Coastguard Workertest results are independent of the system's Vulkan setup.
209*03ce13f7SAndroid Build Coastguard Worker
210*03ce13f7SAndroid Build Coastguard WorkerTo override this, one can set LD_LIBRARY_PATH to point to the location of a
211*03ce13f7SAndroid Build Coastguard WorkerLoader's libvulkan.so.1.
212*03ce13f7SAndroid Build Coastguard Worker
213*03ce13f7SAndroid Build Coastguard Worker### Code coverage
214*03ce13f7SAndroid Build Coastguard Worker
215*03ce13f7SAndroid Build Coastguard WorkerThe [daily run](#daily-run-continuous-integration-testing) produces code
216*03ce13f7SAndroid Build Coastguard Workercoverage information that can be examined for each individual dEQP test at
217*03ce13f7SAndroid Build Coastguard Worker[swiftshader-regres.github.io/swiftshader-coverage](https://swiftshader-regres.github.io/swiftshader-coverage/).
218*03ce13f7SAndroid Build Coastguard Worker
219*03ce13f7SAndroid Build Coastguard WorkerThe process for generating this information is complex, and is described in
220*03ce13f7SAndroid Build Coastguard Workerdetail below:
221*03ce13f7SAndroid Build Coastguard Worker
222*03ce13f7SAndroid Build Coastguard Worker#### Per-test generation
223*03ce13f7SAndroid Build Coastguard Worker
224*03ce13f7SAndroid Build Coastguard WorkerCode coverage instrumentation is generated with
225*03ce13f7SAndroid Build Coastguard Worker[clang's `--coverage`](https://clang.llvm.org/docs/SourceBasedCodeCoverage.html)
226*03ce13f7SAndroid Build Coastguard Workerfunctionality. This compiler option is enabled by using SwiftShader's
227*03ce13f7SAndroid Build Coastguard Worker`SWIFTSHADER_EMIT_COVERAGE` CMake flag.
228*03ce13f7SAndroid Build Coastguard Worker
229*03ce13f7SAndroid Build Coastguard WorkerEach dEQP test process is run with a unique `LLVM_PROFILE_FILE` environment
230*03ce13f7SAndroid Build Coastguard Workervariable value which dictates where the process writes its raw coverage profile
231*03ce13f7SAndroid Build Coastguard Workerfile. Each process gets a different path so that we can emit coverage from
232*03ce13f7SAndroid Build Coastguard Workermultiple, concurrent dEQP test processes.
233*03ce13f7SAndroid Build Coastguard Worker
234*03ce13f7SAndroid Build Coastguard Worker#### Parsing
235*03ce13f7SAndroid Build Coastguard Worker
236*03ce13f7SAndroid Build Coastguard Worker[Clang provides two tools](https://clang.llvm.org/docs/SourceBasedCodeCoverage.html#creating-coverage-reports) for processing coverage data:
237*03ce13f7SAndroid Build Coastguard Worker
238*03ce13f7SAndroid Build Coastguard Worker* `llvm-profdata` indexes the raw `.profraw` coverage profile file and emits a
239*03ce13f7SAndroid Build Coastguard Worker  `.profdata` file.
240*03ce13f7SAndroid Build Coastguard Worker* `llvm-cov` further processes the `.profdata` file into something human
241*03ce13f7SAndroid Build Coastguard Worker  readable or machine parsable.
242*03ce13f7SAndroid Build Coastguard Worker
243*03ce13f7SAndroid Build Coastguard Worker`llvm-cov` provides many options, including emitting an pretty HTML file, but is
244*03ce13f7SAndroid Build Coastguard Workerremarkably slow at producing easily machine-parsable data. Fortunately the core
245*03ce13f7SAndroid Build Coastguard Workerof `llvm-cov` is [a few hundreds of lines of code](https://github.com/llvm/llvm-project/tree/master/llvm/tools/llvm-cov), as it relies on LLVM libraries to do the heavy lifting. Regres
246*03ce13f7SAndroid Build Coastguard Workerreplaces `llvm-cov` with ["`turbo-cov`"](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/cov/turbo-cov/) which efficiently converts a `.profdata` into a simple binary stream which can
247*03ce13f7SAndroid Build Coastguard Workerbe consumed by Regres.
248*03ce13f7SAndroid Build Coastguard Worker
249*03ce13f7SAndroid Build Coastguard Worker#### Processing
250*03ce13f7SAndroid Build Coastguard Worker
251*03ce13f7SAndroid Build Coastguard WorkerAt the time of writing there are over 560,000 individual dEQP tests, and around
252*03ce13f7SAndroid Build Coastguard Worker176,000 lines of C++ code in [`<swiftshader>/src`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:src/).
253*03ce13f7SAndroid Build Coastguard WorkerIf you used 1 bit for each source line, per-line source coverage for all dEQP
254*03ce13f7SAndroid Build Coastguard Workertests would require over 11GiB of storage. That's just for one snapshot.
255*03ce13f7SAndroid Build Coastguard Worker
256*03ce13f7SAndroid Build Coastguard WorkerThe processing and compression schemes described below reduces this down to
257*03ce13f7SAndroid Build Coastguard Workeraround 10 MiB (~1100x reduction in size), and supports sub-line coverage scopes.
258*03ce13f7SAndroid Build Coastguard Worker
259*03ce13f7SAndroid Build Coastguard Worker##### Spans
260*03ce13f7SAndroid Build Coastguard Worker
261*03ce13f7SAndroid Build Coastguard WorkerCode coverage information is described in spans.
262*03ce13f7SAndroid Build Coastguard Worker
263*03ce13f7SAndroid Build Coastguard WorkerA span is a described as an interval of source locations, where a location is a
264*03ce13f7SAndroid Build Coastguard Workerline-column pair:
265*03ce13f7SAndroid Build Coastguard Worker
266*03ce13f7SAndroid Build Coastguard Worker```go
267*03ce13f7SAndroid Build Coastguard Workertype Location struct {
268*03ce13f7SAndroid Build Coastguard Worker    Line, Column int
269*03ce13f7SAndroid Build Coastguard Worker}
270*03ce13f7SAndroid Build Coastguard Worker
271*03ce13f7SAndroid Build Coastguard Workertype Span struct {
272*03ce13f7SAndroid Build Coastguard Worker    Start, End Location
273*03ce13f7SAndroid Build Coastguard Worker}
274*03ce13f7SAndroid Build Coastguard Worker```
275*03ce13f7SAndroid Build Coastguard Worker
276*03ce13f7SAndroid Build Coastguard Worker##### Test tree construction
277*03ce13f7SAndroid Build Coastguard Worker
278*03ce13f7SAndroid Build Coastguard WorkerEach dEQP test is uniquely identified by a fully qualified name.
279*03ce13f7SAndroid Build Coastguard WorkerEach test belongs to a group, and that group may be nested within any number of
280*03ce13f7SAndroid Build Coastguard Workerparent groups. The groups are described in the test name, using dots (`.`) to
281*03ce13f7SAndroid Build Coastguard Workerdelimit the groups and leaf test name.
282*03ce13f7SAndroid Build Coastguard Worker
283*03ce13f7SAndroid Build Coastguard WorkerFor example, the fully qualified test name:
284*03ce13f7SAndroid Build Coastguard Worker
285*03ce13f7SAndroid Build Coastguard Worker`dEQP-VK.fragment_shader_interlock.basic.discard.ssbo.sample_unordered.4xaa.sample_shading.16x16`
286*03ce13f7SAndroid Build Coastguard Worker
287*03ce13f7SAndroid Build Coastguard WorkerCan be broken down into the following groups and test name:
288*03ce13f7SAndroid Build Coastguard Worker
289*03ce13f7SAndroid Build Coastguard Worker```text
290*03ce13f7SAndroid Build Coastguard WorkerdEQP-VK                       <-- root group name
291*03ce13f7SAndroid Build Coastguard Worker╰ fragment_shader_interlock
292*03ce13f7SAndroid Build Coastguard Workerbasic.discard
293*03ce13f7SAndroid Build Coastguard Worker    ╰ ssbo
294*03ce13f7SAndroid Build Coastguard Worker      ╰ sample_unordered
295*03ce13f7SAndroid Build Coastguard Worker        ╰ 4xaa
296*03ce13f7SAndroid Build Coastguard Worker          ╰ sample_shading
297*03ce13f7SAndroid Build Coastguard Worker            ╰ 16x16           <-- leaf test name
298*03ce13f7SAndroid Build Coastguard Worker```
299*03ce13f7SAndroid Build Coastguard Worker
300*03ce13f7SAndroid Build Coastguard WorkerBreaking down fully qualified test names into groups provide a natural way to
301*03ce13f7SAndroid Build Coastguard Workerstructure coverage data, as tests of the same group are likely to have similar
302*03ce13f7SAndroid Build Coastguard Workercoverage spans.
303*03ce13f7SAndroid Build Coastguard Worker
304*03ce13f7SAndroid Build Coastguard WorkerSo, for each source file in the codebase, we create a tree with test groups as
305*03ce13f7SAndroid Build Coastguard Workernon-leaf nodes, and tests as leaf nodes.
306*03ce13f7SAndroid Build Coastguard Worker
307*03ce13f7SAndroid Build Coastguard WorkerFor example, given the following test list:
308*03ce13f7SAndroid Build Coastguard Worker
309*03ce13f7SAndroid Build Coastguard Worker```text
310*03ce13f7SAndroid Build Coastguard Workera.b.d.h
311*03ce13f7SAndroid Build Coastguard Workera.b.d.i.n
312*03ce13f7SAndroid Build Coastguard Workera.b.d.i.o
313*03ce13f7SAndroid Build Coastguard Workera.b.e.j
314*03ce13f7SAndroid Build Coastguard Workera.b.e.k.p
315*03ce13f7SAndroid Build Coastguard Workera.b.e.k.q
316*03ce13f7SAndroid Build Coastguard Workera.c.f
317*03ce13f7SAndroid Build Coastguard Workera.c.g.l.r
318*03ce13f7SAndroid Build Coastguard Workera.c.g.m
319*03ce13f7SAndroid Build Coastguard Worker```
320*03ce13f7SAndroid Build Coastguard Worker
321*03ce13f7SAndroid Build Coastguard WorkerWe would construct the following tree:
322*03ce13f7SAndroid Build Coastguard Worker
323*03ce13f7SAndroid Build Coastguard Worker```text
324*03ce13f7SAndroid Build Coastguard Worker               a
325*03ce13f7SAndroid Build Coastguard Worker        ╭──────┴──────╮
326*03ce13f7SAndroid Build Coastguard Worker        b             c
327*03ce13f7SAndroid Build Coastguard Worker    ╭───┴───╮     ╭───┴───╮
328*03ce13f7SAndroid Build Coastguard Worker    d       e     f       g
329*03ce13f7SAndroid Build Coastguard Worker  ╭─┴─╮   ╭─┴─╮         ╭─┴─╮
330*03ce13f7SAndroid Build Coastguard Worker  h   i   j   k         l   m
331*03ce13f7SAndroid Build Coastguard Worker     ╭┴╮     ╭┴╮        │
332*03ce13f7SAndroid Build Coastguard Worker     n o     p q        r
333*03ce13f7SAndroid Build Coastguard Worker
334*03ce13f7SAndroid Build Coastguard Worker```
335*03ce13f7SAndroid Build Coastguard Worker
336*03ce13f7SAndroid Build Coastguard WorkerEach leaf node in this tree (`h`, `n`, `o`, `j`, `p`, `q`, `f`, `r`, `m`)
337*03ce13f7SAndroid Build Coastguard Workerrepresent a test, and non-leaf nodes (`a`, `b`, `c`, `d`, `e`, `g`, `i`, `k`,
338*03ce13f7SAndroid Build Coastguard Worker`l`) are a groups.
339*03ce13f7SAndroid Build Coastguard Worker
340*03ce13f7SAndroid Build Coastguard WorkerTo begin, we create a test tree structure, and associate the full list of test
341*03ce13f7SAndroid Build Coastguard Workercoverage spans with every leaf node (test) in this tree.
342*03ce13f7SAndroid Build Coastguard Worker
343*03ce13f7SAndroid Build Coastguard WorkerThis data structure hasn't given us any compression benefits yet, but we can
344*03ce13f7SAndroid Build Coastguard Workernow do a few tricks to dramatically reduce number of spans needed to describe
345*03ce13f7SAndroid Build Coastguard Workerthe graph:
346*03ce13f7SAndroid Build Coastguard Worker
347*03ce13f7SAndroid Build Coastguard Worker##### Optimization 1: Common span promotion
348*03ce13f7SAndroid Build Coastguard Worker
349*03ce13f7SAndroid Build Coastguard WorkerThe first compression scheme is to promote common spans up the tree when they
350*03ce13f7SAndroid Build Coastguard Workerare common for all children. This will reduce the number of spans needed to be
351*03ce13f7SAndroid Build Coastguard Workerencoded in the final file.
352*03ce13f7SAndroid Build Coastguard Worker
353*03ce13f7SAndroid Build Coastguard WorkerFor example, if the test group `a` has 4 children that all share the same span
354*03ce13f7SAndroid Build Coastguard Worker`X`:
355*03ce13f7SAndroid Build Coastguard Worker
356*03ce13f7SAndroid Build Coastguard Worker```text
357*03ce13f7SAndroid Build Coastguard Worker          a
358*03ce13f7SAndroid Build Coastguard Worker    ╭───┬─┴─┬───╮
359*03ce13f7SAndroid Build Coastguard Worker    b   c   d   e
360*03ce13f7SAndroid Build Coastguard Worker [X,Y] [X] [X] [X,Z]
361*03ce13f7SAndroid Build Coastguard Worker```
362*03ce13f7SAndroid Build Coastguard Worker
363*03ce13f7SAndroid Build Coastguard WorkerThen span `X` can be promoted up to `a`:
364*03ce13f7SAndroid Build Coastguard Worker
365*03ce13f7SAndroid Build Coastguard Worker```text
366*03ce13f7SAndroid Build Coastguard Worker         [X]
367*03ce13f7SAndroid Build Coastguard Worker          a
368*03ce13f7SAndroid Build Coastguard Worker    ╭───┬─┴─┬───╮
369*03ce13f7SAndroid Build Coastguard Worker    b   c   d   e
370*03ce13f7SAndroid Build Coastguard Worker   [Y] []   [] [Z]
371*03ce13f7SAndroid Build Coastguard Worker```
372*03ce13f7SAndroid Build Coastguard Worker
373*03ce13f7SAndroid Build Coastguard Worker##### Optimization 2: Span XOR promotion
374*03ce13f7SAndroid Build Coastguard Worker
375*03ce13f7SAndroid Build Coastguard WorkerThis idea can be extended further, by not requiring all the children to share
376*03ce13f7SAndroid Build Coastguard Workerthe same span before promotion. If **most** child nodes share the same span, we
377*03ce13f7SAndroid Build Coastguard Workercan still promote the span, but this time we **remove** the span from the
378*03ce13f7SAndroid Build Coastguard Workerchildren **if they had it**, and **add** the span to children **if they didn't
379*03ce13f7SAndroid Build Coastguard Workerhave it**.
380*03ce13f7SAndroid Build Coastguard Worker
381*03ce13f7SAndroid Build Coastguard WorkerFor example, if the test group `a` has 4 children with 3 that share the span
382*03ce13f7SAndroid Build Coastguard Worker`X`:
383*03ce13f7SAndroid Build Coastguard Worker
384*03ce13f7SAndroid Build Coastguard Worker```text
385*03ce13f7SAndroid Build Coastguard Worker          a
386*03ce13f7SAndroid Build Coastguard Worker    ╭───┬─┴─┬───╮
387*03ce13f7SAndroid Build Coastguard Worker    b   c   d   e
388*03ce13f7SAndroid Build Coastguard Worker [X,Y] [X]  [] [X,Z]
389*03ce13f7SAndroid Build Coastguard Worker```
390*03ce13f7SAndroid Build Coastguard Worker
391*03ce13f7SAndroid Build Coastguard WorkerThen span `X` can be promoted up to `a` by flipping the presence of `X` on the
392*03ce13f7SAndroid Build Coastguard Workerchild nodes:
393*03ce13f7SAndroid Build Coastguard Worker
394*03ce13f7SAndroid Build Coastguard Worker```text
395*03ce13f7SAndroid Build Coastguard Worker         [X]
396*03ce13f7SAndroid Build Coastguard Worker          a
397*03ce13f7SAndroid Build Coastguard Worker    ╭───┬─┴─┬───╮
398*03ce13f7SAndroid Build Coastguard Worker    b   c   d   e
399*03ce13f7SAndroid Build Coastguard Worker   [Y] []  [X] [Z]
400*03ce13f7SAndroid Build Coastguard Worker```
401*03ce13f7SAndroid Build Coastguard Worker
402*03ce13f7SAndroid Build Coastguard WorkerThis process repeats up the tree.
403*03ce13f7SAndroid Build Coastguard Worker
404*03ce13f7SAndroid Build Coastguard WorkerWith this optimization applied, we now need to traverse the tree from root to
405*03ce13f7SAndroid Build Coastguard Workerleaf in order to know whether a given span is in use for the leaf node (test):
406*03ce13f7SAndroid Build Coastguard Worker
407*03ce13f7SAndroid Build Coastguard Worker* If the span is encountered an **odd** number of times during traversal, then
408*03ce13f7SAndroid Build Coastguard Worker  the span is **covered**.
409*03ce13f7SAndroid Build Coastguard Worker* If the span is encountered an **even** number of times during traversal, then
410*03ce13f7SAndroid Build Coastguard Worker  the span is **not covered**.
411*03ce13f7SAndroid Build Coastguard Worker
412*03ce13f7SAndroid Build Coastguard WorkerSee [`tests/regres/cov/coverage_test.go`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/cov/coverage_test.go) for more examples of this optimization.
413*03ce13f7SAndroid Build Coastguard Worker
414*03ce13f7SAndroid Build Coastguard Worker##### Optimization 3: Common span grouping
415*03ce13f7SAndroid Build Coastguard Worker
416*03ce13f7SAndroid Build Coastguard WorkerWith real world data, we encounter groups of spans that are commonly found
417*03ce13f7SAndroid Build Coastguard Workertogether. To further reduce coverage data, the whole graph is scanned for common
418*03ce13f7SAndroid Build Coastguard Workerspan patterns, and are indexed by each tree node.
419*03ce13f7SAndroid Build Coastguard WorkerThe XOR'ing of spans as described above is performed as if the spans were not
420*03ce13f7SAndroid Build Coastguard Workergrouped.
421*03ce13f7SAndroid Build Coastguard Worker
422*03ce13f7SAndroid Build Coastguard Worker##### Optimization 4: Lookup tables
423*03ce13f7SAndroid Build Coastguard Worker
424*03ce13f7SAndroid Build Coastguard WorkerAll spans, span-groups and strings are stored in de-duplicated tables, and are
425*03ce13f7SAndroid Build Coastguard Workerindexed wherever possible.
426*03ce13f7SAndroid Build Coastguard Worker
427*03ce13f7SAndroid Build Coastguard WorkerThe final serialization is performed by [`tests/regres/cov/serialization.go`](https://cs.opensource.google/swiftshader/SwiftShader/+/master:tests/regres/cov/serialization.go).
428*03ce13f7SAndroid Build Coastguard Worker
429*03ce13f7SAndroid Build Coastguard Worker##### Optimization 5: zlib compression
430*03ce13f7SAndroid Build Coastguard Worker
431*03ce13f7SAndroid Build Coastguard WorkerThe coverage data is encoded into JSON for parsing by the web page.
432*03ce13f7SAndroid Build Coastguard Worker
433*03ce13f7SAndroid Build Coastguard WorkerBefore writing the JSON file, the text data is zlib compressed.
434*03ce13f7SAndroid Build Coastguard Worker
435*03ce13f7SAndroid Build Coastguard Worker#### Presentation
436*03ce13f7SAndroid Build Coastguard Worker
437*03ce13f7SAndroid Build Coastguard WorkerThe zlib-compressed JSON coverage data is decompressed using
438*03ce13f7SAndroid Build Coastguard Worker[`pako`](https://github.com/nodeca/pako), and consumed by some
439*03ce13f7SAndroid Build Coastguard Worker[vanilla JavaScript](https://github.com/swiftshader-regres/swiftshader-coverage/blob/gh-pages/index.html).
440*03ce13f7SAndroid Build Coastguard Worker
441*03ce13f7SAndroid Build Coastguard Worker[`codemirror`](https://codemirror.net/) is used to perform coverage span and C++
442*03ce13f7SAndroid Build Coastguard Workersyntax highlighting
443