diff --git a/PInvoke/Kernel32/PathCch.cs b/PInvoke/Kernel32/PathCch.cs
new file mode 100644
index 00000000..2ff89cb9
--- /dev/null
+++ b/PInvoke/Kernel32/PathCch.cs
@@ -0,0 +1,1470 @@
+using System;
+using System.Runtime.InteropServices;
+using System.Text;
+using Vanara.InteropServices;
+
+namespace Vanara.PInvoke
+{
+ public static partial class Kernel32
+ {
+ /// The maximum number of characters supported using the "\\?\" syntax for a file path.
+ public const uint PATHCCH_MAX_CCH = 0x8000;
+
+ /// Flags used by PathCch functions.
+ [PInvokeData("pathcch.h", MSDNShortId = "3179fe78-a969-4ee2-a50b-5f4f7d4dad71")]
+ [Flags]
+ public enum PATHCCH_OPTIONS
+ {
+ /// Do not allow for the construction of \\?\ paths (ie, long paths) longer than MAX_PATH.
+ PATHCCH_NONE = 0x0000000,
+
+ /// Allow the building of \\?\ paths longer than MAX_PATH.
+ PATHCCH_ALLOW_LONG_PATHS = 0x00000001,
+
+ ///
+ /// Forces the API to treat the caller as long path enabled, independent of the PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS. Note
+ /// This value is available starting in Windows 10, version 1703.
+ ///
+ PATHCCH_FORCE_ENABLE_LONG_NAME_PROCESS = 0x00000002,
+
+ ///
+ /// Forces the API to treat the caller as long path disabled, independent of the Note This value is available starting in Windows
+ /// 10, version 1703.
+ ///
+ PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS = 0x00000004,
+
+ ///
+ /// Disables the normalization of path segments that includes removing trailing dots and spaces. Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ PATHCCH_DO_NOT_NORMALIZE_SEGMENTS = 0x00000008,
+
+ ///
+ /// Converts the input path into the extended length DOS device path form (with the \\?\ prefix) Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ PATHCCH_ENSURE_IS_EXTENDED_LENGTH_PATH = 0x00000010,
+
+ ///
+ /// When combining or normalizing a path, ensure there is a trailing backslash. Note This value is available starting in Windows
+ /// 10, version 1703.
+ ///
+ PATHCCH_ENSURE_TRAILING_SLASH = 0x00000020,
+ }
+
+ ///
+ /// Converts a path string into a canonical form.
+ ///
+ /// This function differs from PathCchCanonicalize and PathCchCanonicalizeEx in that it returns the result on the heap. This means
+ /// that the caller does not have to declare the size of the returned string and reduces stack use.
+ ///
+ /// This function differs from PathCanonicalize in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ /// Note This function, PathCchCanonicalize, or PathCchCanonicalizeEx, should be used in place of PathCanonicalize.
+ ///
+ ///
+ /// A pointer to a buffer that contains the original string. This value cannot be NULL.
+ ///
+ ///
+ /// One or more of the following flags:
+ ///
+ ///
+ /// Value
+ /// Meaning
+ ///
+ /// -
+ /// PATHCCH_NONE 0x0000000
+ /// Do not allow for the construction of \\?\ paths (ie, long paths) longer than MAX_PATH.
+ ///
+ /// -
+ /// PATHCCH_ALLOW_LONG_PATHS 0x00000001
+ /// Allow the building of \\?\ paths longer than MAX_PATH.
+ ///
+ /// -
+ /// PATHCCH_FORCE_ENABLE_LONG_NAME_PROCESS 0x00000002
+ ///
+ /// Forces the API to treat the caller as long path enabled, independent of the PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS. Note This
+ /// value is available starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS 0x00000004
+ ///
+ /// Forces the API to treat the caller as long path disabled, independent of the Note This value is available starting in Windows 10,
+ /// version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_DO_NOT_NORMALIZE_SEGMENTS 0x00000008
+ ///
+ /// Disables the normalization of path segments that includes removing trailing dots and spaces. Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_ENSURE_IS_EXTENDED_LENGTH_PATH 0x00000010
+ ///
+ /// Converts the input path into the extended length DOS device path form (with the \\?\ prefix) Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_ENSURE_TRAILING_SLASH 0x00000020
+ ///
+ /// When combining or normalizing a path, ensure there is a trailing backslash. Note This value is available starting in Windows 10,
+ /// version 1703.
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ /// The address of a pointer to a buffer that, when this function returns successfully, receives the canonicalized path string. It is
+ /// the responsibility of the caller to free this resource, when it is no longer needed, by calling the LocalFree function. This
+ /// value cannot be NULL.
+ ///
+ ///
+ ///
+ /// If this function succeeds, it returns S_OK. Otherwise, it returns an HRESULT error code.
+ ///
+ ///
+ /// This function supports these alternate path forms:
+ ///
+ /// -
+ /// \\?\
+ ///
+ /// -
+ /// \\?\\UNC\
+ ///
+ /// -
+ /// \\?\Volume{guid}\
+ ///
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathalloccanonicalize HRESULT PathAllocCanonicalize(
+ // PCWSTR pszPathIn, ULONG dwFlags, PWSTR *ppszPathOut );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "3179fe78-a969-4ee2-a50b-5f4f7d4dad71")]
+ public static extern HRESULT PathAllocCanonicalize(string pszPathIn, PATHCCH_OPTIONS dwFlags, [MarshalAs(UnmanagedType.CustomMarshaler, MarshalTypeRef = typeof(LocalStringMarshaler))] out string ppszPathOut);
+
+ ///
+ ///
+ /// Concatenates two path fragments into a single path. This function also canonicalizes any relative path elements, replacing path
+ /// elements such as "." and "..".
+ ///
+ ///
+ /// This function differs from PathCchCombine and PathCchCombineEx in that it returns the result on the heap. This means that the
+ /// caller does not have to declare the size of the returned string and reduces stack use.
+ ///
+ /// This function differs from PathCombine in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ /// Note This function, PathCchCombine, or PathCchCombineEx, should be used in place of PathCombine.
+ ///
+ ///
+ /// A pointer to the first path string.
+ ///
+ ///
+ ///
+ /// A pointer to the second path string. If this path begins with a single backslash, it is combined with only the root of the path
+ /// pointed to by pszPathIn. If this path is fully qualified, it is copied directly to the output buffer without being combined with
+ /// the other path.
+ ///
+ ///
+ ///
+ /// One or more of the following flags:
+ ///
+ ///
+ /// Value
+ /// Meaning
+ ///
+ /// -
+ /// PATHCCH_NONE 0x0000000
+ /// Do not allow for the construction of \\?\ paths (ie, long paths) longer than MAX_PATH.
+ ///
+ /// -
+ /// PATHCCH_ALLOW_LONG_PATHS 0x00000001
+ /// Allow the construction of \\?\ paths longer than MAX_PATH.
+ ///
+ /// -
+ /// PATHCCH_FORCE_ENABLE_LONG_NAME_PROCESS 0x00000002
+ ///
+ /// Forces the API to treat the caller as long path enabled, independent of the PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS. Note This
+ /// value is available starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS 0x00000004
+ ///
+ /// Forces the API to treat the caller as long path disabled, independent of the Note This value is available starting in Windows 10,
+ /// version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_DO_NOT_NORMALIZE_SEGMENTS 0x00000008
+ ///
+ /// Disables the normalization of path segments that includes removing trailing dots and spaces. Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_ENSURE_IS_EXTENDED_LENGTH_PATH 0x00000010
+ ///
+ /// Converts the input path into the extended length DOS device path form (with the \\?\ prefix) Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_ENSURE_TRAILING_SLASH 0x00000020
+ ///
+ /// When combining or normalizing a path, ensure there is a trailing backslash. Note This value is available starting in Windows 10,
+ /// version 1703.
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ /// The address of a pointer to a buffer that, when this function returns successfully, receives the combined path string. It is the
+ /// responsibility of the caller to free this resource, when it is no longer needed, by calling the LocalFree function. This value
+ /// cannot be NULL.
+ ///
+ ///
+ ///
+ /// If this function succeeds, it returns S_OK. Otherwise, it returns an HRESULT error code.
+ ///
+ ///
+ /// While either pszPathIn or pszMore can NULL, they cannot both be NULL.
+ /// This function supports these alternate path forms:
+ ///
+ /// -
+ /// \\?\
+ ///
+ /// -
+ /// \\?\\UNC\
+ ///
+ /// -
+ /// \\?\Volume{guid}\
+ ///
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathalloccombine HRESULT PathAllocCombine( PCWSTR
+ // pszPathIn, PCWSTR pszMore, ULONG dwFlags, PWSTR *ppszPathOut );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "dd619138-f867-4517-bc67-a52c598efad0")]
+ public static extern HRESULT PathAllocCombine(string pszPathIn, string pszMore, PATHCCH_OPTIONS dwFlags, [MarshalAs(UnmanagedType.CustomMarshaler, MarshalTypeRef = typeof(LocalStringMarshaler))] out string ppszPathOut);
+
+ ///
+ ///
+ /// Adds a backslash to the end of a string to create the correct syntax for a path. If the source path already has a trailing
+ /// backslash, no backslash will be added.
+ ///
+ /// This function differs from PathCchAddBackslash in that you are restricted to a final path of length MAX_PATH.
+ /// This function differs from PathAddBackslash in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ /// Note This function, or PathCchAddBackslashEx, should be used in place of PathAddBackslash to prevent the possibility of a
+ /// buffer overrun.
+ ///
+ ///
+ ///
+ ///
+ /// A pointer to the path string. When this function returns successfully, the buffer contains the string with the appended
+ /// backslash. This value should not be NULL.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ ///
+ /// This function returns S_OK if the function was successful, S_FALSE if the path string already ends in a backslash, or an error
+ /// code otherwise.
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchaddbackslash HRESULT PathCchAddBackslash( PWSTR
+ // pszPath, SizeT cchPath );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "b50677cd-8815-4d84-b70a-c83863378c56")]
+ public static extern HRESULT PathCchAddBackslash(StringBuilder pszPath, SizeT cchPath);
+
+ ///
+ ///
+ /// Adds a backslash to the end of a string to create the correct syntax for a path. If the source path already has a trailing
+ /// backslash, no backslash will be added.
+ ///
+ ///
+ /// This function differs from PathCchAddBackslash in that it can return a pointer to the new end of the string and report the number
+ /// of unused characters remaining in the buffer.
+ ///
+ /// This function differs from PathAddBackslash in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ /// Note This function, or PathCchAddBackslashEx, should be used in place of PathAddBackslash to prevent the
+ /// possibility of a buffer overrun.
+ ///
+ ///
+ ///
+ ///
+ /// A pointer to the path string. When this function returns successfully, the buffer contains the string with the appended
+ /// backslash. This value should not be NULL.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ ///
+ /// A value that, when this function returns successfully, receives the address of a pointer to the terminating null character at the
+ /// end of the string.
+ ///
+ ///
+ ///
+ ///
+ /// A pointer to a value that, when this function returns successfully, is set to the number of unused characters in the destination
+ /// buffer, including the terminating null character.
+ ///
+ ///
+ ///
+ ///
+ /// This function returns S_OK if the function was successful, S_FALSE if the path string already ends in a backslash, or an error
+ /// code otherwise.
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchaddbackslashex HRESULT PathCchAddBackslashEx( PWSTR
+ // pszPath, SizeT cchPath, PWSTR *ppszEnd, SizeT *pcchRemaining );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "89adf45f-f16d-49d1-9e76-b57b73b4d4c3")]
+ public static extern HRESULT PathCchAddBackslashEx(StringBuilder pszPath, SizeT cchPath, out IntPtr ppszEnd, out SizeT pcchRemaining);
+
+ ///
+ /// Adds a file name extension to a path string.
+ /// This function differs from PathAddExtension in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ /// Note This function should be used in place of PathAddExtension to prevent the possibility of a buffer overrun.
+ ///
+ ///
+ ///
+ /// A pointer to the path string. When this function returns successfully, the buffer contains the string with the appended
+ /// extension. This value should not be NULL.
+ ///
+ ///
+ /// Note If the original string already has a file name extension present, no new extension will be added and the original
+ /// string will be unchanged.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ ///
+ /// A pointer to the file name extension string. This string can be given either with or without a preceding period (".ext" or "ext").
+ ///
+ ///
+ ///
+ /// This function returns an HRESULT code, including the following.
+ ///
+ ///
+ /// Return code
+ /// Description
+ ///
+ /// -
+ /// S_OK
+ ///
+ /// The function succeeded. Note that this also includes the case of an empty extension, such as a period with no characters
+ /// following it. In that case, the original string is returned unaltered.
+ ///
+ ///
+ /// -
+ /// E_INVALIDARG
+ ///
+ /// This value can be caused by several things, such as the pszPath param being set to NULL, the cchPath being set to 0 or a value
+ /// greater than PATHCCH_MAX_CCH, or the extension string containing illegal characters or otherwise not being a valid extension.
+ ///
+ ///
+ /// -
+ /// S_FALSE
+ /// The original string already has an extension.
+ ///
+ /// -
+ /// PATHCCH_E_FILENAME_TOO_LONG
+ /// The buffer is too small to hold the returned string.
+ ///
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchaddextension HRESULT PathCchAddExtension( PWSTR
+ // pszPath, SizeT cchPath, PCWSTR pszExt );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "c37b438b-39e7-4f24-b076-2401900dab71")]
+ public static extern HRESULT PathCchAddExtension(StringBuilder pszPath, SizeT cchPath, string pszExt);
+
+ ///
+ /// Appends one path to the end of another.
+ /// This function differs from PathCchAppendEx in that you are restricted to a final path of length MAX_PATH.
+ /// This function differs from PathAppend in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ /// Note This function, or PathCchAppendEx, should be used in place of PathAppend to prevent the possibility of a buffer overrun.
+ ///
+ ///
+ ///
+ ///
+ /// A pointer to a buffer that, on entry, contains the original path. When this function returns successfully, the buffer contains
+ /// the original path plus the appended path.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ ///
+ /// A pointer to the path to append to the end of the path pointed to by pszPath. UNC paths and paths beginning with the "\?"
+ /// sequence are accepted and recognized as fully-qualified paths. These paths replace the string pointed to by pszPath instead of
+ /// being appended to it.
+ ///
+ ///
+ ///
+ /// If this function succeeds, it returns S_OK. Otherwise, it returns an HRESULT code, including the following.
+ ///
+ ///
+ /// Return code
+ /// Description
+ ///
+ /// -
+ /// E_INVALIDARG
+ /// Either pszPath or pszMore is NULL, cchPath is 0, or cchPath is greater than PATHCCH_MAX_CCH.
+ ///
+ /// -
+ /// PATHCCH_E_FILENAME_TOO_LONG
+ /// The resulting string would exceed PATHCCH_MAX_CCH.
+ ///
+ /// -
+ /// E_OUTOFMEMORY
+ /// The function could not allocate a buffer of the neccessary size.
+ ///
+ ///
+ ///
+ ///
+ /// This function inserts a backslash between the two strings, if one is not already present.
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchappend HRESULT PathCchAppend( PWSTR pszPath, SizeT
+ // cchPath, PCWSTR pszMore );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "b64884ad-15c7-495e-8037-34daf68f8cf7")]
+ public static extern HRESULT PathCchAppend(StringBuilder pszPath, SizeT cchPath, string pszMore);
+
+ ///
+ /// Appends one path to the end of another.
+ /// This function differs from PathCchAppend in that it allows for a longer final path to be constructed.
+ /// This function differs from PathAppend in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ /// Note This function, or PathCchAppend, should be used in place of PathAppend to prevent the possibility of a buffer overrun.
+ ///
+ ///
+ ///
+ ///
+ /// A pointer to a buffer that, on entry, contains the original path. When this function returns successfully, the buffer contains
+ /// the original path plus the appended path.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ ///
+ /// A pointer the path to append to the end of the path pointed to by pszPath. UNC paths and paths that begin with the sequence \?\
+ /// are accepted and recognized as fully-qualified paths. These paths replace the string pointed to by pszPath instead of being
+ /// appended to it.
+ ///
+ ///
+ ///
+ /// One or more of the following flags:
+ ///
+ ///
+ /// Value
+ /// Meaning
+ ///
+ /// -
+ /// PATHCCH_NONE 0x0000000
+ /// Do not allow for the construction of \\?\ paths (ie, long paths) longer than MAX_PATH.
+ ///
+ /// -
+ /// PATHCCH_ALLOW_LONG_PATHS 0x00000001
+ /// Allow the building of \\?\ paths longer than MAX_PATH.
+ ///
+ /// -
+ /// PATHCCH_FORCE_ENABLE_LONG_NAME_PROCESS 0x00000002
+ ///
+ /// Forces the API to treat the caller as long path enabled, independent of the PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS. Note This
+ /// value is available starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS 0x00000004
+ ///
+ /// Forces the API to treat the caller as long path disabled, independent of the Note This value is available starting in Windows 10,
+ /// version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_DO_NOT_NORMALIZE_SEGMENTS 0x00000008
+ ///
+ /// Disables the normalization of path segments that includes removing trailing dots and spaces. Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_ENSURE_IS_EXTENDED_LENGTH_PATH 0x00000010
+ ///
+ /// Converts the input path into the extended length DOS device path form (with the \\?\ prefix) Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ ///
+ ///
+ ///
+ ///
+ /// If this function succeeds, it returns S_OK. Otherwise, it returns an HRESULT code, including the following.
+ ///
+ ///
+ /// Return code
+ /// Description
+ ///
+ /// -
+ /// E_INVALIDARG
+ /// Either pszPath or pszMore is NULL, cchPath is 0, or cchPath is greater than PATHCCH_MAX_CCH.
+ ///
+ /// -
+ /// PATHCCH_E_FILENAME_TOO_LONG
+ /// The resulting string would exceed PATHCCH_MAX_CCH.
+ ///
+ /// -
+ /// E_OUTOFMEMORY
+ /// The function could not allocate a buffer of the neccessary size.
+ ///
+ ///
+ ///
+ ///
+ /// This function inserts a backslash between the two strings, if one is not already present.
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchappendex HRESULT PathCchAppendEx( PWSTR pszPath,
+ // SizeT cchPath, PCWSTR pszMore, ULONG dwFlags );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "5421c666-1c8a-4ae8-baba-9e6f69c877df")]
+ public static extern HRESULT PathCchAppendEx(StringBuilder pszPath, SizeT cchPath, string pszMore, PATHCCH_OPTIONS dwFlags);
+
+ ///
+ /// Converts a path string into a canonical form.
+ /// This function differs from PathCchCanonicalizeEx in that you are restricted to a final path of length MAX_PATH.
+ ///
+ /// This function differs from PathAllocCanonicalize in that the caller must declare the size of the returned string, which is stored
+ /// on the stack.
+ ///
+ /// This function differs from PathCanonicalize in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ /// Note This function, PathCchCanonicalizeEx, or PathAllocCanonicalize should be used in place of PathCanonicalize to prevent
+ /// the possibility of a buffer overrun.
+ ///
+ ///
+ ///
+ /// A pointer to a buffer that, when this function returns successfully, receives the canonicalized path string.
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPathOut, in characters.
+ ///
+ ///
+ ///
+ /// A pointer to the original path string. If this value points to an empty string, or results in an empty string once the "." and
+ /// ".." elements are removed, a single backslash is copied to the buffer pointed to by pszPathOut.
+ ///
+ ///
+ ///
+ /// If this function succeeds, it returns S_OK. Otherwise, it returns an HRESULT code, including the following.
+ ///
+ ///
+ /// Return code
+ /// Description
+ ///
+ /// -
+ /// E_INVALIDARG
+ /// The cchPathOut value is greater than PATHCCH_MAX_CCH.
+ ///
+ /// -
+ /// PATHCCH_E_FILENAME_TOO_LONG
+ /// A path segment exceeds the standard path segment length limit of 256 characters.
+ ///
+ /// -
+ /// E_OUTOFMEMORY
+ /// The function could not allocate a buffer of the neccessary size.
+ ///
+ ///
+ ///
+ ///
+ ///
+ /// This function responds to the strings "." and ".." embedded in a path. The ".." string indicates to remove the immediately
+ /// preceding path segment. The "." string indicates to skip over the next path segment. Note that the root segment of the path
+ /// cannot be removed. If there are more ".." strings than there are path segments, the function returns S_OK and the buffer pointed
+ /// to by pszPathOut contains a single backslash, "".
+ ///
+ ///
+ /// All trailing periods are removed from the path, except when preceded by the "" wild card character. In that case, a single period
+ /// is retained after the '' character, but all other trailing periods are removed.
+ ///
+ /// If the resulting path is a root drive ("x:"), a backslash is appended ("x:").
+ /// The following examples show the effect of these strings.
+ ///
+ ///
+ /// Original string
+ /// Canonicalized string
+ ///
+ /// -
+ /// C:\name_1\.\name_2\..\name_3
+ /// C:\name_1\name_3
+ ///
+ /// -
+ /// C:\name_1\..\name_2\.\name_3
+ /// C:\name_2\name_3
+ ///
+ /// -
+ /// C:\name_1\name_2\.\name_3\..\name_4
+ /// C:\name_1\name_2\name_4
+ ///
+ /// -
+ /// C:\name_1\.\name_2\.\name_3\..\name_4\..
+ /// C:\name_1\name_2
+ ///
+ /// -
+ /// C:\name_1\*...
+ /// C:\name_1\*.
+ ///
+ /// -
+ /// C:\..
+ /// C:\
+ ///
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchcanonicalize HRESULT PathCchCanonicalize( PWSTR
+ // pszPathOut, SizeT cchPathOut, PCWSTR pszPathIn );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "25ff08b2-5978-4d44-9877-ba4230ef7d12")]
+ public static extern HRESULT PathCchCanonicalize(StringBuilder pszPathOut, SizeT cchPathOut, string pszPathIn);
+
+ ///
+ /// Simplifies a path by removing navigation elements such as "." and ".." to produce a direct, well-formed path.
+ /// This function differs from PathCchCanonicalize in that it allows for a longer final path to be constructed.
+ ///
+ /// This function differs from PathAllocCanonicalize in that the caller must declare the size of the returned string, which is stored
+ /// on the stack.
+ ///
+ /// This function differs from PathCanonicalize in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ /// Note This function, PathCchCanonicalize, or PathAllocCanonicalize should be used in place of PathCanonicalize to prevent
+ /// the possibility of a buffer overrun.
+ ///
+ ///
+ ///
+ /// A pointer to a buffer that, when this function returns successfully, receives the edited path string.
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPathOut, in characters.
+ ///
+ ///
+ ///
+ /// A pointer to the original path string. If this value is NULL, points to an empty string, or results in an empty string
+ /// once the "." and ".." elements are removed, a single backslash is copied to the buffer pointed to by pszPathOut.
+ ///
+ ///
+ ///
+ /// One or more of the following flags:
+ ///
+ ///
+ /// Value
+ /// Meaning
+ ///
+ /// -
+ /// PATHCCH_NONE 0x0000000
+ /// Do not allow for the construction of \\?\ paths (ie, long paths) longer than MAX_PATH.
+ ///
+ /// -
+ /// PATHCCH_ALLOW_LONG_PATHS 0x00000001
+ ///
+ /// Allow the building of \\?\ paths longer than MAX_PATH. Note that cchPathOut must be greater than MAX_PATH. If it is not, this
+ /// flag is ignored.
+ ///
+ ///
+ /// -
+ /// PATHCCH_FORCE_ENABLE_LONG_NAME_PROCESS 0x00000002
+ ///
+ /// Forces the API to treat the caller as long path enabled, independent of the PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS. Note This
+ /// value is available starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS 0x00000004
+ ///
+ /// Forces the API to treat the caller as long path disabled, independent of the Note This value is available starting in Windows 10,
+ /// version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_DO_NOT_NORMALIZE_SEGMENTS 0x00000008
+ ///
+ /// Disables the normalization of path segments that includes removing trailing dots and spaces. Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_ENSURE_IS_EXTENDED_LENGTH_PATH 0x00000010
+ ///
+ /// Converts the input path into the extended length DOS device path form (with the \\?\ prefix) Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_ENSURE_TRAILING_SLASH 0x00000020
+ ///
+ /// When combining or normalizing a path, ensure there is a trailing backslash. Note This value is available starting in Windows 10,
+ /// version 1703.
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ /// If this function succeeds, it returns S_OK. Otherwise, it returns an HRESULT code, including but not limited to the following.
+ ///
+ ///
+ ///
+ /// Return code
+ /// Description
+ ///
+ /// -
+ /// E_INVALIDARG
+ /// The cchPathOut value is greater than PATHCCH_MAX_CCH.
+ ///
+ /// -
+ /// PATHCCH_E_FILENAME_TOO_LONG
+ ///
+ /// A path segment has more than PATHCCH_MAX_CCH characters, or, if the PATHCCH_ALLOW_LONG_PATHS flag is not set, exceeds the
+ /// standard path segment length limit of 256 characters.
+ ///
+ ///
+ /// -
+ /// E_OUTOFMEMORY
+ /// The function could not allocate a buffer of the neccessary size.
+ ///
+ ///
+ ///
+ ///
+ ///
+ /// This function responds to the strings "." and ".." embedded in a path. The ".." string indicates to remove the immediately
+ /// preceding path segment. The "." string indicates to skip over the next path segment. Note that the root segment of the path
+ /// cannot be removed. If there are more ".." strings than there are path segments, the function returns S_OK and the buffer pointed
+ /// to by pszPathOut contains a single backslash, "".
+ ///
+ ///
+ /// All trailing periods are removed from the path, except when preceded by the "" wild card character. In that case, a single period
+ /// is retained after the '' character, but all other trailing periods are removed.
+ ///
+ /// If the resulting path is a root drive ("x:"), a backslash is appended ("x:").
+ /// The following examples show the effect of these strings.
+ ///
+ ///
+ /// Original string
+ /// Canonicalized string
+ ///
+ /// -
+ /// C:\name_1\.\name_2\..\name_3
+ /// C:\name_1\name_3
+ ///
+ /// -
+ /// C:\name_1\..\name_2\.\name_3
+ /// C:\name_2\name_3
+ ///
+ /// -
+ /// C:\name_1\name_2\.\name_3\..\name_4
+ /// C:\name_1\name_2\name_4
+ ///
+ /// -
+ /// C:\name_1\.\name_2\.\name_3\..\name_4\..
+ /// C:\name_1\name_2
+ ///
+ /// -
+ /// C:\name_1\*...
+ /// C:\name_1\*.
+ ///
+ /// -
+ /// C:\..
+ /// C:\
+ ///
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchcanonicalizeex HRESULT PathCchCanonicalizeEx( PWSTR
+ // pszPathOut, SizeT cchPathOut, PCWSTR pszPathIn, ULONG dwFlags );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "fd7b8ce0-3c67-48fb-8e7e-521a6b438676")]
+ public static extern HRESULT PathCchCanonicalizeEx(StringBuilder pszPathOut, SizeT cchPathOut, string pszPathIn, PATHCCH_OPTIONS dwFlags);
+
+ ///
+ ///
+ /// Combines two path fragments into a single path. This function also canonicalizes any relative path elements, removing "." and
+ /// ".." elements to simplify the final path.
+ ///
+ /// This function differs from PathCchCombineEx in that you are restricted to a final path of length MAX_PATH.
+ ///
+ /// This function differs from PathAllocCombine in that the caller must declare the size of the returned string, which is stored on
+ /// the stack.
+ ///
+ /// This function differs from PathCombine in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ /// Note This function, PathCchCombineEx, or PathAllocCombine should be used in place of PathCombine to prevent the
+ /// possibility of a buffer overrun.
+ ///
+ ///
+ ///
+ ///
+ /// A pointer to a buffer that, when this function returns successfully, receives the combined path string. This parameter can point
+ /// to the same buffer as pszPathIn or pszMore.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPathOut, in characters.
+ ///
+ ///
+ /// A pointer to the first path string. This value can be NULL.
+ ///
+ ///
+ ///
+ /// A pointer to the second path string. If this path begins with a single backslash, it is combined with only the root of the path
+ /// pointed to by pszPathIn. If this path is fully qualfied, it is copied directly to the output buffer without being combined with
+ /// the other path. This value can be NULL.
+ ///
+ ///
+ ///
+ /// This function returns an HRESULT code, including the following.
+ ///
+ ///
+ /// Return code
+ /// Description
+ ///
+ /// -
+ /// S_OK
+ ///
+ /// The function succeeded. Note that this also includes the case of an empty extension, such as a period with no characters
+ /// following it. In that case, the original string is returned unaltered.
+ ///
+ ///
+ /// -
+ /// E_INVALIDARG
+ ///
+ /// This value can be caused by several things, such as the pszPathOut param being set to NULL, or the cchPathOut value being set to
+ /// 0 or a value greater than PATHCCH_MAX_CCH.
+ ///
+ ///
+ /// -
+ /// E_OUTOFMEMORY
+ /// The function could not allocate enough memory to perform the operation.
+ ///
+ /// -
+ /// PATHCCH_E_FILENAME_TOO_LONG
+ /// The size of one or both of the original paths exceeded PATHCCH_MAX_CCH.
+ ///
+ ///
+ ///
+ ///
+ ///
+ /// If both pszPathIn and pszMore are NULL or point to empty strings, a single backslash is copied to the buffer pointed to by pszPathOut.
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchcombine HRESULT PathCchCombine( PWSTR pszPathOut,
+ // SizeT cchPathOut, PCWSTR pszPathIn, PCWSTR pszMore );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "506a4165-f572-4521-958f-56a0296f9c05")]
+ public static extern HRESULT PathCchCombine(StringBuilder pszPathOut, SizeT cchPathOut, string pszPathIn, string pszMore);
+
+ ///
+ ///
+ /// Combines two path fragments into a single path. This function also canonicalizes any relative path elements, removing "." and
+ /// ".." elements to simplify the final path.
+ ///
+ /// This function differs from PathCchCombine in that it allows for a longer final path to be constructed.
+ ///
+ /// This function differs from PathAllocCombine in that the caller must declare the size of the returned string, which is stored on
+ /// the stack.
+ ///
+ /// This function differs from PathCombine in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ /// Note This function, PathCchCombine, or PathAllocCombine should be used in place of PathCombine to prevent the possibility
+ /// of a buffer overrun.
+ ///
+ ///
+ ///
+ ///
+ /// A pointer to a buffer that, when this function returns successfully, receives the combined path string. This parameter can point
+ /// to the same buffer as pszPathIn or pszMore.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPathOut, in characters.
+ ///
+ ///
+ /// A pointer to the first path string. This value can be NULL.
+ ///
+ ///
+ ///
+ /// A pointer to the second path string. If this path begins with a single backslash, it is combined with only the root of the path
+ /// pointed to by pszPathIn. If this path is fully qualfied, it is copied directly to the output buffer without being combined with
+ /// the other path. This value can be NULL.
+ ///
+ ///
+ ///
+ /// One or more of the following flags:
+ ///
+ ///
+ /// Value
+ /// Meaning
+ ///
+ /// -
+ /// PATHCCH_NONE 0x0000000
+ /// Do not allow for the construction of \\?\ paths (ie, long paths) longer than MAX_PATH.
+ ///
+ /// -
+ /// PATHCCH_ALLOW_LONG_PATHS 0x00000001
+ ///
+ /// Allow the construction of \\?\ paths longer than MAX_PATH. Note that cchPathOut must be greater than MAX_PATH. Note that
+ /// cchPathOut must be greater than MAX_PATH. If it is not, this flag is ignored.
+ ///
+ ///
+ /// -
+ /// PATHCCH_FORCE_ENABLE_LONG_NAME_PROCESS 0x00000002
+ ///
+ /// Forces the API to treat the caller as long path enabled, independent of the PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS. Note This
+ /// value is available starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_FORCE_DISABLE_LONG_NAME_PROCESS 0x00000004
+ ///
+ /// Forces the API to treat the caller as long path disabled, independent of the Note This value is available starting in Windows 10,
+ /// version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_DO_NOT_NORMALIZE_SEGMENTS 0x00000008
+ ///
+ /// Disables the normalization of path segments that includes removing trailing dots and spaces. Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ ///
+ /// -
+ /// PATHCCH_ENSURE_IS_EXTENDED_LENGTH_PATH 0x00000010
+ ///
+ /// Converts the input path into the extended length DOS device path form (with the \\?\ prefix) Note This value is available
+ /// starting in Windows 10, version 1703.
+ ///
+ ///
+ ///
+ ///
+ ///
+ /// This function returns an HRESULT code, including the following.
+ ///
+ ///
+ /// Return code
+ /// Description
+ ///
+ /// -
+ /// S_OK
+ ///
+ /// The function succeeded. Note that this also includes the case of an empty extension, such as a period with no characters
+ /// following it. In that case, the original string is returned unaltered.
+ ///
+ ///
+ /// -
+ /// E_INVALIDARG
+ ///
+ /// This value can be caused by several things, such as the pszPathOut param being set to NULL, or the cchPathOut value being set to
+ /// 0 or a value greater than PATHCCH_MAX_CCH.
+ ///
+ ///
+ /// -
+ /// E_OUTOFMEMORY
+ /// The function could not allocate enough memory to perform the operation.
+ ///
+ /// -
+ /// PATHCCH_E_FILENAME_TOO_LONG
+ /// The size of one or both of the original paths exceeded PATHCCH_MAX_CCH.
+ ///
+ ///
+ ///
+ ///
+ ///
+ /// If both pszPathIn and pszMore are NULL or point to empty strings, a single backslash is copied to the buffer pointed to by pszPathOut.
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchcombineex HRESULT PathCchCombineEx( PWSTR
+ // pszPathOut, SizeT cchPathOut, PCWSTR pszPathIn, PCWSTR pszMore, ULONG dwFlags );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "798c2e49-04a5-4270-b584-41faf1519e4b")]
+ public static extern HRESULT PathCchCombineEx(StringBuilder pszPathOut, SizeT cchPathOut, string pszPathIn, string pszMore, PATHCCH_OPTIONS dwFlags);
+
+ ///
+ ///
+ /// Searches a path to find its file name extension, such as ".exe" or ".ini". This function does not search for a specific
+ /// extension; it searches for the presence of any extension.
+ ///
+ /// This function differs from PathFindExtension in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ /// Note This function should be used in place of PathFindExtension to prevent the possibility of a buffer overrun.
+ ///
+ ///
+ /// A pointer to the path to search.
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ ///
+ /// The address of a pointer that, when this function returns successfully, points to the "." character that precedes the extension
+ /// within pszPath. If no extension is found, it points to the string's terminating null character.
+ ///
+ ///
+ ///
+ /// If this function succeeds, it returns S_OK. Otherwise, it returns an HRESULT error code.
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchfindextension HRESULT PathCchFindExtension( PCWSTR
+ // pszPath, SizeT cchPath, PCWSTR *ppszExt );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "dac6cf02-7b53-449c-b788-4a7b6d1622ed")]
+ public static extern HRESULT PathCchFindExtension(string pszPath, SizeT cchPath, out IntPtr ppszExt);
+
+ ///
+ /// Determines whether a path string refers to the root of a volume.
+ /// This function differs from PathIsRoot in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ ///
+ /// A pointer to the path string.
+ ///
+ ///
+ /// Returns TRUE if the specified path is a root, or FALSE otherwise.
+ ///
+ ///
+ /// The following table shows the PathCchIsRoot return value for various paths.
+ ///
+ ///
+ /// Path
+ /// PathCchIsRoot
+ ///
+ /// -
+ /// "c:\"
+ /// TRUE
+ ///
+ /// -
+ /// "c:"
+ /// FALSE
+ ///
+ /// -
+ /// "c:\path1"
+ /// FALSE
+ ///
+ /// -
+ /// "\path1"
+ /// TRUE
+ ///
+ /// -
+ /// "path1"
+ /// FALSE
+ ///
+ /// -
+ /// "\\path1\path2"
+ /// TRUE
+ ///
+ /// -
+ /// "\\path1\path2\"
+ /// FALSE
+ ///
+ /// -
+ /// "\\path1\path2\path3"
+ /// FALSE
+ ///
+ /// -
+ /// "\\path1"
+ /// TRUE
+ ///
+ /// -
+ /// "\\path1\"
+ /// FALSE
+ ///
+ /// -
+ /// "\\"
+ /// TRUE
+ ///
+ /// -
+ /// "\\?\UNC\"
+ /// TRUE
+ ///
+ /// -
+ /// "\\?\UNC\path1\path2"
+ /// TRUE
+ ///
+ /// -
+ /// "\\?\UNC\path1\path2\"
+ /// FALSE
+ ///
+ /// -
+ /// "\\?\UNC\path1\path2\path3"
+ /// FALSE
+ ///
+ /// -
+ /// "\\?\UNC\path1"
+ /// TRUE
+ ///
+ /// -
+ /// "\\?\UNC\path1\"
+ /// FALSE
+ ///
+ /// -
+ /// "\\?\c:\"
+ /// TRUE
+ ///
+ /// -
+ /// "\\?\c:"
+ /// FALSE
+ ///
+ /// -
+ /// "\\?\c:\path1"
+ /// FALSE
+ ///
+ /// -
+ /// "\\?\Volume{guid}\"
+ /// TRUE
+ ///
+ /// -
+ /// "\\?\Volume{guid}"
+ /// FALSE
+ ///
+ /// -
+ /// "\\?\Volume{guid}\path1"
+ /// FALSE
+ ///
+ /// -
+ /// NULL
+ /// FALSE
+ ///
+ /// -
+ /// ""
+ /// FALSE
+ ///
+ ///
+ ///
+ /// This function returns TRUE for paths such as "", "X:" or "\server<i>share". Paths such as "..\path2" or "\server"
+ /// return FALSE.
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchisroot BOOL PathCchIsRoot( PCWSTR pszPath );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "b9770030-b298-47f8-98a7-3ce9b4d44dd1")]
+ [return: MarshalAs(UnmanagedType.Bool)]
+ public static extern bool PathCchIsRoot(string pszPath);
+
+ ///
+ /// Removes the trailing backslash from the end of a path string.
+ /// This function differs from PathRemoveBackslash in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ /// Note This function, or PathCchRemoveBackslashEx, should be used in place of PathRemoveBackslash to prevent the possibility
+ /// of a buffer overrun.
+ ///
+ ///
+ ///
+ ///
+ /// A pointer to the path string. When this function returns successfully, the string contains the path with any trailing backslash
+ /// removed. If no trailing backslash was found, the string is unchanged.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ ///
+ /// This function returns S_OK if the function was successful, S_FALSE if the string was a root path or if no backslash was found, or
+ /// an error code otherwise.
+ ///
+ ///
+ ///
+ /// This function will not remove the backslash from a root path string, such as "C:".
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchremovebackslash HRESULT PathCchRemoveBackslash(
+ // PWSTR pszPath, SizeT cchPath );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "61afc20e-ee6c-46ad-a058-64c57de41ba4")]
+ public static extern HRESULT PathCchRemoveBackslash(StringBuilder pszPath, SizeT cchPath);
+
+ ///
+ /// Removes the trailing backslash from the end of a path string.
+ ///
+ /// This function differs from PathCchRemoveBackslash in that it can return a pointer to the new end of the string and report the
+ /// number of unused characters remaining in the buffer.
+ ///
+ /// This function differs from PathRemoveBackslash in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ /// Note This function, or PathCchRemoveBackslash, should be used in place of PathRemoveBackslash to prevent the possibility
+ /// of a buffer overrun.
+ ///
+ ///
+ ///
+ ///
+ /// A pointer to the path string. When this function returns successfully, the string contains the path with any trailing backslash
+ /// removed. If no trailing backslash was found, the string is unchanged.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ ///
+ /// A value that, when this function returns successfully, receives the address of a pointer to end of the new string. If the string
+ /// is a root path such as "C:", the pointer points to the backslash; otherwise the pointer points to the string's terminating null character.
+ ///
+ ///
+ ///
+ ///
+ /// A pointer to a value that, when this function returns successfully, receives the number of unused characters in the destination
+ /// buffer, including the terminating null character. If the string is a root path such as "C:", this count includes the backslash in
+ /// that string.
+ ///
+ ///
+ ///
+ ///
+ /// This function returns S_OK if the function was successful, S_FALSE if the string was a root path or if no backslash was found, or
+ /// an error code otherwise.
+ ///
+ ///
+ ///
+ /// This function will not remove the backslash from a root path string, such as "C:".
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchremovebackslashex HRESULT PathCchRemoveBackslashEx(
+ // PWSTR pszPath, SizeT cchPath, PWSTR *ppszEnd, SizeT *pcchRemaining );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "250c2faa-94bb-42c1-97d4-37f8f59dbde6")]
+ public static extern HRESULT PathCchRemoveBackslashEx(StringBuilder pszPath, SizeT cchPath, out IntPtr ppszEnd, out SizeT pcchRemaining);
+
+ ///
+ /// Removes the file name extension from a path, if one is present.
+ /// This function differs from PathRemoveExtension in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ /// Note This function, should be used in place of PathRemoveExtension to prevent the possibility of a buffer overrun.
+ ///
+ ///
+ ///
+ /// A pointer to the path string. When this function returns successfully, the string contains the path with any extension removed.
+ /// If no extension was found, the string is unchanged.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ /// This function returns S_OK if the function was successful, S_FALSE if no extension was found, or an error code otherwise.
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchremoveextension HRESULT PathCchRemoveExtension(
+ // PWSTR pszPath, SizeT cchPath );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "9adfb054-6d62-41bb-9036-0bf670ea24b2")]
+ public static extern HRESULT PathCchRemoveExtension(StringBuilder pszPath, SizeT cchPath);
+
+ ///
+ ///
+ /// Removes the last element in a path string, whether that element is a file name or a directory name. The element's leading
+ /// backslash is also removed.
+ ///
+ /// This function differs from PathRemoveFileSpec in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ /// Note This function should be used in place of PathRemoveFileSpec to prevent the possibility of a buffer overrun.
+ ///
+ ///
+ ///
+ /// A pointer to the fully-qualified path string. When this function returns successfully, the string will have had its last element
+ /// and its leading backslash removed. This function does not affect root paths such as "C:". In the case of a root path, the path
+ /// string is returned unaltered. If a path string ends with a trailing backslash, only that backslash is removed.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ /// This function returns S_OK if the function was successful, S_FALSE if there was nothing to remove, or an error code otherwise.
+ ///
+ ///
+ /// The following table shows the effect of this function on a selection of path strings.
+ ///
+ ///
+ /// Original String
+ /// Returned String
+ ///
+ /// -
+ /// "C:\path1"
+ /// "C:\"
+ ///
+ /// -
+ /// "C:\path1\path2"
+ /// "C:\path1"
+ ///
+ /// -
+ /// "C:\path1\"
+ /// "C:\path1"
+ ///
+ /// -
+ /// "\\path1\path2\path3"
+ /// "\\path1\path2"
+ ///
+ /// -
+ /// "\path1"
+ /// "\"
+ ///
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchremovefilespec HRESULT PathCchRemoveFileSpec( PWSTR
+ // pszPath, SizeT cchPath );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "c37aeddc-ed24-4828-b92b-bce0e6384726")]
+ public static extern HRESULT PathCchRemoveFileSpec(StringBuilder pszPath, SizeT cchPath);
+
+ ///
+ ///
+ /// Replaces a file name's extension at the end of a path string with a new extension. If the path string does not end with an
+ /// extension, the new extension is added.
+ ///
+ /// This function differs from PathRenameExtension in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ /// Note This function should be used in place of PathRenameExtension to prevent the possibility of a buffer overrun.
+ ///
+ ///
+ ///
+ /// A pointer to the path string. When this function returns successfully, this value points to the same string, but with the renamed
+ /// or added extension.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ ///
+ /// A pointer to the new extension string. The leading '.' character is optional. In the case of an empty string (""), any existing
+ /// extension in the path string is removed.
+ ///
+ ///
+ ///
+ /// If this function succeeds, it returns S_OK. Otherwise, it returns an HRESULT error code.
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchrenameextension HRESULT PathCchRenameExtension(
+ // PWSTR pszPath, SizeT cchPath, PCWSTR pszExt );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "79cd9499-03b7-4482-abd3-a42edd1b2b67")]
+ public static extern HRESULT PathCchRenameExtension(StringBuilder pszPath, SizeT cchPath, string pszExt);
+
+ ///
+ ///
+ /// Retrieves a pointer to the first character in a path following the drive letter or Universal Naming Convention (UNC) server/share
+ /// path elements.
+ ///
+ /// This function differs from PathSkipRoot in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ ///
+ ///
+ /// A pointer to the path string.
+ ///
+ ///
+ ///
+ /// The address of a pointer that, when this function returns successfully, points to the first character in a path following the
+ /// drive letter or UNC server/share path elements. If the path consists of only a root, this value will point to the string's
+ /// terminating null character.
+ ///
+ ///
+ ///
+ /// If this function succeeds, it returns S_OK. Otherwise, it returns an HRESULT error code.
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchskiproot HRESULT PathCchSkipRoot( PCWSTR pszPath,
+ // PCWSTR *ppszRootEnd );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "187bc49e-c5ae-42b8-acbd-a765f871d73b")]
+ public static extern HRESULT PathCchSkipRoot(string pszPath, out IntPtr ppszRootEnd);
+
+ ///
+ /// Removes the "\?" prefix, if present, from a file path.
+ ///
+ ///
+ ///
+ /// A pointer to the path string. When this function returns successfully, the same path string will have had the prefix removed, if
+ /// the prefix was present. If no prefix was present, the string will be unchanged.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ ///
+ /// This function returns S_OK if the prefix was removed, S_FALSE if the path did not have a prefix to remove, or an HRESULT failure code.
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchstripprefix HRESULT PathCchStripPrefix( PWSTR
+ // pszPath, SizeT cchPath );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "2e50b23e-2725-4200-bd5e-845ff3458026")]
+ public static extern HRESULT PathCchStripPrefix(StringBuilder pszPath, SizeT cchPath);
+
+ ///
+ /// Removes all file and directory elements in a path except for the root information.
+ /// This function differs from PathStripToRoot in that it accepts paths with "\", "\?" and "\?\UNC" prefixes.
+ /// Note This function should be used in place of PathStripToRoot to prevent the possibility of a buffer overrun.
+ ///
+ ///
+ ///
+ /// A pointer to the path string. When this function returns successfully, this string contains only the root information taken from
+ /// that path.
+ ///
+ ///
+ ///
+ /// The size of the buffer pointed to by pszPath, in characters.
+ ///
+ ///
+ ///
+ /// This function returns S_OK if the path was truncated, S_FALSE if the path was already just a root, or an HRESULT failure code.
+ ///
+ ///
+ ///
+ /// Some examples of the effect of this function:
+ ///
+ ///
+ /// Initial string
+ /// Final string
+ ///
+ /// -
+ /// "C:\path1\path2\file"
+ /// "C:\"
+ ///
+ /// -
+ /// "\\path1\path2\path3"
+ /// "\\path1\path2"
+ ///
+ /// -
+ /// "\path1"
+ /// "\"
+ ///
+ ///
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathcchstriptoroot HRESULT PathCchStripToRoot( PWSTR
+ // pszPath, SizeT cchPath );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "e0539478-8c64-4445-ab99-22f1df70afe8")]
+ public static extern HRESULT PathCchStripToRoot(StringBuilder pszPath, SizeT cchPath);
+
+ ///
+ /// Determines if a path string is a valid Universal Naming Convention (UNC) path, as opposed to a path based on a drive letter.
+ /// This function differs from PathIsUNC in that it also allows you to extract the name of the server from the path.
+ ///
+ ///
+ /// A pointer to the path string.
+ ///
+ ///
+ ///
+ /// A pointer to a string that, when this function returns successfully, receives the server portion of the UNC path. This value can
+ /// be NULL if you don't need this information.
+ ///
+ ///
+ ///
+ /// Returns TRUE if the string is a valid UNC path; otherwise, FALSE.
+ ///
+ // https://docs.microsoft.com/en-us/windows/desktop/api/pathcch/nf-pathcch-pathisuncex BOOL PathIsUNCEx( PCWSTR pszPath, PCWSTR
+ // *ppszServer );
+ [DllImport(Lib.KernelBase, SetLastError = false, ExactSpelling = true, CharSet = CharSet.Unicode)]
+ [PInvokeData("pathcch.h", MSDNShortId = "3b2a4158-63ec-49eb-a031-7493d02f2caa")]
+ [return: MarshalAs(UnmanagedType.Bool)]
+ public static extern bool PathIsUNCEx(string pszPath, ref StringBuilder ppszServer);
+ }
+}
\ No newline at end of file