2017-09-23 35 views
8

Tworzę prostą funkcję, która tworzy losowy plik. Aby być bezpiecznym dla wątków, tworzy plik w pętli retry i jeśli plik istnieje, próbuje ponownie.Czy .NET Standard znormalizuje wartości HR na wszystkich platformach, które obsługuje?

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; 
    } 
} 

Zgodnie z MSDN, wartość hresult pochodzi z COM, które wydają się wskazywać na to będzie działać tylko na Windows, i to specifically lists them as "Win32 codes". Ale to jest w bibliotece, która jest skierowana na .NET Standard i najlepiej powinna działać na every platform .NET Standard supports.

Zastanawiam się, czy mogę polegać na powyższym podejściu, które wykorzystuje wartość HResult do współpracy między platformami? documentation nie jest jasne w tym punkcie.

Jeśli nie, w jaki sposób ustalić, jakich wartości HR można oczekiwać na innych platformach?

UWAGA: Istnieje podobne pytanie Does .NET define common HRESULT values?, ale został poproszony przed .NET Standard (a wsparcie cross-platform dla .NET) istniał, więc nie można powoływać się na tę odpowiedź do tego celu.

Na razie nasza codebase używa tylko:

  1. 0x00000020 - ERROR_SHARING_VIOLATION
  2. 0x00000021 - ERROR_LOCK_VIOLATION
  3. 0x00000050 - ERROR_FILE_EXISTS

Jesteśmy kierowania .NET standard 1.5.

UWAGA: Choć przyjął odpowiedź spełnia co prosiłem tutaj, mam kolejne pytanie How do I make catching generic IOExceptions reliably portable across platforms?

+0

Chyba trzeba być bardziej szczegółowe na temat scenariusza lub konkretnych kodów błędów chcesz polegać na .. Istnieje wiele miejsc zostały wykazy z predefiniowanych kodów są używane (możesz wyszukać 'hresults.cs' zarówno w źródłowym kodzie źródłowym CoreCLR, jak iw niektórych przypadkach istnieją funkcje normalizacyjne [takie jak ta dla błędów plików] (https://github.com/dotnet /coreclr/blob/5c07c5aa98f8a088bf25099f1ab2d38b59ea5478/src/pal/src/file/file.cpp#L184-L194). –

+0

Dzięki Martin. Dodałem 3 błędy, które aktualnie mnie interesują. Miałem jednak nadzieję na bardziej ogólną odpowiedź. Ogólnie rzecz biorąc, jesteśmy zainteresowani tylko błędami pliku IO. – NightOwl888

+0

Możesz chcieć umieścić link do [tej dokumentacji] (https://docs.microsoft.com/en-us/dotnet/api/system.exception.hresult?view=netstandard-1.5) zamiast nazwy msdn oficjalne standardowe dokumenty 1.5 API .net. (Dość pewny, że jest to kopia i wklej MSDN, ale dobrze jest wskazać we właściwym miejscu) –

Odpowiedz

7

wartości Exception.HResult nie są standaryzowane na różnych platformach.

W przypadku błędów we/wy .NET Core zwróci kod błędu specyficzny dla platformy jako HResult. Wartość własności HResult dla pliku już istnieje w twoim przykładzie będzie 17 na Linuksie, i może być inna wartość dla innych systemów uniksowych.

Odpowiedni kod, który odwzorowuje błędy IO wyjątków na Uniksie jest tutaj: https://github.com/dotnet/corefx/blob/master/src/Common/src/Interop/Unix/Interop.IOErrors.cs

+0

Dzięki. Niestety podany link pokazuje tylko kod, ale nie plik zasobów dostarczający wartości. W tym katalogu nie ma odpowiedniego pliku dla innych platform. Czy mam od tego odrzucić, że powyższe podejście nie może być wiarygodne? Czy jest jakiś sposób na uzyskanie wszystkich wartości, których potrzebuję na wszystkich platformach? Zauważ, że potrzebuję tylko 3 błędy w moim pytaniu dla każdej platformy .NET Standard 1.5 obsługuje. – NightOwl888

+0

To podejście nie może być niezawodne przenośne. HR w tym przypadku jest tym, co powraca system operacyjny. Może się różnić pomiędzy Linux, MacOS, FreeBSD, .... Będę edytować post, aby było jasne. –

Powiązane problemy