- Feature Articles
- CodeSOD
- Error'd
-
Forums
-
Other Articles
- Random Article
- Other Series
- Alex's Soapbox
- Announcements
- Best of…
- Best of Email
- Best of the Sidebar
- Bring Your Own Code
- Coded Smorgasbord
- Mandatory Fun Day
- Off Topic
- Representative Line
- News Roundup
- Editor's Soapbox
- Software on the Rocks
- Souvenir Potpourri
- Sponsor Post
- Tales from the Interview
- The Daily WTF: Live
- Virtudyne
Admin
Dateline : 2025/11/26.
There are no comments on this article yet (there will be in a moment), which might be because the actual dateline on the article is 2025/12/02, and yet the Random Article button let me see it anyway...
Admin
did you submit it to last week Error'd?
Admin
Unfortunately, I didn't think of doing that at the time, then I forgot about it in the meantime, until I saw it come up today.
Admin
Ooohhh, that would have been WAY too much fun!
I need to get out more....
Admin
I'm going to go out on a limb and assume ExtractFileName isn't a pure function either, which would make debugging all the more painful.
Admin
It seems a fairly minor WTF but the whole
is itself a WTF since there is a race condition in that, if it exists, something else might have deleted it before you get to do what you want to do with it. You might as well just go ahead and do the operation without testing for existence and handle the errors if they arise.
Admin
ExtractFileName is a pure function. It returns the argument without the drive and directory.
Admin
Yeah, what I tend to call a "toctou" == "Time of Check, Time of Use" (name derived from the reports from the static analyser we use at $JOB).
Admin
Back in Ye Olden Dayes of computers running one app at a time and no multi-threading, TOCTOU (an industry standard term) wasn't nearly the code smell it is today. Given that we're talking about Delphi, decent bet this is a nearly single-threaded application where the only thing that could disturb that file between check and use is a hard drive failure. Or maybe somebody opening the floppy drive door at just the right moment. ;)
Also back in Ye Olden Dayes the way you checked for errors in most languages was itself pretty laborious, code intensive, and bug-prone. From a code cleanliness perspective they're probably better off the way they are.
Addendum 2025-12-02 10:28: Would I recommend writing TOCTOU bugs in a modern multi-threaded multi-user app written in a modern exception-driven language?
Of course not.
Admin
Hello from the future!
Admin
And yet people still do it. TOCTOU is what took down US-EAST-1 AWS a little while ago.
Admin
If by that you mean "all computers" (it's not clear), then that was a very long time ago. Various flavours of time-sharing system could (by definition) run multiple programs simultaneously, and something that's recognisably very similar to multithreading appeared on IBM mainframes in the 1960s.
If it's olde-skoole Delphi of the Windows 3.1 era, maybe (if Windows is running in "enhanced" mode), because background DOS programs multitask pre-emptively with the Windows GUI subsystem.
So, yeah, but no.
Admin
Right back to you (at 88 miles per hour) <3
Admin
@Steve the Cynic. Yep, multiprogramming and time-sharing and whatnot dated to the early 1960s. No argument there.
But very few user mode programs written for business use even into the mini or PC era used much in the way of multi-threading. Over in teh mainframe world, a whole lotta stuff was also batch oriented. Which meant effectively stovepiped, where App A worked on App A's files while App B might be running simultaneously in another partition, but only ever touched App B's files.
Whatever this Delphi app is doing it's probably running one instance on one box that updates one collection of files that no other app touches. By design, no other app is going to reach in and add or remove a file or a directory while this app is running.
Sure, there were some exceptions to that rule of thumb. I'm just suggesting that the worldview of app developers in the 1990s was much more single string than it is today. And they were largely correct for their era.
Admin
It's actually a function in the System.SysUtils library that comes standard with Delphi ever since I can remember (although it might have been in a different library when I first started working in Delphi 5 way back on the early 00s)
Admin
I've seen my share of system that neatly solved that issue by... never deleting anything, especially temporary files.
It's always been awesome when the explanation I was given is "/tmp files are all erased after a reboot". Seriously.
A heavy dose of cynical sarcasm is needed to avoid crying.
Admin
To be fair, how is the average user supposed to know what does and does not happen in case of an event that only ever occurs in theory?
Admin
Someone was just refactoring this part, they created variable FileName and right then they were inter...
Admin
I wonder if we used to work at the same company. They used Borland's Delphi, then when that died moved to Embarcadero. Keeping these applications running and building on modern OS's was a major effort.
Admin
Technically speaking, that is the same Delphi.
Borland in its (in)finite wisdom decided to focus on application lifecycle management tools, spun off the IDE/compiler side of things into Codegear. And then Codegear became part of Embarcadero.