I am creating a simple function that creates a random file. To be thread safe, it creates the file in a retry loop and if the file exists it tries again.
while (true)
{
fileName = NewTempFileName(prefix, suffix, directory);
if (File.Exists(fileName))
{
continue;
}
try
{
// Create the file, and close it immediately
using (var stream = new FileStream(fileName, FileMode.CreateNew, FileAccess.Write, FileShare.Read))
{
break;
}
}
catch (IOException e)
{
// If the error was because the file exists, try again
if ((e.HResult & 0xFFFF) == 0x00000050)
{
continue;
}
// else rethrow it
throw;
}
}
According to MSDN, the HResult value is derived from COM which would seem to indicate it will only work on Windows, and it specifically lists them as "Win32 codes". But this is in a library which targets .NET Standard and ideally it should work on every platform .NET Standard supports.
What I am wondering is whether I can rely on the above approach that uses the value from HResult to be cross-platform? The documentation is not clear on this point.
If not, how do I determine what HResult values to expect on other platforms?
NOTE: There is a similar question Does .NET define common HRESULT values?, but it was asked before .NET Standard (and cross-platform support for .NET) existed, so I cannot rely on that answer for this purpose.
For now, our codebase only uses:
- 0x00000020 - ERROR_SHARING_VIOLATION
- 0x00000021 - ERROR_LOCK_VIOLATION
- 0x00000050 - ERROR_FILE_EXISTS
We are targeting .NET Standard 1.5.
NOTE: While the accepted answer does satisfy what I asked here, I have a follow-up question How do I make catching generic IOExceptions reliably portable across platforms?
See Question&Answers more detail:
os 与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…