From: Pedro Alves <pedro@palves.net>
To: gdb-patches@sourceware.org
Subject: [PATCH] Windows: Fix set_unbuffered_mode.o file rename race
Date: Thu, 9 Jul 2026 16:56:57 +0100 [thread overview]
Message-ID: <20260709155657.412594-1-pedro@palves.net> (raw)
The atomic file rename for set_unbuffered_mode.o can fail in this scenario:
| process A | process B |
|---------------------------------+---------------------------|
| compiles temp .o | compiles temp .o |
| moves .o | |
| links with .o file (locks file) | moves .o (fails w/ EBUSY) |
Here's what it looks like:
builtin_spawn -ignore SIGHUP /mingw64/bin/clang -fdiagnostics-color=never -Wno-unknown-warning-option -w -c -o /c/msys2/home/alves/gdb/build-testsuite/temp/53930/set_unbuffered_mode-c.o /c/rocgdb/src/gdb/testsuite/lib/set_unbuffered_mode.c
pid is 54259 -54259
pid is -1
output is status 0
ERROR: tcl error sourcing /c/rocgdb/src/gdb/testsuite/gdb.base/step-over-no-symbols.exp.
ERROR: tcl error code POSIX EBUSY {file busy}
ERROR: error renaming "/c/msys2/home/alves/gdb/build-testsuite/temp/53930/set_unbuffered_mode.o" to "/c/msys2/home/alves/gdb/build-testsuite/set_unbuffered_mode.o": file busy
while executing
"file rename -force -- $unbuf_obj $gdb_saved_set_unbuffered_mode_obj"
(procedure "gdb_compile" line 559)
invoked from within
"gdb_compile $source $dest $type $options"
(procedure "gdb_compile" line 42)
invoked from within
"$func $objects "${binfile}" executable $options"
(procedure "build_executable_from_specs" line 50)
invoked from within
"build_executable_from_specs {*}$arglist"
(procedure "build_executable" line 11)
invoked from within
"build_executable "failed to build" ${testfile} $srcfile"
(file "/c/rocgdb/src/gdb/testsuite/gdb.base/step-over-no-symbols.exp" line 21)
invoked from within
"source /c/rocgdb/src/gdb/testsuite/gdb.base/step-over-no-symbols.exp"
("uplevel" body line 1)
invoked from within
"uplevel #0 source /c/rocgdb/src/gdb/testsuite/gdb.base/step-over-no-symbols.exp"
invoked from within
"catch "uplevel #0 source $test_file_name" msg"
UNRESOLVED: gdb.base/step-over-no-symbols.exp: testcase '/c/rocgdb/src/gdb/testsuite/gdb.base/step-over-no-symbols.exp' aborted due to Tcl error
If we get EBUSY, it's because another parallel worker already managed
to build and move its set_unbuffered_mode.o copy to the final
destination. So fix it by simply ignoring EBUSY. Put the rename in
its own procedure, as I expect this will be used in more places.
(Note: the set_unbuffered_mode.o path is Windows-specific.)
Change-Id: I6a32d17364a19337d7f55e4376de736e1cca799d
---
gdb/testsuite/lib/gdb.exp | 21 ++++++++++++++++++++-
1 file changed, 20 insertions(+), 1 deletion(-)
diff --git a/gdb/testsuite/lib/gdb.exp b/gdb/testsuite/lib/gdb.exp
index a40c87c6727..db5a0dd7afc 100644
--- a/gdb/testsuite/lib/gdb.exp
+++ b/gdb/testsuite/lib/gdb.exp
@@ -6402,6 +6402,25 @@ proc quote_for_host { args } {
return $str
}
+# Rename SRC to DST, ignoring EBUSY. This is used when multiple
+# parallel workers all want to rename their copy of SRC to DST, as an
+# atomic commit, and it doesn't matter which one wins, as all the
+# copies are identical.
+proc file_rename_atomic {src dst} {
+ set rc [catch { file rename -force -- $src $dst } err opts]
+
+ if {$rc} {
+ set code [dict get $opts -errorcode]
+ if {[llength $code] >= 2 && [lindex $code 1] eq "EBUSY"} {
+ # Normal parallel race loss.
+ } else {
+ error $err $opts
+ }
+ }
+
+ return $rc
+}
+
# Compile source files specified by SOURCE into a binary of type TYPE at path
# DEST. gdb_compile is implemented using DejaGnu's target_compile, so the type
# parameter and most options are passed directly to it.
@@ -6922,7 +6941,7 @@ proc gdb_compile {source dest type options} {
# Make sure to write the .o file atomically.
# (Note GDB_PARALLEL mode does not support remote
# host testing.)
- file rename -force -- $unbuf_obj $gdb_saved_set_unbuffered_mode_obj
+ file_rename_atomic $unbuf_obj $gdb_saved_set_unbuffered_mode_obj
} else {
remote_download host $unbuf_obj $gdb_saved_set_unbuffered_mode_obj
}
base-commit: b43c744924b3f5df3677dbe97d12608e63ca5a4d
--
2.54.0
next reply other threads:[~2026-07-09 15:57 UTC|newest]
Thread overview: 5+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-07-09 15:56 Pedro Alves [this message]
2026-07-21 16:43 ` Tom Tromey
2026-07-22 15:07 ` Pedro Alves
2026-07-22 15:20 ` [PATCH] gdb/testsuite: Use file_rename_atomic in gdb_do_cache too Pedro Alves
2026-07-22 15:50 ` Tom Tromey
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260709155657.412594-1-pedro@palves.net \
--to=pedro@palves.net \
--cc=gdb-patches@sourceware.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox