14

I have a library function that returns GetLastError codes (things like these). I need to compare them with specific errors, like ERROR_INVALID_HANDLE. However I don't feel comfortable to define the constants myself. So the question is, is there a predefined enumeration for this purpose?

Todd Li
  • 3,209
  • 21
  • 19

6 Answers6

8

No, you'll have to make your own.

user541686
  • 205,094
  • 128
  • 528
  • 886
6

I published a NuGet package for this:

Install-Package BetterWin32Errors

First add a using for the library:

using BetterWin32Errors;

Then you can use it like this:

if (!SomeWin32ApiCall(...))
{
    var error = Win32Exception.GetLastWin32Error();
    if (error == Win32Error.ERROR_FILE_NOT_FOUND)
    {
        // ...do something...
    }
    else if (error == Win32Error.ERROR_PATH_NOT_FOUND)
    {
        // ...do something else...
    }
    else
    {
        throw new Win32Exception(error);
    }
}

See the site for more examples of how to use the library.

Michael Kropat
  • 14,557
  • 12
  • 70
  • 91
  • Wow! That's such a lifesaver! I'm surprised it took 15 years for someone to put together something so straightforward for handling Win32 error codes. Thanks! – Andrew Rondeau Jan 17 '18 at 22:50
2

You can copy the code from http://msdn.microsoft.com/en-us/library/windows/desktop/ms681382.aspx added by katmassage to your own class SystemErrorCodes. It contains the codes from 0 to 499. This is a good starter. If someone already has a class containing also all the codes his code would be appreciated.

huha
  • 4,053
  • 2
  • 29
  • 47
0

The Win32Exception class can be used for this.

    /// <summary>
    /// Setting the system Date and Time
    /// </summary>
    /// <param name="dateAndTime">The date and time settings</param>
    /// <returns>Operation success</returns>
    public static bool SetSystemTimeAndDate(DateTime dateAndTime)
    {
        var newDateAndTime = new Win32SystemTimeStruct(dateAndTime);

        var ret = Win32ApiStub.SetSystemTime(ref newDateAndTime);
        if(!ret)
            ThrowExceptionForHr(Marshal.GetLastWin32Error());
        return ret;
    }

    /// <summary>
    /// This function checks an error code and throws a nice exception if the code is signifying an error.
    /// Do not confuse this with <see cref="Marshal.ThrowExceptionForHR"/> which gets error information out of the context of the current thread.
    /// </summary>
    /// <param name="nativeErrorCode">The HRESULT error code</param>
    public static void ThrowExceptionForHr(int nativeErrorCode)
    {
        if (nativeErrorCode != 0)
            throw new Win32Exception(nativeErrorCode);
    }
sommmen
  • 6,570
  • 2
  • 30
  • 51
  • Also see: https://learn.microsoft.com/en-us/windows/desktop/Debug/system-error-codes--0-499- and FormatMessage – sommmen Oct 15 '18 at 09:04
0

There is class published at pinvoke. I haven't tried to post the 12.000 lines here.

Download: WINERROR

using System;
using System.Runtime;
using System.Runtime.InteropServices;
using System.Reflection;

namespace Microsoft.Win32.Interop
{
    public class ResultWin32
    {
        public static string GetErrorName(int result)
        {
            FieldInfo[] fields = typeof(ResultWin32).GetFields();
            foreach (FieldInfo fi in fields)
                if ((int)fi.GetValue(null) == result)
                    return fi.Name;
            return String.Empty;
        }

        /// <summary>
        /// The operation completed successfully.
        /// </summary>
        public const int ERROR_SUCCESS = 0;
        /// <summary>
        /// Incorrect function.
        /// </summary>
        public const int ERROR_INVALID_FUNCTION = 1;
        /// <summary>
        /// The system cannot find the file specified.
        /// </summary>
        public const int ERROR_FILE_NOT_FOUND = 2;
        /// <summary>
        /// The system cannot find the path specified.
        /// </summary>



        // !! Don't use this cutout
        // get the whole file at: http://www.pinvoke.net/default.aspx/Constants/WINERROR.html



        public const int COMADMIN_E_SAFERINVALID = (int)(0x80110822 - 0x100000000);
        /// <summary>
        /// The specified user cannot write to the system registry
        /// </summary>
        public const int COMADMIN_E_REGISTRY_ACCESSDENIED = (int)(0x80110823 - 0x100000000);
        /// <summary>
        /// No information avialable.
        /// </summary>
        public const int COMADMIN_E_PARTITIONS_DISABLED = (int)(0x80110824 - 0x100000000);
        /// <summary>
        /// Failed to open a file.
        /// </summary>
        public const int NS_E_FILE_OPEN_FAILED = (int)(0xC00D001DL - 0x100000000);

        public static bool Succeeded(int result)
        {
            return result >= 0;
        }

        public static bool Failed(int result)
        {
            return result < 0;
        }
    }
}
marsh-wiggle
  • 2,508
  • 3
  • 35
  • 52
-1

My answer originally aims the errors described here, but seems like yours are a subset of those.

All the answers here talk about having to do the work manually. I just did that (scraped the aforementioned link and generated an enum class with those values).

But - to my despair - I figured out that you can simply do throw new Win32Exception(errorCode) and you get the matching error message text.

Read about Win32Exception here.

Veverke
  • 9,208
  • 4
  • 51
  • 95