1 module photon.windows.support; 2 version(Windows): 3 import core.sys.windows.core; 4 import core.sys.windows.winsock2; 5 import std.format; 6 7 struct WSABUF 8 { 9 uint length; 10 void* buf; 11 } 12 13 extern(Windows) SOCKET WSASocketW( 14 int af, 15 int type, 16 int protocol, 17 void* lpProtocolInfo, 18 WORD g, 19 DWORD dwFlags 20 ); 21 22 // hackish, we do not use LPCONDITIONPROC 23 alias LPCONDITIONPROC = void*; 24 alias LPWSABUF = WSABUF*; 25 26 extern(Windows) SOCKET WSAAccept( 27 SOCKET s, 28 sockaddr *addr, 29 LPINT addrlen, 30 LPCONDITIONPROC lpfnCondition, 31 DWORD_PTR dwCallbackData 32 ); 33 34 extern(Windows) int WSARecv( 35 SOCKET s, 36 LPWSABUF lpBuffers, 37 DWORD dwBufferCount, 38 LPDWORD lpNumberOfBytesRecvd, 39 LPDWORD lpFlags, 40 LPWSAOVERLAPPED lpOverlapped, 41 LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine 42 ); 43 44 extern(Windows) int WSASend( 45 SOCKET s, 46 LPWSABUF lpBuffers, 47 DWORD dwBufferCount, 48 LPDWORD lpNumberOfBytesSent, 49 DWORD dwFlags, 50 LPWSAOVERLAPPED lpOverlapped, 51 LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine 52 ); 53 54 struct OVERLAPPED_ENTRY { 55 ULONG_PTR lpCompletionKey; 56 LPOVERLAPPED lpOverlapped; 57 ULONG_PTR Internal; 58 DWORD dwNumberOfBytesTransferred; 59 } 60 61 alias LPOVERLAPPED_ENTRY = OVERLAPPED_ENTRY*; 62 63 extern(Windows) BOOL GetQueuedCompletionStatusEx( 64 HANDLE CompletionPort, 65 LPOVERLAPPED_ENTRY lpCompletionPortEntries, 66 ULONG ulCount, 67 PULONG ulNumEntriesRemoved, 68 DWORD dwMilliseconds, 69 BOOL fAlertable 70 ); 71 72 enum WSA_FLAG_OVERLAPPED = 0x01; 73 74 struct TP_POOL; 75 76 alias PTP_POOL = TP_POOL*; 77 78 extern(Windows) PTP_POOL CreateThreadpool( 79 PVOID reserved 80 ); 81 82 extern(Windows) void SetThreadpoolThreadMaximum( 83 PTP_POOL ptpp, 84 DWORD cthrdMost 85 ); 86 87 extern(Windows) BOOL SetThreadpoolThreadMinimum( 88 PTP_POOL ptpp, 89 DWORD cthrdMic 90 ); 91 92 alias TP_VERSION = DWORD; 93 alias PTP_VERSION = TP_VERSION*; 94 95 struct TP_CALLBACK_INSTANCE; 96 alias PTP_CALLBACK_INSTANCE = TP_CALLBACK_INSTANCE*; 97 98 alias PTP_SIMPLE_CALLBACK = extern(Windows) VOID function(PTP_CALLBACK_INSTANCE, PVOID); 99 100 enum TP_CALLBACK_PRIORITY : int { 101 TP_CALLBACK_PRIORITY_HIGH, 102 TP_CALLBACK_PRIORITY_NORMAL, 103 TP_CALLBACK_PRIORITY_LOW, 104 TP_CALLBACK_PRIORITY_INVALID, 105 TP_CALLBACK_PRIORITY_COUNT = TP_CALLBACK_PRIORITY_INVALID 106 } 107 108 struct TP_POOL_STACK_INFORMATION { 109 SIZE_T StackReserve; 110 SIZE_T StackCommit; 111 } 112 alias PTP_POOL_STACK_INFORMATION = TP_POOL_STACK_INFORMATION*; 113 114 struct TP_CLEANUP_GROUP; 115 alias PTP_CLEANUP_GROUP = TP_CLEANUP_GROUP*; 116 117 alias PTP_CLEANUP_GROUP_CANCEL_CALLBACK = extern(Windows) VOID function(PVOID, PVOID); 118 119 struct ACTIVATION_CONTEXT; 120 121 struct TP_CALLBACK_ENVIRON_V3 { 122 TP_VERSION Version; 123 PTP_POOL Pool; 124 PTP_CLEANUP_GROUP CleanupGroup; 125 PTP_CLEANUP_GROUP_CANCEL_CALLBACK CleanupGroupCancelCallback; 126 PVOID RaceDll; 127 ACTIVATION_CONTEXT* ActivationContext; 128 PTP_SIMPLE_CALLBACK FinalizationCallback; 129 DWORD Flags; 130 TP_CALLBACK_PRIORITY CallbackPriority; 131 DWORD Size; 132 } 133 134 alias TP_CALLBACK_ENVIRON = TP_CALLBACK_ENVIRON_V3; 135 alias PTP_CALLBACK_ENVIRON = TP_CALLBACK_ENVIRON*; 136 137 VOID InitializeThreadpoolEnvironment(PTP_CALLBACK_ENVIRON cbe) { 138 cbe.Pool = NULL; 139 cbe.CleanupGroup = NULL; 140 cbe.CleanupGroupCancelCallback = NULL; 141 cbe.RaceDll = NULL; 142 cbe.ActivationContext = NULL; 143 cbe.FinalizationCallback = NULL; 144 cbe.Flags = 0; 145 cbe.Version = 3; 146 cbe.CallbackPriority = TP_CALLBACK_PRIORITY.TP_CALLBACK_PRIORITY_NORMAL; 147 cbe.Size = TP_CALLBACK_ENVIRON.sizeof; 148 } 149 150 extern(Windows) void CloseThreadpool( 151 PTP_POOL ptpp 152 ); 153 154 // inline "function" 155 VOID SetThreadpoolCallbackPool(PTP_CALLBACK_ENVIRON cbe, PTP_POOL pool) { cbe.Pool = pool; } 156 157 struct TP_WORK; 158 alias PTP_WORK = TP_WORK*; 159 160 struct TP_WAIT; 161 alias PTP_WAIT = TP_WAIT*; 162 163 struct TP_TIMER; 164 alias PTP_TIMER = TP_TIMER*; 165 166 alias TP_WAIT_RESULT = DWORD; 167 168 alias PTP_WORK_CALLBACK = extern(Windows) VOID function (PTP_CALLBACK_INSTANCE Instance, PVOID Context, PTP_WORK Work); 169 alias PTP_WAIT_CALLBACK = extern(Windows) VOID function (PTP_CALLBACK_INSTANCE Instance, PVOID Context, PTP_WAIT Wait, TP_WAIT_RESULT WaitResult); 170 alias PTP_TIMER_CALLBACK = extern(Windows) VOID function(PTP_CALLBACK_INSTANCE Instance, PVOID Context, PTP_TIMER Timer); 171 172 extern(Windows) PTP_WORK CreateThreadpoolWork( 173 PTP_WORK_CALLBACK pfnwk, 174 PVOID pv, 175 PTP_CALLBACK_ENVIRON pcbe 176 ); 177 178 extern(Windows) PTP_WAIT CreateThreadpoolWait(PTP_WAIT_CALLBACK pfnwa, PVOID pv, PTP_CALLBACK_ENVIRON pcbe); 179 180 extern(Windows) void SubmitThreadpoolWork( 181 PTP_WORK pwk 182 ); 183 184 extern(Windows) void CloseThreadpoolWork( 185 PTP_WORK pwk 186 ); 187 188 extern(Windows) void SetThreadpoolWait( 189 PTP_WAIT pwa, 190 HANDLE h, 191 PFILETIME pftTimeout 192 ); 193 194 extern(Windows) void CloseThreadpoolWait( 195 PTP_WAIT pwa 196 ); 197 198 extern(Windows) PTP_TIMER CreateThreadpoolTimer( 199 PTP_TIMER_CALLBACK pfnti, 200 PVOID pv, 201 PTP_CALLBACK_ENVIRON pcbe 202 ); 203 204 extern(Windows) void SetThreadpoolTimer( 205 PTP_TIMER pti, 206 PFILETIME pftDueTime, 207 DWORD msPeriod, 208 DWORD msWindowLength 209 ); 210 211 extern(Windows) void CloseThreadpoolTimer( 212 PTP_TIMER pti 213 ); 214 215 216 void outputToConsole(const(wchar)[] msg) 217 { 218 HANDLE output = GetStdHandle(STD_OUTPUT_HANDLE); 219 uint size = cast(uint)msg.length; 220 WriteConsole(output, msg.ptr, size, &size, null); 221 } 222 223 void logf(T...)(const(wchar)[] fmt, T args) 224 { 225 debug(photon) try { 226 formattedWrite(&outputToConsole, fmt, args); 227 formattedWrite(&outputToConsole, "\n"); 228 } 229 catch (Exception e) { 230 outputToConsole("ARGH!"w); 231 } 232 } 233