Finished unit testing and fixes for winbase.h process, thread and numa functions

pull/83/head
David Hall 2019-07-25 18:36:28 -06:00
parent 99cf640a97
commit 0caca64a6d
4 changed files with 286 additions and 91 deletions

View File

@ -1225,7 +1225,7 @@ namespace Vanara.PInvoke
// flProtect, _In_ DWORD dwMaximumSizeHigh, _In_ DWORD dwMaximumSizeLow, _In_opt_ LPCTSTR lpName, _In_ DWORD nndPreferred);
[DllImport(Lib.Kernel32, SetLastError = true, CharSet = CharSet.Auto)]
[PInvokeData("WinBase.h", MSDNShortId = "aa366539")]
public static extern SafeHFILE CreateFileMappingNuma([In] HFILE hFile, [In] SECURITY_ATTRIBUTES lpFileMappingAttributes, MEM_PROTECTION flProtect,
public static extern SafeHFILE CreateFileMappingNuma([In] HFILE hFile, [In, Optional] SECURITY_ATTRIBUTES lpFileMappingAttributes, MEM_PROTECTION flProtect,
uint dwMaximumSizeHigh, uint dwMaximumSizeLow, string lpName, uint nndPreferred);
/// <summary>

View File

@ -7,7 +7,8 @@ namespace Vanara.PInvoke
{
/// <summary>
/// An application-defined function used with the <c>CreateFiber</c> function. It serves as the starting address for a fiber. The
/// <c>LPFIBER_START_ROUTINE</c> type defines a pointer to this callback function. <c>FiberProc</c> is a placeholder for the application-defined function name.
/// <c>LPFIBER_START_ROUTINE</c> type defines a pointer to this callback function. <c>FiberProc</c> is a placeholder for the
/// application-defined function name.
/// </summary>
/// <param name="lpParameter">The fiber data passed using the lpParameter parameter of the <c>CreateFiber</c> function.</param>
/// <returns>This function does not return a value.</returns>
@ -22,23 +23,27 @@ namespace Vanara.PInvoke
/// <summary>
/// Enables away mode. This value must be specified with ES_CONTINUOUS.
/// <para>
/// Away mode should be used only by media-recording and media-distribution applications that must perform critical background processing on desktop
/// computers while the computer appears to be sleeping. See Remarks.
/// Away mode should be used only by media-recording and media-distribution applications that must perform critical background
/// processing on desktop computers while the computer appears to be sleeping. See Remarks.
/// </para>
/// </summary>
ES_AWAYMODE_REQUIRED = 0x00000040,
/// <summary>
/// Informs the system that the state being set should remain in effect until the next call that uses ES_CONTINUOUS and one of the other state flags
/// is cleared.
/// Informs the system that the state being set should remain in effect until the next call that uses ES_CONTINUOUS and one of
/// the other state flags is cleared.
/// </summary>
ES_CONTINUOUS = 0x80000000,
/// <summary>Forces the display to be on by resetting the display idle timer.</summary>
ES_DISPLAY_REQUIRED = 0x00000002,
/// <summary>Forces the system to be in the working state by resetting the system idle timer.</summary>
ES_SYSTEM_REQUIRED = 0x00000001,
/// <summary>
/// This value is not supported. If ES_USER_PRESENT is combined with other esFlags values, the call will fail and none of the specified states will
/// be set.
/// This value is not supported. If ES_USER_PRESENT is combined with other esFlags values, the call will fail and none of the
/// specified states will be set.
/// </summary>
ES_USER_PRESENT = 0x00000004,
}
@ -78,7 +83,7 @@ namespace Vanara.PInvoke
// LPVOID WINAPI ConvertThreadToFiber( _In_opt_ LPVOID lpParameter); https://msdn.microsoft.com/en-us/library/windows/desktop/ms682115(v=vs.85).aspx
[DllImport(Lib.Kernel32, SetLastError = true, ExactSpelling = true)]
[PInvokeData("WinBase.h", MSDNShortId = "ms682115")]
public static extern IntPtr ConvertThreadToFiber([In] IntPtr lpParameter);
public static extern IntPtr ConvertThreadToFiber([In, Optional] IntPtr lpParameter);
/// <summary>
/// <para>Converts the current thread into a fiber. You must convert a thread into a fiber before you can schedule other fibers.</para>
@ -111,54 +116,56 @@ namespace Vanara.PInvoke
// LPVOID lpParameter, DWORD dwFlags );
[DllImport(Lib.Kernel32, SetLastError = true, ExactSpelling = true)]
[PInvokeData("winbase.h", MSDNShortId = "cb0473f8-bc49-44c9-a8b7-6d5b55aa37a5")]
public static extern IntPtr ConvertThreadToFiberEx(IntPtr lpParameter, FIBER_FLAG dwFlags);
public static extern IntPtr ConvertThreadToFiberEx([In, Optional] IntPtr lpParameter, FIBER_FLAG dwFlags);
/// <summary>
/// Allocates a fiber object, assigns it a stack, and sets up execution to begin at the specified start address, typically the fiber function. This
/// function does not schedule the fiber.
/// Allocates a fiber object, assigns it a stack, and sets up execution to begin at the specified start address, typically the fiber
/// function. This function does not schedule the fiber.
/// </summary>
/// <param name="dwStackSize">
/// The initial size of the stack, in bytes. If this parameter is zero, the new fiber uses the default stack size for the executable. For more
/// information, see Thread Stack Size.
/// The initial size of the stack, in bytes. If this parameter is zero, the new fiber uses the default stack size for the executable.
/// For more information, see Thread Stack Size.
/// </param>
/// <param name="lpStartAddress">
/// A pointer to the application-defined function to be executed by the fiber and represents the starting address of the fiber. Execution of the newly
/// created fiber does not begin until another fiber calls the SwitchToFiber function with this address. For more information of the fiber callback
/// function, see FiberProc.
/// A pointer to the application-defined function to be executed by the fiber and represents the starting address of the fiber.
/// Execution of the newly created fiber does not begin until another fiber calls the SwitchToFiber function with this address. For
/// more information of the fiber callback function, see FiberProc.
/// </param>
/// <param name="lpParameter">
/// A pointer to a variable that is passed to the fiber. The fiber can retrieve this data by using the GetFiberData macro.
/// </param>
/// <param name="lpParameter">A pointer to a variable that is passed to the fiber. The fiber can retrieve this data by using the GetFiberData macro.</param>
/// <returns>
/// If the function succeeds, the return value is the address of the fiber. If the function fails, the return value is NULL.To get extended error
/// information, call GetLastError.
/// If the function succeeds, the return value is the address of the fiber. If the function fails, the return value is NULL.To get
/// extended error information, call GetLastError.
/// </returns>
// VOID CALLBACK FiberProc( _In_ PVOID lpParameter); https://msdn.microsoft.com/en-us/library/windows/desktop/ms682402(v=vs.85).aspx
[DllImport(Lib.Kernel32, SetLastError = true, ExactSpelling = true)]
[PInvokeData("WinBase.h", MSDNShortId = "ms682402")]
public static extern IntPtr CreateFiber(SizeT dwStackSize, FiberProc lpStartAddress, [In] IntPtr lpParameter);
public static extern IntPtr CreateFiber([Optional] SizeT dwStackSize, FiberProc lpStartAddress, [In, Optional] IntPtr lpParameter);
/// <summary>
/// Allocates a fiber object, assigns it a stack, and sets up execution to begin at the specified start address, typically the fiber function. This
/// function does not schedule the fiber.
/// Allocates a fiber object, assigns it a stack, and sets up execution to begin at the specified start address, typically the fiber
/// function. This function does not schedule the fiber.
/// </summary>
/// <param name="dwStackCommitSize">
/// The initial commit size of the stack, in bytes. If this parameter is zero, the new fiber uses the default commit stack size for the executable. For
/// more information, see <c>Thread Stack Size</c>.
/// The initial commit size of the stack, in bytes. If this parameter is zero, the new fiber uses the default commit stack size for
/// the executable. For more information, see <c>Thread Stack Size</c>.
/// </param>
/// <param name="dwStackReserveSize">
/// The initial reserve size of the stack, in bytes. If this parameter is zero, the new fiber uses the default reserved stack size for the executable.
/// For more information, see <c>Thread Stack Size</c>.
/// The initial reserve size of the stack, in bytes. If this parameter is zero, the new fiber uses the default reserved stack size
/// for the executable. For more information, see <c>Thread Stack Size</c>.
/// </param>
/// <param name="dwFlags">
/// <para>
/// If this parameter is zero, the floating-point state on x86 systems is not switched and data can be corrupted if a fiber uses floating-point
/// arithmetic. If this parameter is <c>FIBER_FLAG_FLOAT_SWITCH</c>, the floating-point state is switched for the fiber.
/// If this parameter is zero, the floating-point state on x86 systems is not switched and data can be corrupted if a fiber uses
/// floating-point arithmetic. If this parameter is <c>FIBER_FLAG_FLOAT_SWITCH</c>, the floating-point state is switched for the fiber.
/// </para>
/// <para><c>Windows XP:</c> The <c>FIBER_FLAG_FLOAT_SWITCH</c> flag is not supported.</para>
/// </param>
/// <param name="lpStartAddress">
/// A pointer to the application-defined function to be executed by the fiber and represents the starting address of the fiber. Execution of the newly
/// created fiber does not begin until another fiber calls the <c>SwitchToFiber</c> function with this address. For more information on the fiber
/// callback function, see <c>FiberProc</c>.
/// A pointer to the application-defined function to be executed by the fiber and represents the starting address of the fiber.
/// Execution of the newly created fiber does not begin until another fiber calls the <c>SwitchToFiber</c> function with this
/// address. For more information on the fiber callback function, see <c>FiberProc</c>.
/// </param>
/// <param name="lpParameter">
/// A pointer to a variable that is passed to the fiber. The fiber can retrieve this data by using the <c>GetFiberData</c> macro.
@ -167,11 +174,11 @@ namespace Vanara.PInvoke
/// <para>If the function succeeds, the return value is the address of the fiber.</para>
/// <para>If the function fails, the return value is NULL. To get extended error information, call <c>GetLastError</c>.</para>
/// </returns>
// LPVOID WINAPI CreateFiberEx( _In_ SIZE_T dwStackCommitSize, _In_ SIZE_T dwStackReserveSize, _In_ DWORD dwFlags, _In_ LPFIBER_START_ROUTINE
// lpStartAddress, _In_opt_ LPVOID lpParameter); https://msdn.microsoft.com/en-us/library/windows/desktop/ms682406(v=vs.85).aspx
// LPVOID WINAPI CreateFiberEx( _In_ SIZE_T dwStackCommitSize, _In_ SIZE_T dwStackReserveSize, _In_ DWORD dwFlags, _In_
// LPFIBER_START_ROUTINE lpStartAddress, _In_opt_ LPVOID lpParameter); https://msdn.microsoft.com/en-us/library/windows/desktop/ms682406(v=vs.85).aspx
[DllImport(Lib.Kernel32, SetLastError = true, ExactSpelling = true)]
[PInvokeData("WinBase.h", MSDNShortId = "ms682406")]
public static extern IntPtr CreateFiberEx(SizeT dwStackCommitSize, SizeT dwStackReserveSize, FIBER_FLAG dwFlags, FiberProc lpStartAddress, [In] IntPtr lpParameter);
public static extern IntPtr CreateFiberEx(SizeT dwStackCommitSize, SizeT dwStackReserveSize, FIBER_FLAG dwFlags, FiberProc lpStartAddress, [In, Optional] IntPtr lpParameter);
/// <summary>Deletes an existing fiber.</summary>
/// <param name="lpFiber">The address of the fiber to be deleted.</param>
@ -183,8 +190,7 @@ namespace Vanara.PInvoke
/// <summary>Retrieves a pseudo handle for the current process.</summary>
/// <returns>The return value is a pseudo handle to the current process.</returns>
// HANDLE WINAPI GetCurrentProcess(void);
// https://msdn.microsoft.com/en-us/library/windows/desktop/ms683179(v=vs.85).aspx
// HANDLE WINAPI GetCurrentProcess(void); https://msdn.microsoft.com/en-us/library/windows/desktop/ms683179(v=vs.85).aspx
[DllImport(Lib.Kernel32, SetLastError = false, ExactSpelling = true)]
[PInvokeData("WinBase.h", MSDNShortId = "ms683179")]
public static extern HPROCESS GetCurrentProcess();
@ -279,11 +285,14 @@ namespace Vanara.PInvoke
/// </summary>
/// <param name="Node">The number of the node.</param>
/// <param name="ProcessorMask">
/// <para>The processor mask for the node. A processor mask is a bit vector in which each bit represents a processor and whether it is in the node.</para>
/// <para>
/// The processor mask for the node. A processor mask is a bit vector in which each bit represents a processor and whether it is in
/// the node.
/// </para>
/// <para>If the node has no processors configured, the processor mask is zero.</para>
/// <para>
/// On systems with more than 64 processors, this parameter is set to the processor mask for the node only if the node is in the same processor group as
/// the calling thread. Otherwise, the parameter is set to zero.
/// On systems with more than 64 processors, this parameter is set to the processor mask for the node only if the node is in the same
/// processor group as the calling thread. Otherwise, the parameter is set to zero.
/// </para>
/// </param>
/// <returns>
@ -298,13 +307,15 @@ namespace Vanara.PInvoke
/// <summary>
/// <para>Retrieves the node number for the specified processor.</para>
/// <para>Use the <c>GetNumaProcessorNodeEx</c> function to specify a processor group and retrieve the node number as a <c>USHORT</c> value.</para>
/// <para>
/// Use the <c>GetNumaProcessorNodeEx</c> function to specify a processor group and retrieve the node number as a <c>USHORT</c> value.
/// </para>
/// </summary>
/// <param name="Processor">
/// <para>The processor number.</para>
/// <para>
/// On a system with more than 64 logical processors, the processor number is relative to the processor group that contains the processor on which the
/// calling thread is running.
/// On a system with more than 64 logical processors, the processor number is relative to the processor group that contains the
/// processor on which the calling thread is running.
/// </para>
/// </param>
/// <param name="NodeNumber">The node number. If the processor does not exist, this parameter is 0xFF.</param>
@ -345,7 +356,7 @@ namespace Vanara.PInvoke
[DllImport(Lib.Kernel32, SetLastError = true, ExactSpelling = true)]
[PInvokeData("winbase.h", MSDNShortId = "6b843cd8-eeb5-4aa1-aad4-ce98916346b1")]
[return: MarshalAs(UnmanagedType.Bool)]
public static extern bool GetNumaProcessorNodeEx(ref PROCESSOR_NUMBER Processor, out ushort NodeNumber);
public static extern bool GetNumaProcessorNodeEx(in PROCESSOR_NUMBER Processor, out ushort NodeNumber);
/// <summary>
/// <para>Retrieves the NUMA node number that corresponds to the specified proximity domain identifier.</para>
@ -386,8 +397,8 @@ namespace Vanara.PInvoke
/// <param name="hProcess">
/// <para>A handle to the process whose affinity mask is desired.</para>
/// <para>
/// This handle must have the <c>PROCESS_QUERY_INFORMATION</c> or <c>PROCESS_QUERY_LIMITED_INFORMATION</c> access right. For more information, see
/// Process Security and Access Rights.
/// This handle must have the <c>PROCESS_QUERY_INFORMATION</c> or <c>PROCESS_QUERY_LIMITED_INFORMATION</c> access right. For more
/// information, see Process Security and Access Rights.
/// </para>
/// <para><c>Windows Server 2003 and Windows XP:</c> The handle must have the <c>PROCESS_QUERY_INFORMATION</c> access right.</para>
/// </param>
@ -399,16 +410,18 @@ namespace Vanara.PInvoke
/// lpSystemAffinityMask to the appropriate affinity masks.
/// </para>
/// <para>
/// On a system with more than 64 processors, if the threads of the calling process are in a single processor group, the function sets the variables
/// pointed to by lpProcessAffinityMask and lpSystemAffinityMask to the process affinity mask and the processor mask of active logical processors for
/// that group. If the calling process contains threads in multiple groups, the function returns zero for both affinity masks.
/// On a system with more than 64 processors, if the threads of the calling process are in a single processor group, the function
/// sets the variables pointed to by lpProcessAffinityMask and lpSystemAffinityMask to the process affinity mask and the processor
/// mask of active logical processors for that group. If the calling process contains threads in multiple groups, the function
/// returns zero for both affinity masks.
/// </para>
/// <para>
/// If the function fails, the return value is zero, and the values of the variables pointed to by lpProcessAffinityMask and lpSystemAffinityMask are
/// undefined. To get extended error information, call <c>GetLastError</c>.
/// If the function fails, the return value is zero, and the values of the variables pointed to by lpProcessAffinityMask and
/// lpSystemAffinityMask are undefined. To get extended error information, call <c>GetLastError</c>.
/// </para>
/// </returns>
// BOOL WINAPI GetProcessAffinityMask( _In_ HANDLE hProcess, _Out_ PDWORD_PTR lpProcessAffinityMask, _Out_ PDWORD_PTR lpSystemAffinityMask); https://msdn.microsoft.com/en-us/library/windows/desktop/ms683213(v=vs.85).aspx
// BOOL WINAPI GetProcessAffinityMask( _In_ HANDLE hProcess, _Out_ PDWORD_PTR lpProcessAffinityMask, _Out_ PDWORD_PTR
// lpSystemAffinityMask); https://msdn.microsoft.com/en-us/library/windows/desktop/ms683213(v=vs.85).aspx
[DllImport(Lib.Kernel32, SetLastError = true, ExactSpelling = true)]
[PInvokeData("WinBase.h", MSDNShortId = "ms683213")]
[return: MarshalAs(UnmanagedType.Bool)]
@ -417,12 +430,14 @@ namespace Vanara.PInvoke
/// <summary>Retrieves accounting information for all I/O operations performed by the specified process.</summary>
/// <param name="hProcess">
/// <para>
/// A handle to the process. The handle must have the <c>PROCESS_QUERY_INFORMATION</c> or <c>PROCESS_QUERY_LIMITED_INFORMATION</c> access right. For more
/// information, see Process Security and Access Rights.
/// A handle to the process. The handle must have the <c>PROCESS_QUERY_INFORMATION</c> or <c>PROCESS_QUERY_LIMITED_INFORMATION</c>
/// access right. For more information, see Process Security and Access Rights.
/// </para>
/// <para><c>Windows Server 2003 and Windows XP:</c> The handle must have the <c>PROCESS_QUERY_INFORMATION</c> access right.</para>
/// </param>
/// <param name="lpIoCounters">A pointer to an <c>IO_COUNTERS</c> structure that receives the I/O accounting information for the process.</param>
/// <param name="lpIoCounters">
/// A pointer to an <c>IO_COUNTERS</c> structure that receives the I/O accounting information for the process.
/// </param>
/// <returns>
/// <para>If the function succeeds, the return value is nonzero.</para>
/// <para>If the function fails, the return value is zero. To get extended error information, call <c>GetLastError</c>.</para>
@ -442,12 +457,12 @@ namespace Vanara.PInvoke
/// <para><c>Windows Server 2003 and Windows XP:</c> The handle must have the <c>PROCESS_QUERY_INFORMATION</c> access right.</para>
/// </param>
/// <param name="lpMinimumWorkingSetSize">
/// A pointer to a variable that receives the minimum working set size of the specified process, in bytes. The virtual memory manager attempts to keep at
/// least this much memory resident in the process whenever the process is active.
/// A pointer to a variable that receives the minimum working set size of the specified process, in bytes. The virtual memory manager
/// attempts to keep at least this much memory resident in the process whenever the process is active.
/// </param>
/// <param name="lpMaximumWorkingSetSize">
/// A pointer to a variable that receives the maximum working set size of the specified process, in bytes. The virtual memory manager attempts to keep no
/// more than this much memory resident in the process whenever the process is active when memory is in short supply.
/// A pointer to a variable that receives the maximum working set size of the specified process, in bytes. The virtual memory manager
/// attempts to keep no more than this much memory resident in the process whenever the process is active when memory is in short supply.
/// </param>
/// <returns>
/// <para>If the function succeeds, the return value is nonzero.</para>
@ -663,11 +678,12 @@ namespace Vanara.PInvoke
// lpBaseAddress, DWORD nndPreferred );
[DllImport(Lib.Kernel32, SetLastError = true, ExactSpelling = true)]
[PInvokeData("winbase.h", MSDNShortId = "1e28c8db-112d-481d-b470-8ca618e125ce")]
public static extern IntPtr MapViewOfFileExNuma(HFILE hFileMappingObject, FileAccess dwDesiredAccess, uint dwFileOffsetHigh, uint dwFileOffsetLow, SizeT dwNumberOfBytesToMap, IntPtr lpBaseAddress, uint nndPreferred);
public static extern IntPtr MapViewOfFileExNuma(HFILE hFileMappingObject, FILE_MAP dwDesiredAccess, uint dwFileOffsetHigh, uint dwFileOffsetLow, SizeT dwNumberOfBytesToMap, IntPtr lpBaseAddress, uint nndPreferred);
/// <summary>Sets a processor affinity mask for the threads of the specified process.</summary>
/// <param name="hProcess">
/// A handle to the process whose affinity mask is to be set. This handle must have the <c>PROCESS_SET_INFORMATION</c> access right. For more
/// information, see Process Security and Access Rights.
/// A handle to the process whose affinity mask is to be set. This handle must have the <c>PROCESS_SET_INFORMATION</c> access right.
/// For more information, see Process Security and Access Rights.
/// </param>
/// <param name="dwProcessAffinityMask">
/// <para>The affinity mask for the threads of the process.</para>
@ -678,7 +694,8 @@ namespace Vanara.PInvoke
/// <para>If the function fails, the return value is zero. To get extended error information, call <c>GetLastError</c>.</para>
/// <para>If the process affinity mask requests a processor that is not configured in the system, the last error code is <c>ERROR_INVALID_PARAMETER</c>.</para>
/// <para>
/// On a system with more than 64 processors, if the calling process contains threads in more than one processor group, the last error code is <c>ERROR_INVALID_PARAMETER</c>.
/// On a system with more than 64 processors, if the calling process contains threads in more than one processor group, the last
/// error code is <c>ERROR_INVALID_PARAMETER</c>.
/// </para>
/// </returns>
// BOOL WINAPI SetProcessAffinityMask( _In_ HANDLE hProcess, _In_ DWORD_PTR dwProcessAffinityMask); https://msdn.microsoft.com/en-us/library/windows/desktop/ms686223(v=vs.85).aspx
@ -690,41 +707,46 @@ namespace Vanara.PInvoke
/// <summary>Sets the minimum and maximum working set sizes for the specified process.</summary>
/// <param name="hProcess">
/// <para>A handle to the process whose working set sizes is to be set.</para>
/// <para>The handle must have the <c>PROCESS_SET_QUOTA</c> access right. For more information, see Process Security and Access Rights.</para>
/// <para>
/// The handle must have the <c>PROCESS_SET_QUOTA</c> access right. For more information, see Process Security and Access Rights.
/// </para>
/// </param>
/// <param name="dwMinimumWorkingSetSize">
/// <para>
/// The minimum working set size for the process, in bytes. The virtual memory manager attempts to keep at least this much memory resident in the process
/// whenever the process is active.
/// The minimum working set size for the process, in bytes. The virtual memory manager attempts to keep at least this much memory
/// resident in the process whenever the process is active.
/// </para>
/// <para>
/// This parameter must be greater than zero but less than or equal to the maximum working set size. The default size is 50 pages (for example, this is
/// 204,800 bytes on systems with a 4K page size). If the value is greater than zero but less than 20 pages, the minimum value is set to 20 pages.
/// This parameter must be greater than zero but less than or equal to the maximum working set size. The default size is 50 pages
/// (for example, this is 204,800 bytes on systems with a 4K page size). If the value is greater than zero but less than 20 pages,
/// the minimum value is set to 20 pages.
/// </para>
/// <para>
/// If both dwMinimumWorkingSetSize and dwMaximumWorkingSetSize have the value ( <c>SIZE_T</c>)1, the function removes as many pages as possible from
/// the working set of the specified process.
/// If both dwMinimumWorkingSetSize and dwMaximumWorkingSetSize have the value ( <c>SIZE_T</c>)1, the function removes as many pages
/// as possible from the working set of the specified process.
/// </para>
/// </param>
/// <param name="dwMaximumWorkingSetSize">
/// <para>
/// The maximum working set size for the process, in bytes. The virtual memory manager attempts to keep no more than this much memory resident in the
/// process whenever the process is active and available memory is low.
/// The maximum working set size for the process, in bytes. The virtual memory manager attempts to keep no more than this much memory
/// resident in the process whenever the process is active and available memory is low.
/// </para>
/// <para>
/// This parameter must be greater than or equal to 13 pages (for example, 53,248 on systems with a 4K page size), and less than the system-wide maximum
/// (number of available pages minus 512 pages). The default size is 345 pages (for example, this is 1,413,120 bytes on systems with a 4K page size).
/// This parameter must be greater than or equal to 13 pages (for example, 53,248 on systems with a 4K page size), and less than the
/// system-wide maximum (number of available pages minus 512 pages). The default size is 345 pages (for example, this is 1,413,120
/// bytes on systems with a 4K page size).
/// </para>
/// <para>
/// If both dwMinimumWorkingSetSize and dwMaximumWorkingSetSize have the value ( <c>SIZE_T</c>)1, the function removes as many pages as possible from
/// the working set of the specified process.
/// If both dwMinimumWorkingSetSize and dwMaximumWorkingSetSize have the value ( <c>SIZE_T</c>)1, the function removes as many pages
/// as possible from the working set of the specified process.
/// </para>
/// </param>
/// <returns>
/// <para>If the function succeeds, the return value is nonzero.</para>
/// <para>If the function fails, the return value is zero. Call <c>GetLastError</c> to obtain extended error information.</para>
/// </returns>
// BOOL WINAPI SetProcessWorkingSetSize( _In_ HANDLE hProcess, _In_ SIZE_T dwMinimumWorkingSetSize, _In_ SIZE_T dwMaximumWorkingSetSize); https://msdn.microsoft.com/en-us/library/windows/desktop/ms686234(v=vs.85).aspx
// BOOL WINAPI SetProcessWorkingSetSize( _In_ HANDLE hProcess, _In_ SIZE_T dwMinimumWorkingSetSize, _In_ SIZE_T
// dwMaximumWorkingSetSize); https://msdn.microsoft.com/en-us/library/windows/desktop/ms686234(v=vs.85).aspx
[DllImport(Lib.Kernel32, SetLastError = true, ExactSpelling = true)]
[PInvokeData("WinBase.h", MSDNShortId = "ms686234")]
[return: MarshalAs(UnmanagedType.Bool)]
@ -734,21 +756,27 @@ namespace Vanara.PInvoke
/// <param name="hThread">
/// <para>A handle to the thread whose affinity mask is to be set.</para>
/// <para>
/// This handle must have the <c>THREAD_SET_INFORMATION</c> or <c>THREAD_SET_LIMITED_INFORMATION</c> access right and the <c>THREAD_QUERY_INFORMATION</c>
/// or <c>THREAD_QUERY_LIMITED_INFORMATION</c> access right. For more information, see Thread Security and Access Rights.
/// This handle must have the <c>THREAD_SET_INFORMATION</c> or <c>THREAD_SET_LIMITED_INFORMATION</c> access right and the
/// <c>THREAD_QUERY_INFORMATION</c> or <c>THREAD_QUERY_LIMITED_INFORMATION</c> access right. For more information, see Thread
/// Security and Access Rights.
/// </para>
/// <para>
/// <c>Windows Server 2003 and Windows XP:</c> The handle must have the <c>THREAD_SET_INFORMATION</c> and <c>THREAD_QUERY_INFORMATION</c> access rights.
/// <c>Windows Server 2003 and Windows XP:</c> The handle must have the <c>THREAD_SET_INFORMATION</c> and
/// <c>THREAD_QUERY_INFORMATION</c> access rights.
/// </para>
/// </param>
/// <param name="dwThreadAffinityMask">
/// <para>The affinity mask for the thread.</para>
/// <para>On a system with more than 64 processors, the affinity mask must specify processors in the thread's current processor group.</para>
/// <para>
/// On a system with more than 64 processors, the affinity mask must specify processors in the thread's current processor group.
/// </para>
/// </param>
/// <returns>
/// <para>If the function succeeds, the return value is the thread's previous affinity mask.</para>
/// <para>If the function fails, the return value is zero. To get extended error information, call <c>GetLastError</c>.</para>
/// <para>If the thread affinity mask requests a processor that is not selected for the process affinity mask, the last error code is <c>ERROR_INVALID_PARAMETER</c>.</para>
/// <para>
/// If the thread affinity mask requests a processor that is not selected for the process affinity mask, the last error code is <c>ERROR_INVALID_PARAMETER</c>.
/// </para>
/// </returns>
// DWORD_PTR WINAPI SetThreadAffinityMask( _In_ HANDLE hThread, _In_ DWORD_PTR dwThreadAffinityMask); https://msdn.microsoft.com/en-us/library/windows/desktop/ms686247(v=vs.85).aspx
[DllImport(Lib.Kernel32, SetLastError = true, ExactSpelling = true)]
@ -756,8 +784,8 @@ namespace Vanara.PInvoke
public static extern UIntPtr SetThreadAffinityMask([In] HTHREAD hThread, UIntPtr dwThreadAffinityMask);
/// <summary>
/// Enables an application to inform the system that it is in use, thereby preventing the system from entering sleep or turning off the display while the
/// application is running.
/// Enables an application to inform the system that it is in use, thereby preventing the system from entering sleep or turning off
/// the display while the application is running.
/// </summary>
/// <param name="esFlags">
/// <para>The thread's execution requirements. This parameter can be one or more of the following values.</para>
@ -770,14 +798,16 @@ namespace Vanara.PInvoke
/// <item>
/// <term>ES_AWAYMODE_REQUIRED0x00000040</term>
/// <term>
/// Enables away mode. This value must be specified with ES_CONTINUOUS.Away mode should be used only by media-recording and media-distribution
/// applications that must perform critical background processing on desktop computers while the computer appears to be sleeping. See Remarks.
/// Enables away mode. This value must be specified with ES_CONTINUOUS.Away mode should be used only by media-recording and
/// media-distribution applications that must perform critical background processing on desktop computers while the computer appears
/// to be sleeping. See Remarks.
/// </term>
/// </item>
/// <item>
/// <term>ES_CONTINUOUS0x80000000</term>
/// <term>
/// Informs the system that the state being set should remain in effect until the next call that uses ES_CONTINUOUS and one of the other state flags is cleared.
/// Informs the system that the state being set should remain in effect until the next call that uses ES_CONTINUOUS and one of the
/// other state flags is cleared.
/// </term>
/// </item>
/// <item>
@ -791,7 +821,8 @@ namespace Vanara.PInvoke
/// <item>
/// <term>ES_USER_PRESENT0x00000004</term>
/// <term>
/// This value is not supported. If ES_USER_PRESENT is combined with other esFlags values, the call will fail and none of the specified states will be set.
/// This value is not supported. If ES_USER_PRESENT is combined with other esFlags values, the call will fail and none of the
/// specified states will be set.
/// </term>
/// </item>
/// </list>
@ -816,8 +847,8 @@ namespace Vanara.PInvoke
/// <summary>Runs the specified application.</summary>
/// <param name="lpCmdLine">
/// The command line (file name plus optional parameters) for the application to be executed. If the name of the executable file in the lpCmdLine
/// parameter does not contain a directory path, the system searches for the executable file in this sequence:
/// The command line (file name plus optional parameters) for the application to be executed. If the name of the executable file in
/// the lpCmdLine parameter does not contain a directory path, the system searches for the executable file in this sequence:
/// </param>
/// <param name="uCmdShow">
/// The display options. For a list of the acceptable values, see the description of the nCmdShow parameter of the <c>ShowWindow</c> function.
@ -853,6 +884,6 @@ namespace Vanara.PInvoke
// UINT WINAPI WinExec( _In_ LPCSTR lpCmdLine, _In_ UINT uCmdShow); https://msdn.microsoft.com/en-us/library/windows/desktop/ms687393(v=vs.85).aspx
[DllImport(Lib.Kernel32, SetLastError = false, ExactSpelling = true)]
[PInvokeData("WinBase.h", MSDNShortId = "ms687393")]
public static extern uint WinExec([In] [MarshalAs(UnmanagedType.LPStr)] string lpCmdLine, ShowWindowCommand uCmdShow);
public static extern uint WinExec([In, MarshalAs(UnmanagedType.LPStr)] string lpCmdLine, ShowWindowCommand uCmdShow);
}
}

View File

@ -48,6 +48,7 @@
<Compile Include="AppModelTests.cs" />
<Compile Include="InterlockedApiTests.cs" />
<Compile Include="InteropServices\SafeLocalHandleTests.cs" />
<Compile Include="WinBase.ProcessThreadTests.cs" />
<Compile Include="WinBase.PowerTests.cs" />
<Compile Include="WinBase.MemMgmtTests.cs" />
<Compile Include="WinBase.MailslotTests.cs" />

View File

@ -0,0 +1,163 @@
using NUnit.Framework;
using System;
using static Vanara.PInvoke.Kernel32;
namespace Vanara.PInvoke.Tests
{
[TestFixture]
public partial class WinBaseTests_ProcessThread
{
public readonly static byte ValidNumaNode = GetNumaHighestNodeNumber(out var n) ? (byte)n : (byte)0;
public readonly static byte ValidProcessor = (byte)(Environment.ProcessorCount - 1);
[Test]
public void ConvertThreadToFiberExTest()
{
Assert.That(ConvertThreadToFiberEx(default, FIBER_FLAG.FIBER_FLAG_FLOAT_SWITCH), ResultIs.ValidHandle);
Assert.That(ConvertFiberToThread(), ResultIs.Successful);
}
[Test]
public void ConvertThreadToFiberTest()
{
Assert.That(ConvertThreadToFiber(), ResultIs.ValidHandle);
Assert.That(ConvertFiberToThread(), ResultIs.Successful);
}
[Test]
public void CreateFiberExTest()
{
var fibers = new IntPtr[2];
Assert.That(fibers[0] = ConvertThreadToFiber(), ResultIs.ValidHandle);
Assert.That(fibers[1] = CreateFiberEx(0, 0, FIBER_FLAG.FIBER_FLAG_FLOAT_SWITCH, LocalProc), ResultIs.ValidHandle);
SwitchToFiber(fibers[1]);
DeleteFiber(fibers[1]);
void LocalProc(IntPtr lpParameter) { TestContext.WriteLine("In fiber."); SwitchToFiber(fibers[0]); }
}
[Test]
public void CreateFiberTest()
{
var fibers = new IntPtr[2];
Assert.That(fibers[0] = ConvertThreadToFiber(), ResultIs.ValidHandle);
Assert.That(fibers[1] = CreateFiber(0, LocalProc), ResultIs.ValidHandle);
SwitchToFiber(fibers[1]);
DeleteFiber(fibers[1]);
void LocalProc(IntPtr lpParameter) { TestContext.WriteLine("In fiber."); SwitchToFiber(fibers[0]); }
}
[Test]
public void GetCurrentProcessTest()
{
Assert.That(GetCurrentProcess(), ResultIs.ValidHandle);
}
[Test]
public void GetNumaAvailableMemoryNodeExTest()
{
Assert.That(GetNumaAvailableMemoryNodeEx(ValidNumaNode, out var bytes), ResultIs.Successful);
TestContext.Write(bytes);
}
[Test]
public void GetNumaAvailableMemoryNodeTest()
{
Assert.That(GetNumaAvailableMemoryNode(ValidNumaNode, out var bytes), ResultIs.Successful);
bytes.WriteValues();
}
[Test]
public void GetNumaNodeNumberFromHandleTest()
{
using (var tmp = new TempFile(FileAccess.GENERIC_READ, System.IO.FileShare.Read))
{
Assert.That(GetNumaNodeNumberFromHandle(tmp.hFile, out var num), ResultIs.Successful);
TestContext.Write(num);
}
}
[Test]
public void GetNumaNodeProcessorMaskTest()
{
Assert.That(GetNumaNodeProcessorMask(ValidNumaNode, out var mask), ResultIs.Successful);
TestContext.Write(mask);
}
[Test]
public void GetNumaProcessorNodeExTest()
{
var pn = new PROCESSOR_NUMBER(0, 0);
Assert.That(GetNumaProcessorNodeEx(pn, out var num), ResultIs.Successful);
TestContext.Write(num);
}
[Test]
public void GetNumaProcessorNodeTest()
{
Assert.That(GetNumaProcessorNode(ValidProcessor, out var num), ResultIs.Successful);
TestContext.Write(num);
}
[Test]
public void GetNumaProximityNodeTest()
{
Assert.That(GetNumaProximityNode(0, out var num), ResultIs.Successful);
TestContext.Write(num);
}
[Test]
public void GetProcessIoCountersTest()
{
Assert.That(GetProcessIoCounters(GetCurrentProcess(), out var c), ResultIs.Successful);
TestContext.Write(c);
}
[Test]
public void GetSetProcessAffinityMaskTest()
{
Assert.That(GetProcessAffinityMask(GetCurrentProcess(), out var pAff, out var sAff), ResultIs.Successful);
TestContext.Write((pAff, sAff));
Assert.That(SetProcessAffinityMask(GetCurrentProcess(), pAff), ResultIs.Successful);
}
[Test]
public void GetSetProcessWorkingSetSizeTest()
{
Assert.That(GetProcessWorkingSetSize(GetCurrentProcess(), out var min, out var max), ResultIs.Successful);
TestContext.Write((min, max));
Assert.That(SetProcessWorkingSetSize(GetCurrentProcess(), min, max), ResultIs.Successful);
}
[Test]
public void MapViewOfFileExNumaTest()
{
using (var hfile = CreateFileMappingNuma(HFILE.INVALID_HANDLE_VALUE, null, MEM_PROTECTION.PAGE_EXECUTE_READWRITE, 0, 16 * 1024, "Local\\X", 0xffffffff))
{
Assert.That(hfile, ResultIs.ValidHandle);
Assert.That(MapViewOfFileExNuma(hfile, 0, 0, 0, 0, default, 0xffffffff), Is.Not.EqualTo(IntPtr.Zero));
}
}
[Test]
public void SetThreadAffinityMaskTest()
{
Assert.That(SetThreadAffinityMask(GetCurrentThread(), (UIntPtr)1).ToUInt64(), Is.Not.Zero);
//Assert.That(SetThreadAffinityMask(GetCurrentThread(), (UIntPtr)0).ToUInt64(), Is.Not.Zero);
}
[Test]
public void SetThreadExecutionStateTest()
{
Assert.That((int)SetThreadExecutionState(EXECUTION_STATE.ES_SYSTEM_REQUIRED), Is.Not.Zero);
}
[Test]
public void WinExecTest()
{
Assert.That(WinExec("notepad.exe", ShowWindowCommand.SW_NORMAL), Is.GreaterThan(31));
}
}
}