Skip to content

Commit 3ce40e5

Browse files
authored
Merge branch 'main' into user/kdhawaniya/android-idataviewer-api
2 parents 8e97566 + 88defca commit 3ce40e5

39 files changed

Lines changed: 1606 additions & 988 deletions

‎.github/memory-leak-baseline.csv‎

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
Platform,Scenario,UniqueLeaks,TotalLeaks,LeakBytes,UniquePossibleLeaks,TotalPossibleLeaks,PossibleLeakBytes,UniqueReachable,TotalReachable,ReachableBytes
2+
Windows,unit-tests,10,113,4256,14,15,7206,467,644,227717
3+
Windows,functional-tests,7,382,14072,7,3994,1038248411,1722,2823,725167
4+
Windows,sample-cpp-mini,0,0,0,0,0,0,973,1795,411008
5+
Linux,unit-tests,10,127,3730,5,7,3452,8,8,77045
6+
Linux,functional-tests,3,156,4694,1,1,4104,360,643,279619
7+
Linux,sample-cpp-mini,1,2,32,0,0,0,15,23,81130

‎.github/scripts/run-drmemory.ps1‎

Lines changed: 153 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,153 @@
1+
[CmdletBinding()]
2+
param(
3+
[Parameter(Mandatory = $true)]
4+
[ValidateNotNullOrEmpty()]
5+
[string]$DrMemoryPath,
6+
7+
[Parameter(Mandatory = $true)]
8+
[ValidateNotNullOrEmpty()]
9+
[string]$LogDirectory,
10+
11+
[Parameter(Mandatory = $true)]
12+
[ValidatePattern('^[A-Za-z0-9_.-]+$')]
13+
[string]$Scenario,
14+
15+
[Parameter(Mandatory = $true)]
16+
[ValidateNotNullOrEmpty()]
17+
[string]$TargetPath,
18+
19+
[string[]]$TargetArguments = @(),
20+
21+
[string]$BaselinePath
22+
)
23+
24+
Set-StrictMode -Version Latest
25+
$ErrorActionPreference = "Stop"
26+
27+
function Get-LeakCount {
28+
param(
29+
[Parameter(Mandatory = $true)]
30+
[string]$Results,
31+
32+
[Parameter(Mandatory = $true)]
33+
[string]$Category
34+
)
35+
36+
$escapedCategory = [regex]::Escape($Category)
37+
$pattern = "(?m)^\s*(?:~~Dr\.M~~\s+)?([\d,]+) unique,\s+([\d,]+) total,\s+([\d,]+) byte\(s\) of $escapedCategory\r?$"
38+
$match = [regex]::Match($Results, $pattern)
39+
if (-not $match.Success) {
40+
throw "Dr. Memory results do not contain the '$Category' summary."
41+
}
42+
43+
return @{
44+
Unique = [int64]($match.Groups[1].Value -replace ",", "")
45+
Total = [int64]($match.Groups[2].Value -replace ",", "")
46+
Bytes = [int64]($match.Groups[3].Value -replace ",", "")
47+
}
48+
}
49+
50+
$resolvedDrMemoryPath = (Resolve-Path -LiteralPath $DrMemoryPath).Path
51+
$resolvedTargetPath = (Resolve-Path -LiteralPath $TargetPath).Path
52+
$resolvedLogDirectory = [System.IO.Path]::GetFullPath($LogDirectory)
53+
$scenarioDirectory = Join-Path $resolvedLogDirectory $Scenario
54+
New-Item -ItemType Directory -Path $scenarioDirectory -Force | Out-Null
55+
56+
Write-Host "Running Dr. Memory leak analysis for $Scenario"
57+
& $resolvedDrMemoryPath `
58+
-batch `
59+
-leaks_only `
60+
-logdir $scenarioDirectory `
61+
-- `
62+
$resolvedTargetPath `
63+
@TargetArguments
64+
$targetExitCode = $LASTEXITCODE
65+
if ($targetExitCode -ne 0) {
66+
throw "Dr. Memory or $Scenario exited with code $targetExitCode."
67+
}
68+
69+
$resultFiles = @(Get-ChildItem -LiteralPath $scenarioDirectory -Filter results.txt -File -Recurse)
70+
$resultFiles = @($resultFiles | Where-Object {
71+
Select-String -LiteralPath $_.FullName -Pattern '^(?:NO )?ERRORS FOUND:\r?$' -Quiet
72+
})
73+
if ($resultFiles.Count -ne 1) {
74+
throw "Expected one completed Dr. Memory results.txt for $Scenario, found $($resultFiles.Count)."
75+
}
76+
77+
$results = Get-Content -LiteralPath $resultFiles[0].FullName -Raw
78+
$leaks = Get-LeakCount -Results $results -Category "leak(s)"
79+
$possibleLeaks = Get-LeakCount -Results $results -Category "possible leak(s)"
80+
$reachable = Get-LeakCount -Results $results -Category "still-reachable allocation(s)"
81+
82+
$summary = [pscustomobject]@{
83+
Platform = if ($env:RUNNER_OS) { $env:RUNNER_OS } else { [System.Environment]::OSVersion.Platform }
84+
Scenario = $Scenario
85+
UniqueLeaks = $leaks.Unique
86+
TotalLeaks = $leaks.Total
87+
LeakBytes = $leaks.Bytes
88+
UniquePossibleLeaks = $possibleLeaks.Unique
89+
TotalPossibleLeaks = $possibleLeaks.Total
90+
PossibleLeakBytes = $possibleLeaks.Bytes
91+
UniqueReachable = $reachable.Unique
92+
TotalReachable = $reachable.Total
93+
ReachableBytes = $reachable.Bytes
94+
}
95+
96+
$summaryPath = Join-Path $resolvedLogDirectory "summary.csv"
97+
$summaries = if (Test-Path -LiteralPath $summaryPath) {
98+
@(Import-Csv -LiteralPath $summaryPath) + @($summary)
99+
}
100+
else {
101+
@($summary)
102+
}
103+
$summaries | Export-Csv -LiteralPath $summaryPath -NoTypeInformation
104+
105+
$baselineStatus = "Not compared"
106+
if ($BaselinePath) {
107+
$resolvedBaselinePath = (Resolve-Path -LiteralPath $BaselinePath).Path
108+
$baselineRows = @(Import-Csv -LiteralPath $resolvedBaselinePath | Where-Object {
109+
$_.Platform -eq $summary.Platform -and $_.Scenario -eq $summary.Scenario
110+
})
111+
if ($baselineRows.Count -ne 1) {
112+
throw "Expected one baseline for $($summary.Platform)/$Scenario, found $($baselineRows.Count)."
113+
}
114+
115+
$regressions = @()
116+
foreach ($metric in @(
117+
"UniqueLeaks",
118+
"TotalLeaks",
119+
"LeakBytes",
120+
"UniquePossibleLeaks",
121+
"TotalPossibleLeaks",
122+
"PossibleLeakBytes",
123+
"UniqueReachable",
124+
"TotalReachable",
125+
"ReachableBytes"
126+
)) {
127+
$currentValue = [int64]$summary.$metric
128+
$baselineValue = [int64]$baselineRows[0].$metric
129+
if ($currentValue -gt $baselineValue) {
130+
$regressions += "$metric increased from $baselineValue to $currentValue"
131+
}
132+
}
133+
134+
if ($regressions.Count -eq 0) {
135+
$baselineStatus = "At or below baseline"
136+
}
137+
else {
138+
$baselineStatus = "$($regressions.Count) increase(s)"
139+
foreach ($regression in $regressions) {
140+
Write-Host "::warning title=Dr. Memory regression ($($summary.Platform)/$Scenario)::$regression"
141+
}
142+
}
143+
}
144+
145+
$markdown = @"
146+
| Scenario | Unique leaks | Total leaks | Leak bytes | Unique possible | Total possible | Possible bytes | Unique reachable | Total reachable | Reachable bytes | Baseline |
147+
|---|---:|---:|---:|---:|---:|---:|---:|---:|---:|---|
148+
| $Scenario | $($leaks.Unique) | $($leaks.Total) | $($leaks.Bytes) | $($possibleLeaks.Unique) | $($possibleLeaks.Total) | $($possibleLeaks.Bytes) | $($reachable.Unique) | $($reachable.Total) | $($reachable.Bytes) | $baselineStatus |
149+
"@
150+
Write-Host $markdown
151+
if ($env:GITHUB_STEP_SUMMARY) {
152+
Add-Content -LiteralPath $env:GITHUB_STEP_SUMMARY -Value $markdown
153+
}
Lines changed: 227 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,227 @@
1+
name: Memory leak analysis
2+
3+
on:
4+
workflow_dispatch:
5+
schedule:
6+
- cron: 0 8 * * 1
7+
push:
8+
branches:
9+
- main
10+
paths:
11+
- .github/scripts/run-drmemory.ps1
12+
- .github/memory-leak-baseline.csv
13+
- .github/workflows/memory-leak-analysis.yml
14+
- CMakeLists.txt
15+
- CMakePresets.json
16+
- Solutions/**
17+
- cmake/**
18+
- examples/cpp/SampleCppMini/**
19+
- lib/**
20+
- sqlite/**
21+
- tests/**
22+
- third_party/Solutions/zlib/**
23+
- third_party/googletest
24+
- tools/gen-version.cmd
25+
- zlib/**
26+
pull_request:
27+
branches:
28+
- main
29+
paths:
30+
- .github/scripts/run-drmemory.ps1
31+
- .github/memory-leak-baseline.csv
32+
- .github/workflows/memory-leak-analysis.yml
33+
34+
permissions:
35+
contents: read
36+
37+
concurrency:
38+
group: memory-leak-analysis-${{ github.ref }}
39+
cancel-in-progress: false
40+
41+
env:
42+
DRMEMORY_VERSION: 2.6.20434
43+
DRMEMORY_TAG: cronbuild-2.6.20434
44+
45+
jobs:
46+
windows:
47+
name: Dr. Memory on Windows
48+
runs-on: windows-2022
49+
timeout-minutes: 120
50+
steps:
51+
- name: Checkout
52+
uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4.4.0
53+
54+
- name: Initialize googletest
55+
run: git submodule update --init --depth=1 third_party/googletest
56+
57+
- name: Setup MSBuild
58+
uses: microsoft/setup-msbuild@6fb02220983dee41ce7ae257b6f4d8f9bf5ed4ce # v2.0.0
59+
with:
60+
vs-version: '[17,)'
61+
62+
- name: Build leak-analysis targets
63+
shell: cmd
64+
run: >-
65+
tools\gen-version.cmd &&
66+
msbuild Solutions\MSTelemetrySDK.sln
67+
/target:sqlite:Rebuild,zlib:Rebuild,Tests\gmock:Rebuild,Tests\gtest:Rebuild,Tests\UnitTests:Rebuild,Tests\FuncTests:Rebuild,Samples\cpp\SampleCppMini:Rebuild
68+
/p:BuildProjectReferences=true
69+
/p:Configuration=Debug
70+
/p:Platform=x64
71+
/maxcpucount:2
72+
73+
- name: Download Dr. Memory
74+
shell: pwsh
75+
env:
76+
DRMEMORY_SHA256: ED9C0E3F1BDB7F8DB1ADC13531493FB1C451E15F375638592C01D8837825A73A
77+
run: |
78+
$archive = Join-Path $env:RUNNER_TEMP "DrMemory-Windows-$env:DRMEMORY_VERSION.zip"
79+
$url = "https://github.com/DynamoRIO/drmemory/releases/download/$env:DRMEMORY_TAG/DrMemory-Windows-$env:DRMEMORY_VERSION.zip"
80+
Invoke-WebRequest -Uri $url -OutFile $archive
81+
$actualHash = (Get-FileHash -LiteralPath $archive -Algorithm SHA256).Hash
82+
if ($actualHash -ne $env:DRMEMORY_SHA256) {
83+
throw "Dr. Memory archive hash mismatch: expected $env:DRMEMORY_SHA256, got $actualHash."
84+
}
85+
Expand-Archive -LiteralPath $archive -DestinationPath $env:RUNNER_TEMP
86+
87+
- name: Analyze unit tests
88+
shell: pwsh
89+
run: >-
90+
./.github/scripts/run-drmemory.ps1
91+
-DrMemoryPath "$env:RUNNER_TEMP/DrMemory-Windows-$env:DRMEMORY_VERSION/bin64/drmemory.exe"
92+
-LogDirectory drmemory-results
93+
-Scenario unit-tests
94+
-TargetPath Solutions/out/Debug/x64/UnitTests/UnitTests.exe
95+
-BaselinePath .github/memory-leak-baseline.csv
96+
-TargetArguments "--gtest_filter=-OfflineStorageTests_SQLite.StoreThousandEventsTakesLessThanASecond"
97+
98+
- name: Analyze functional tests
99+
shell: pwsh
100+
run: >-
101+
./.github/scripts/run-drmemory.ps1
102+
-DrMemoryPath "$env:RUNNER_TEMP/DrMemory-Windows-$env:DRMEMORY_VERSION/bin64/drmemory.exe"
103+
-LogDirectory drmemory-results
104+
-Scenario functional-tests
105+
-TargetPath Solutions/out/Debug/x64/FuncTests/FuncTests.exe
106+
-BaselinePath .github/memory-leak-baseline.csv
107+
-TargetArguments "--gtest_filter=-BasicFuncTests.killSwitchWorks"
108+
109+
- name: Analyze basic sample
110+
shell: pwsh
111+
run: >-
112+
./.github/scripts/run-drmemory.ps1
113+
-DrMemoryPath "$env:RUNNER_TEMP/DrMemory-Windows-$env:DRMEMORY_VERSION/bin64/drmemory.exe"
114+
-LogDirectory drmemory-results
115+
-Scenario sample-cpp-mini
116+
-BaselinePath .github/memory-leak-baseline.csv
117+
-TargetPath Solutions/out/Debug/x64/SampleCppMini/SampleCppMini.exe
118+
119+
- name: Verify Network List Manager is not loaded
120+
shell: pwsh
121+
run: |
122+
$moduleLogs = @()
123+
foreach ($scenario in @("unit-tests", "functional-tests", "sample-cpp-mini")) {
124+
$scenarioLogs = @(Get-ChildItem "drmemory-results/$scenario" -Filter global.*.log -File -Recurse)
125+
if ($scenarioLogs.Count -eq 0) {
126+
throw "Dr. Memory did not produce a module log for $scenario."
127+
}
128+
$moduleLogs += $scenarioLogs
129+
}
130+
$matches = $moduleLogs | Select-String -Pattern 'module load event:\s+"netprofm\.dll"'
131+
if ($matches) {
132+
$matches | ForEach-Object { Write-Error "$($_.Path):$($_.LineNumber): $($_.Line)" }
133+
throw "Network detection loaded netprofm.dll."
134+
}
135+
136+
- name: Upload Windows reports
137+
if: always()
138+
uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4.6.2
139+
with:
140+
name: drmemory-windows
141+
path: drmemory-results
142+
if-no-files-found: error
143+
retention-days: 90
144+
145+
linux:
146+
name: Dr. Memory on Linux
147+
runs-on: ubuntu-22.04
148+
timeout-minutes: 120
149+
env:
150+
CMAKE_POLICY_VERSION_MINIMUM: "3.5"
151+
steps:
152+
- name: Checkout
153+
uses: actions/checkout@11d5960a326750d5838078e36cf38b85af677262 # v4.4.0
154+
155+
- name: Initialize googletest
156+
run: git submodule update --init --depth=1 third_party/googletest
157+
158+
- name: Install build dependencies
159+
run: |
160+
sudo apt-get update
161+
sudo apt-get install -y libcurl4-openssl-dev
162+
163+
- name: Build leak-analysis targets
164+
run: |
165+
cmake --preset matsdk-debug \
166+
-DMATSDK_BUILD_UNIT_TESTS=ON \
167+
-DMATSDK_BUILD_FUNC_TESTS=ON
168+
cmake --build --preset matsdk-debug --parallel 2
169+
170+
- name: Build basic sample
171+
run: |
172+
cmake --install out --prefix "$PWD/out/install"
173+
cmake -S examples/cpp/SampleCppMini -B out/sample-cpp-mini \
174+
-DCMAKE_BUILD_TYPE=Debug \
175+
-DCMAKE_DISABLE_FIND_PACKAGE_MSTelemetry=TRUE \
176+
-DMATSDK_INSTALL_DIR="$PWD/out/install"
177+
cmake --build out/sample-cpp-mini --parallel 2
178+
179+
- name: Download Dr. Memory
180+
env:
181+
DRMEMORY_SHA256: 79B7718C0040A68B4FCECD9BA1C422174350A5B3A40A8417047A9219E9C2F258
182+
run: |
183+
archive="$RUNNER_TEMP/DrMemory-Linux-$DRMEMORY_VERSION.tar.gz"
184+
url="https://github.com/DynamoRIO/drmemory/releases/download/$DRMEMORY_TAG/DrMemory-Linux-$DRMEMORY_VERSION.tar.gz"
185+
curl --fail --location --retry 3 --output "$archive" "$url"
186+
echo "$DRMEMORY_SHA256 $archive" | sha256sum --check --strict
187+
tar -xzf "$archive" -C "$RUNNER_TEMP"
188+
189+
- name: Analyze unit tests
190+
shell: pwsh
191+
run: >-
192+
./.github/scripts/run-drmemory.ps1
193+
-DrMemoryPath "$env:RUNNER_TEMP/DrMemory-Linux-$env:DRMEMORY_VERSION/bin64/drmemory"
194+
-LogDirectory drmemory-results
195+
-Scenario unit-tests
196+
-BaselinePath .github/memory-leak-baseline.csv
197+
-TargetPath out/tests/unittests/UnitTests
198+
199+
- name: Analyze functional tests
200+
shell: pwsh
201+
run: >-
202+
./.github/scripts/run-drmemory.ps1
203+
-DrMemoryPath "$env:RUNNER_TEMP/DrMemory-Linux-$env:DRMEMORY_VERSION/bin64/drmemory"
204+
-LogDirectory drmemory-results
205+
-Scenario functional-tests
206+
-TargetPath out/tests/functests/FuncTests
207+
-BaselinePath .github/memory-leak-baseline.csv
208+
-TargetArguments "--gtest_filter=-BasicFuncTests.killSwitchWorks"
209+
210+
- name: Analyze basic sample
211+
shell: pwsh
212+
run: >-
213+
./.github/scripts/run-drmemory.ps1
214+
-DrMemoryPath "$env:RUNNER_TEMP/DrMemory-Linux-$env:DRMEMORY_VERSION/bin64/drmemory"
215+
-LogDirectory drmemory-results
216+
-Scenario sample-cpp-mini
217+
-BaselinePath .github/memory-leak-baseline.csv
218+
-TargetPath out/sample-cpp-mini/SampleCppMini
219+
220+
- name: Upload Linux reports
221+
if: always()
222+
uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4.6.2
223+
with:
224+
name: drmemory-linux
225+
path: drmemory-results
226+
if-no-files-found: error
227+
retention-days: 90

‎.github/workflows/test-win-latest.yml‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -75,7 +75,7 @@ jobs:
7575
retention-days: 7
7676

7777
public-headers:
78-
name: Public header gate (MSVC)
78+
name: Public header gate (MSVC, Windows 10 API floor)
7979
runs-on: windows-2022
8080
steps:
8181
- name: Checkout

0 commit comments

Comments
 (0)