tint/win: fix TmpFilePath asserting in some msvc crts

We were using the "x" flag for exclusive mode in the call to fopen_s,
but this seems not to be supported in all c runtimes. For instance, we
get this error when using the debug crt on the LUCI windows bots:
```
minkernel\crts\ucrt\inc\corecrt_internal_stdio.h(656) : Assertion failed: ("Invalid file open mode", 0)
```

Replaced this with MS-specific _sopen_s that accepts flags
`_O_CREAT | _O_EXCL` to create a file in exclusive mode, failing if it
already exists.

Bug: dawn:2435
Change-Id: I1ef997846c6d034dea4cae619cd85c6b6e9d9295
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/179140
Kokoro: Kokoro <noreply+kokoro@google.com>
Commit-Queue: Antonio Maiorano <amaiorano@google.com>
Reviewed-by: Austin Eng <enga@chromium.org>
diff --git a/src/tint/utils/file/tmpfile_windows.cc b/src/tint/utils/file/tmpfile_windows.cc
index 486c2ea..d4112eb 100644
--- a/src/tint/utils/file/tmpfile_windows.cc
+++ b/src/tint/utils/file/tmpfile_windows.cc
@@ -29,6 +29,8 @@
 
 #include "src/tint/utils/file/tmpfile.h"
 
+#include <fcntl.h>
+#include <io.h>
 #include <stdio.h>
 #include <cstdio>
 
@@ -42,11 +44,16 @@
     // creating it, failing if it already exists.
     while (tmpnam_s(name, L_tmpnam - 1) == 0) {
         std::string name_with_ext = std::string(name) + ext;
-        FILE* f = nullptr;
-        // The "x" arg forces the function to fail if the file already exists.
-        fopen_s(&f, name_with_ext.c_str(), "wbx");
-        if (f) {
-            fclose(f);
+
+        // Use MS-specific _sopen_s as it allows us to create the file in exclusive mode (_O_EXCL)
+        // so that it returns an error if the file already exists.
+        int fh = 0;
+        errno_t e = _sopen_s(&fh, name_with_ext.c_str(),                    //
+                             /* _OpenFlag */ _O_RDWR | _O_CREAT | _O_EXCL,  //
+                             /* _ShareFlag */ _SH_DENYNO,
+                             /* _PermissionMode */ _S_IREAD | _S_IWRITE);
+        if (e == 0) {
+            _close(fh);
             return name_with_ext;
         }
     }