Skip to content

Commit 8d85c5a

Browse files
Maxime XuMridul Muralidharan
authored andcommitted
[SPARK-52776][CORE][3.5] Do not split the comm field in ProcfsMetricsGetter
### What changes were proposed in this pull request? This is a backport of #51457. We are fixing an issue in `ProcfsMetricsGetter` when parsing the `/proc/<pid>/stat` file. The current implementation will split the comm field by spaces if it contains them, thereby causing subsequent numbers to be shifted. The comm field, and only the comm field, is in parentheses so we can resolve this issue by ignoring everything between the first open parenthesis and last closing parenthesis when splitting the stat file. ### Why are the changes needed? These changes are needed to prevent a comm field with spaces from causing incorrect calculations for vmem/rssmem metrics. Please see [JIRA](https://issues.apache.org/jira/projects/SPARK/issues/SPARK-52776) for details. ### Does this PR introduce _any_ user-facing change? No ### How was this patch tested? Added a unit test to test for irregular characters in the comm field ### Was this patch authored or co-authored using generative AI tooling? No ### Original PR Info Closes #51457 from max2718281/procfs. Authored-by: Maxime Xu <maxxulinkedin.com> (cherry picked from commit cf097a5) Closes #51481 from max2718281/procfs-3.5. Authored-by: Maxime Xu <[email protected]> Signed-off-by: Mridul Muralidharan <mridul<at>gmail.com>
1 parent eb123a1 commit 8d85c5a

File tree

3 files changed

+21
-1
lines changed

3 files changed

+21
-1
lines changed

core/src/main/scala/org/apache/spark/executor/ProcfsMetricsGetter.scala

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -176,7 +176,14 @@ private[spark] class ProcfsMetricsGetter(procfsDir: String = "/proc/") extends L
176176
}
177177
Utils.tryWithResource(openReader) { in =>
178178
val procInfo = in.readLine
179-
val procInfoSplit = procInfo.split(" ")
179+
// The comm field, which is inside parentheses, could contain spaces. We should not split
180+
// by those spaces as doing so could cause the numbers after it to be shifted.
181+
val commStartIndex = procInfo.indexOf('(')
182+
val commEndIndex = procInfo.lastIndexOf(')') + 1
183+
val pidArray = Array(procInfo.substring(0, commStartIndex).trim)
184+
val commArray = Array(procInfo.substring(commStartIndex, commEndIndex))
185+
val splitAfterComm = procInfo.substring(commEndIndex).trim.split(" ")
186+
val procInfoSplit = pidArray ++ commArray ++ splitAfterComm
180187
val vmem = procInfoSplit(22).toLong
181188
val rssMem = procInfoSplit(23).toLong * pageSize
182189
if (procInfoSplit(1).toLowerCase(Locale.US).contains("java")) {
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
487713 ((Executor) task l)) D 474416 474398 474398 0 -1 4194368 5 0 0 0 0 0 0 0 25 5 1 0 1542745216 7469137920 120815 18446744073709551615 104424108929024 104424108932808 140734257079632 0 0 0 4 3 553671884 1 0 0 17 58 0 0 0 0 0 104424108940536 104424108941336 104424532111360 140734257083781 140734257085131 140734257085131 140734257102797 0

core/src/test/scala/org/apache/spark/executor/ProcfsMetricsGetterSuite.scala

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,4 +62,16 @@ class ProcfsMetricsGetterSuite extends SparkFunSuite {
6262
assert(r.pythonVmemTotal == 0)
6363
assert(r.pythonRSSTotal == 0)
6464
}
65+
66+
test("SPARK-52776: Whitespace and parentheses in the comm field") {
67+
val p = new ProcfsMetricsGetter(getTestResourcePath("ProcfsMetrics"))
68+
var r = ProcfsMetrics(0, 0, 0, 0, 0, 0)
69+
r = p.addProcfsMetricsFromOneProcess(r, 487713)
70+
assert(r.jvmVmemTotal == 0)
71+
assert(r.jvmRSSTotal == 0)
72+
assert(r.pythonVmemTotal == 0)
73+
assert(r.pythonRSSTotal == 0)
74+
assert(r.otherVmemTotal == 7469137920L)
75+
assert(r.otherRSSTotal == 494858240)
76+
}
6577
}

0 commit comments

Comments
 (0)