1 |
william |
4 |
using System; |
2 |
|
|
using System.Collections.Generic; |
3 |
|
|
using System.Text; |
4 |
|
|
using System.Runtime.InteropServices; |
5 |
|
|
using System.Net; |
6 |
|
|
using System.Windows.Forms; |
7 |
|
|
using System.Data; |
8 |
william |
47 |
using log4net; |
9 |
william |
4 |
namespace AnywhereTS |
10 |
|
|
{ |
11 |
|
|
public class TSManager |
12 |
|
|
{ |
13 |
|
|
// Imports |
14 |
|
|
[DllImport("wtsapi32.dll")] |
15 |
|
|
static extern IntPtr WTSOpenServer([MarshalAs(UnmanagedType.LPStr)] String pServerName); |
16 |
|
|
|
17 |
|
|
[DllImport("wtsapi32.dll")] |
18 |
|
|
public static extern void WTSCloseServer(IntPtr hServer); |
19 |
|
|
|
20 |
|
|
[DllImport("wtsapi32.dll")] |
21 |
|
|
public static extern Int32 WTSEnumerateSessions( |
22 |
|
|
IntPtr hServer, |
23 |
|
|
[MarshalAs(UnmanagedType.U4)] Int32 Reserved, |
24 |
|
|
[MarshalAs(UnmanagedType.U4)] Int32 Version, |
25 |
|
|
ref IntPtr ppSessionInfo, |
26 |
|
|
[MarshalAs(UnmanagedType.U4)] ref Int32 pCount); |
27 |
|
|
|
28 |
|
|
[DllImport("wtsapi32.dll", EntryPoint = "WTSQuerySessionInformation", CallingConvention = CallingConvention.Cdecl)] |
29 |
|
|
public static extern bool WTSQuerySessionInformation( |
30 |
|
|
System.IntPtr hServer, |
31 |
|
|
uint sessionId, |
32 |
|
|
WTSInfoClass wtsInfoClass, |
33 |
|
|
out System.IntPtr ppBuffer, |
34 |
|
|
out uint pBytesReturned); |
35 |
|
|
|
36 |
|
|
[DllImport("wtsapi32.dll")] |
37 |
|
|
static extern void WTSFreeMemory(IntPtr pMemory); |
38 |
|
|
|
39 |
|
|
// For Lookup of MAC address |
40 |
|
|
[DllImport("iphlpapi.dll", ExactSpelling = true)] |
41 |
|
|
public static extern int SendARP(int DestIP, int SrcIP, [Out] byte[] |
42 |
|
|
pMacAddr, ref int PhyAddrLen); |
43 |
|
|
|
44 |
|
|
// Consts |
45 |
|
|
public const uint WTS_CURRENT_SESSION = 4294967295; // = -1 |
46 |
|
|
|
47 |
|
|
// Type definitions |
48 |
|
|
|
49 |
|
|
[StructLayout(LayoutKind.Sequential)] |
50 |
|
|
|
51 |
|
|
private struct WTS_SESSION_INFO |
52 |
|
|
{ |
53 |
|
|
public uint SessionID; |
54 |
|
|
|
55 |
|
|
[MarshalAs(UnmanagedType.LPStr)] |
56 |
|
|
public String pWinStationName; |
57 |
|
|
|
58 |
|
|
public WTS_CONNECTSTATE_CLASS State; |
59 |
|
|
} |
60 |
|
|
|
61 |
|
|
public enum WTS_CONNECTSTATE_CLASS |
62 |
|
|
{ |
63 |
|
|
WTSActive, // User logged on to WinStation |
64 |
|
|
WTSConnected, // WinStation connected to client |
65 |
|
|
WTSConnectQuery, // In the process of connecting to client |
66 |
|
|
WTSShadow, // Shadowing another WinStation |
67 |
|
|
WTSDisconnected, // WinStation logged on without client |
68 |
|
|
WTSIdle, // Waiting for client to connect |
69 |
|
|
WTSListen, // WinStation is listening for connection |
70 |
|
|
WTSReset, // WinStation is being reset |
71 |
|
|
WTSDown, // WinStation is down due to error |
72 |
|
|
WTSInit, // WinStation in initialization |
73 |
|
|
}; |
74 |
|
|
|
75 |
|
|
public enum WTSInfoClass |
76 |
|
|
{ |
77 |
|
|
WTSInitialProgram, |
78 |
|
|
WTSApplicationName, |
79 |
|
|
WTSWorkingDirectory, |
80 |
|
|
WTSOEMId, |
81 |
|
|
WTSSessionId, |
82 |
|
|
WTSUserName, |
83 |
|
|
WTSWinStationName, |
84 |
|
|
WTSDomainName, |
85 |
|
|
WTSConnectState, |
86 |
|
|
WTSClientBuildNumber, |
87 |
|
|
WTSClientName, |
88 |
|
|
WTSClientDirectory, |
89 |
|
|
WTSClientProductId, |
90 |
|
|
WTSClientHardwareId, |
91 |
|
|
WTSClientAddress, |
92 |
|
|
WTSClientDisplay, |
93 |
|
|
WTSClientProtocolType, |
94 |
|
|
} ; |
95 |
|
|
|
96 |
|
|
public struct WTS_CLIENT_ADDRESS |
97 |
|
|
{ |
98 |
|
|
public uint AddressFamily; // AF_INET, AF_IPX, AF_NETBIOS, AF_UNSPEC |
99 |
|
|
public Byte[] Address; |
100 |
|
|
}; |
101 |
|
|
|
102 |
|
|
public struct WTS_CLIENT_DISPLAY |
103 |
|
|
{ |
104 |
|
|
public uint HorizontalResolution; // horizontal dimensions, in pixels |
105 |
|
|
public uint VerticalResolution; // vertical dimensions, in pixels |
106 |
|
|
public uint ColorDepth; // 1=16, 2=256, 4=64K, 8=16M |
107 |
|
|
}; |
108 |
|
|
|
109 |
|
|
|
110 |
|
|
// Selected info for terminal server sessions |
111 |
|
|
public struct TS_SESSION_INFO |
112 |
|
|
{ |
113 |
|
|
public uint sessionID; |
114 |
|
|
public string ipAddress; // The IP address of the client |
115 |
|
|
public string macAddress; // The MAC address of the client |
116 |
|
|
public string name; // The (netbios) name of the client |
117 |
|
|
public string username; // User logged in to the session, if any. |
118 |
|
|
public WTS_CONNECTSTATE_CLASS state; // The state of the session |
119 |
|
|
public int HorizontalResolution; // Vertical screen res for the session |
120 |
|
|
public int VerticalResolution; // Horiz screen res for the session |
121 |
|
|
public int ColorDepth; // Screen color depth for the session |
122 |
|
|
}; |
123 |
|
|
|
124 |
|
|
|
125 |
|
|
public static IntPtr OpenServer(String Name) |
126 |
|
|
{ |
127 |
|
|
IntPtr server = WTSOpenServer(Name); |
128 |
|
|
return server; |
129 |
|
|
} |
130 |
|
|
public static void CloseServer(IntPtr ServerHandle) |
131 |
|
|
{ |
132 |
|
|
WTSCloseServer(ServerHandle); |
133 |
|
|
} |
134 |
|
|
|
135 |
|
|
|
136 |
|
|
// Return address for a terminal server session. |
137 |
|
|
// WTSClientAddress gives a pointer to a WTS_CLIENT_ADDRESS structure containing |
138 |
|
|
// the network type and network address of the client. If the function is called |
139 |
|
|
// from the Terminal Services console, ppBuffer returns a NULL pointer. |
140 |
|
|
// Note that the first byte of the IP address returned in the ppBuffer |
141 |
|
|
// parameter will be located at an offset of two bytes from the first location |
142 |
|
|
// of the buffer. |
143 |
|
|
private static string GetTSClientAddress(uint sessionID, IntPtr server) |
144 |
|
|
{ |
145 |
|
|
System.IntPtr ppBuffer = System.IntPtr.Zero; |
146 |
|
|
uint pBytesReturned = 0; |
147 |
|
|
StringBuilder builder = new StringBuilder(); |
148 |
|
|
|
149 |
|
|
// Interface avec API |
150 |
|
|
WTS_CLIENT_ADDRESS wtsAdr = new WTS_CLIENT_ADDRESS(); |
151 |
|
|
|
152 |
|
|
|
153 |
|
|
if (WTSQuerySessionInformation( |
154 |
|
|
server, |
155 |
|
|
sessionID, |
156 |
|
|
WTSInfoClass.WTSClientAddress, |
157 |
|
|
out ppBuffer, |
158 |
|
|
out pBytesReturned)) |
159 |
|
|
{ |
160 |
|
|
wtsAdr.Address = new Byte[pBytesReturned - 1]; |
161 |
|
|
int run = (int)ppBuffer; // pointeur sur les données |
162 |
|
|
Type t = typeof(Byte); |
163 |
|
|
Type t1 = typeof(uint); |
164 |
|
|
|
165 |
|
|
int uintSize = Marshal.SizeOf(t1); |
166 |
|
|
int byteSize = Marshal.SizeOf(t); |
167 |
|
|
|
168 |
|
|
wtsAdr.AddressFamily = (uint)Marshal.ReadInt32((System.IntPtr)run); |
169 |
|
|
|
170 |
|
|
// Address family can be only: |
171 |
|
|
// AF_UNSPEC = 0 (unspecified) |
172 |
|
|
// AF_INET = 2 (internetwork: UDP, TCP, etc.) |
173 |
|
|
// AF_IPX = AF_NS = 6 (IPX protocols: IPX, SPX, etc.) |
174 |
|
|
// AF_NETBIOS = 17 (NetBios-style addresses) |
175 |
|
|
|
176 |
|
|
//run+=uintSize; |
177 |
|
|
//run+=dataSize; |
178 |
|
|
/*switch(wtsAdr.AddressFamily) |
179 |
|
|
{ |
180 |
|
|
case 0:builder.Append("AF_UNSPEC"); |
181 |
|
|
break; |
182 |
|
|
case 1:builder.Append("AF_INET"); |
183 |
|
|
break; |
184 |
|
|
case 2:builder.Append("AF_IPX"); |
185 |
|
|
break; |
186 |
|
|
case 3:builder.Append("AF_NETBIOS"); |
187 |
|
|
break; |
188 |
|
|
}*/ |
189 |
|
|
for (int i = 0; i < pBytesReturned - 1; i++) |
190 |
|
|
{ |
191 |
|
|
wtsAdr.Address[i] = Marshal.ReadByte((System.IntPtr)run); |
192 |
|
|
run += byteSize; |
193 |
|
|
// TO GET and to SEE ALL the DATA |
194 |
|
|
//builder.Append(wtsAdr.Address[i].ToString()+"-"); |
195 |
|
|
} |
196 |
|
|
//builder.Append("-"); |
197 |
|
|
|
198 |
|
|
// The IP address is located in bytes 2, 3, 4, and 5. The other bytes are not used. |
199 |
|
|
// If AddressFamily returns AF_UNSPEC, the first byte in Address |
200 |
|
|
// is initialized to zero. |
201 |
|
|
|
202 |
|
|
// Check if the returned address is an IP address |
203 |
|
|
if (wtsAdr.AddressFamily == 2) |
204 |
|
|
{ // It is an IP address |
205 |
|
|
builder.Append((wtsAdr.Address[4 + 2]).ToString()); |
206 |
|
|
builder.Append("."); |
207 |
|
|
builder.Append((wtsAdr.Address[4 + 3]).ToString()); |
208 |
|
|
builder.Append("."); |
209 |
|
|
builder.Append((wtsAdr.Address[4 + 4]).ToString()); |
210 |
|
|
builder.Append("."); |
211 |
|
|
builder.Append((wtsAdr.Address[4 + 5]).ToString()); |
212 |
|
|
} |
213 |
|
|
} |
214 |
|
|
WTSFreeMemory(ppBuffer); |
215 |
|
|
return builder.ToString(); |
216 |
|
|
} |
217 |
|
|
|
218 |
|
|
// Get display parameters for a user session on a terminal server |
219 |
|
|
// In: SessionID = identifier for the session |
220 |
|
|
// In: server = server handle for the server that the session resides on. |
221 |
|
|
private static void GetTSClientDisplay(uint sessionID, IntPtr server, out int horizontalResolution, out int verticalResolution, out int colorDepth) |
222 |
|
|
{ |
223 |
|
|
horizontalResolution = 0; |
224 |
|
|
verticalResolution = 0; |
225 |
|
|
colorDepth = 0; |
226 |
|
|
|
227 |
|
|
System.IntPtr ppBuffer = System.IntPtr.Zero; |
228 |
|
|
uint pBytesReturned = 0; |
229 |
|
|
StringBuilder sDisplay = new StringBuilder(); |
230 |
|
|
|
231 |
|
|
WTS_CLIENT_DISPLAY clientDisplay = new WTS_CLIENT_DISPLAY(); |
232 |
|
|
clientDisplay.HorizontalResolution = 0; |
233 |
|
|
clientDisplay.VerticalResolution = 0; |
234 |
|
|
clientDisplay.ColorDepth = 0; |
235 |
|
|
|
236 |
|
|
Type dataType = typeof(WTS_CLIENT_DISPLAY); |
237 |
|
|
|
238 |
|
|
if (WTSQuerySessionInformation( |
239 |
|
|
server, |
240 |
|
|
sessionID, |
241 |
|
|
WTSInfoClass.WTSClientDisplay, |
242 |
|
|
out ppBuffer, |
243 |
|
|
out pBytesReturned)) |
244 |
|
|
{ |
245 |
|
|
clientDisplay = (WTS_CLIENT_DISPLAY)Marshal.PtrToStructure(ppBuffer, dataType); |
246 |
|
|
horizontalResolution = (int)(clientDisplay.HorizontalResolution); |
247 |
|
|
verticalResolution = (int)(clientDisplay.VerticalResolution); |
248 |
|
|
colorDepth = (int)(clientDisplay.ColorDepth); |
249 |
|
|
} |
250 |
|
|
|
251 |
|
|
WTSFreeMemory(ppBuffer); |
252 |
|
|
} |
253 |
|
|
|
254 |
|
|
|
255 |
|
|
// Get Mac from IP, using ARP |
256 |
|
|
private static string GetMACFromIP(string ipString) |
257 |
|
|
{ |
258 |
|
|
|
259 |
|
|
IPAddress ip = IPAddress.Parse(ipString); // Actual IP |
260 |
|
|
int rv; |
261 |
|
|
string macStr; |
262 |
|
|
byte[] mac = new byte[6]; |
263 |
|
|
int maclen = mac.Length; |
264 |
|
|
|
265 |
|
|
rv = SendARP(BitConverter.ToInt32(ip.GetAddressBytes(), 0), 0, mac, ref maclen); |
266 |
|
|
if (rv == 0) // If not 0, error |
267 |
|
|
{ |
268 |
|
|
// macStr = BitConverter.ToString(mac, 0, 6); |
269 |
|
|
macStr = BitConverter.ToString(mac, 0, 1)+BitConverter.ToString(mac, 1, 1)+BitConverter.ToString(mac, 2, 1) |
270 |
|
|
+BitConverter.ToString(mac, 3, 1)+BitConverter.ToString(mac, 4, 1)+BitConverter.ToString(mac, 5, 1); |
271 |
|
|
} |
272 |
|
|
else |
273 |
|
|
{ |
274 |
|
|
macStr = ""; |
275 |
|
|
} |
276 |
|
|
return macStr; |
277 |
|
|
} |
278 |
|
|
|
279 |
|
|
|
280 |
|
|
private static string GetTSUserName(uint sessionID, IntPtr server) |
281 |
|
|
{ |
282 |
|
|
System.IntPtr ppBuffer = System.IntPtr.Zero; |
283 |
|
|
uint pBytesReturned = 0; |
284 |
|
|
string currentUserName = ""; |
285 |
|
|
|
286 |
|
|
if (WTSQuerySessionInformation( |
287 |
|
|
server, |
288 |
|
|
sessionID, |
289 |
|
|
WTSInfoClass.WTSUserName, |
290 |
|
|
out ppBuffer, |
291 |
|
|
out pBytesReturned)) |
292 |
|
|
{ |
293 |
|
|
currentUserName = Marshal.PtrToStringAnsi(ppBuffer); |
294 |
|
|
} |
295 |
|
|
|
296 |
|
|
WTSFreeMemory(ppBuffer); |
297 |
|
|
|
298 |
|
|
return currentUserName; |
299 |
|
|
} |
300 |
|
|
|
301 |
|
|
public static string GetTSClientName(uint sessionID, IntPtr server) |
302 |
|
|
{ |
303 |
|
|
System.IntPtr ppBuffer = System.IntPtr.Zero; |
304 |
|
|
int adrBuffer; |
305 |
|
|
uint pBytesReturned = 0; |
306 |
|
|
string clientName = ""; |
307 |
|
|
|
308 |
|
|
if (WTSQuerySessionInformation( |
309 |
|
|
server, |
310 |
|
|
sessionID, |
311 |
|
|
WTSInfoClass.WTSClientName, |
312 |
|
|
out ppBuffer, |
313 |
|
|
out pBytesReturned)) |
314 |
|
|
{ |
315 |
|
|
adrBuffer = (int)ppBuffer; |
316 |
|
|
clientName = Marshal.PtrToStringAnsi((System.IntPtr)adrBuffer); |
317 |
|
|
} |
318 |
|
|
|
319 |
|
|
WTSFreeMemory(ppBuffer); |
320 |
|
|
|
321 |
|
|
return clientName; |
322 |
|
|
} |
323 |
|
|
|
324 |
|
|
// List all sessions on all registered terminal servers and return in a list with selected data for each session. |
325 |
|
|
public static List<TS_SESSION_INFO> ListSessions() |
326 |
|
|
{ |
327 |
|
|
List<TS_SESSION_INFO> ret = new List<TS_SESSION_INFO>(); |
328 |
|
|
if (ATSGlobals.terminalServerConfig == 0) // This server is a terminal server |
329 |
|
|
{ |
330 |
|
|
ListSessions(ret, "localhost"); // Add sessions from local server |
331 |
|
|
} |
332 |
|
|
|
333 |
|
|
// Add sessions from other terminal servers |
334 |
|
|
atsDataSet.TerminalServerDataTable datatableTerminalServer; |
335 |
|
|
datatableTerminalServer = new atsDataSet.TerminalServerDataTable(); |
336 |
|
|
ProSupport.terminalServerTableAdapter.Fill(datatableTerminalServer); |
337 |
|
|
foreach (DataRow row in datatableTerminalServer.Rows) |
338 |
|
|
{ |
339 |
|
|
string strError = ""; |
340 |
|
|
try |
341 |
|
|
{ |
342 |
|
|
strError = ListSessions(ret, row["Path"].ToString()); |
343 |
|
|
} |
344 |
|
|
catch |
345 |
|
|
{ |
346 |
|
|
//MessageBox.Show("Error: Could not retrieve session data from server '" + row["Path"].ToString() + "'. Error 39092."); |
347 |
|
|
} |
348 |
|
|
if (strError.Length != 0) |
349 |
|
|
{ |
350 |
|
|
//MessageBox.Show("Warning: " + strError, "AnywhereTS"); |
351 |
|
|
} |
352 |
|
|
} |
353 |
|
|
return ret; |
354 |
|
|
} |
355 |
|
|
|
356 |
|
|
// List all sessions on the terminal server and return in a list with selected data for each session. |
357 |
|
|
public static List<TS_SESSION_INFO> ListSessions(String serverName) |
358 |
|
|
{ |
359 |
|
|
IntPtr server = IntPtr.Zero; |
360 |
|
|
List<TS_SESSION_INFO> ret = new List<TS_SESSION_INFO>(); |
361 |
|
|
server = OpenServer(serverName); |
362 |
|
|
|
363 |
|
|
try |
364 |
|
|
{ |
365 |
|
|
IntPtr ppSessionInfo = IntPtr.Zero; |
366 |
|
|
|
367 |
|
|
Int32 count = 0; |
368 |
|
|
Int32 retval = WTSEnumerateSessions(server, 0, 1, ref ppSessionInfo, ref count); |
369 |
|
|
Int32 dataSize = Marshal.SizeOf(typeof(WTS_SESSION_INFO)); |
370 |
|
|
Int32 current = (int)ppSessionInfo; |
371 |
|
|
TS_SESSION_INFO CurrentClientInfo; |
372 |
|
|
|
373 |
|
|
if (retval != 0) |
374 |
|
|
{ |
375 |
|
|
for (int i = 0; i < count; i++) // Iterate through all sessions on the server |
376 |
|
|
{ |
377 |
|
|
WTS_SESSION_INFO si = (WTS_SESSION_INFO)Marshal.PtrToStructure((System.IntPtr)current, typeof(WTS_SESSION_INFO)); |
378 |
|
|
current += dataSize; |
379 |
|
|
CurrentClientInfo.sessionID = si.SessionID; |
380 |
|
|
CurrentClientInfo.ipAddress = GetTSClientAddress(si.SessionID, server); |
381 |
|
|
CurrentClientInfo.name = GetTSClientName(si.SessionID, server); |
382 |
|
|
CurrentClientInfo.username = GetTSUserName(si.SessionID, server); |
383 |
|
|
CurrentClientInfo.state = si.State; |
384 |
|
|
if (CurrentClientInfo.name != "") |
385 |
|
|
{ |
386 |
|
|
CurrentClientInfo.macAddress = ProSupport.GetMacAddressFromNameAndDatabase(CurrentClientInfo.name); |
387 |
|
|
} |
388 |
|
|
else |
389 |
|
|
{ |
390 |
|
|
CurrentClientInfo.macAddress = ""; |
391 |
|
|
} |
392 |
|
|
|
393 |
|
|
GetTSClientDisplay( |
394 |
|
|
si.SessionID, |
395 |
|
|
server, |
396 |
|
|
out CurrentClientInfo.HorizontalResolution, |
397 |
|
|
out CurrentClientInfo.VerticalResolution, |
398 |
|
|
out CurrentClientInfo.ColorDepth); |
399 |
|
|
ret.Add(CurrentClientInfo); |
400 |
|
|
} |
401 |
|
|
|
402 |
|
|
WTSFreeMemory(ppSessionInfo); |
403 |
|
|
} |
404 |
|
|
} |
405 |
|
|
|
406 |
|
|
finally |
407 |
|
|
{ |
408 |
|
|
try |
409 |
|
|
{ |
410 |
|
|
CloseServer(server); |
411 |
|
|
} |
412 |
william |
46 |
catch (Exception e) |
413 |
william |
4 |
{ |
414 |
|
|
MessageBox.Show("Error could not close terminal server connection (63210)"); |
415 |
william |
46 |
using (log4net.NDC.Push(string.Format("SqlException: MESSAGE={0}{1}Diagnostics:{1}{2}", e.Message, System.Environment.NewLine, e.ToString()))) |
416 |
|
|
{ |
417 |
|
|
Logging.ATSAdminLog.Error("Error could not close terminal server connection (63210)"); |
418 |
|
|
} |
419 |
william |
4 |
} |
420 |
|
|
} |
421 |
|
|
return ret; |
422 |
|
|
} |
423 |
|
|
|
424 |
|
|
// List all sessions on the terminal server and return in a list with selected data for each session. |
425 |
|
|
public static List<AtsSession> ListTSsessions(String serverName) |
426 |
|
|
{ |
427 |
|
|
IntPtr server = IntPtr.Zero; |
428 |
|
|
List<AtsSession> ret = new List<AtsSession>(); |
429 |
|
|
server = OpenServer(serverName); |
430 |
|
|
|
431 |
|
|
try |
432 |
|
|
{ |
433 |
|
|
IntPtr ppSessionInfo = IntPtr.Zero; |
434 |
|
|
|
435 |
|
|
Int32 count = 0; |
436 |
|
|
Int32 retval = WTSEnumerateSessions(server, 0, 1, ref ppSessionInfo, ref count); |
437 |
|
|
Int32 dataSize = Marshal.SizeOf(typeof(WTS_SESSION_INFO)); |
438 |
|
|
Int32 current = (int)ppSessionInfo; |
439 |
|
|
AtsSession CurrentSession = new AtsSession(); |
440 |
|
|
|
441 |
|
|
if (retval != 0) |
442 |
|
|
{ |
443 |
|
|
for (int i = 0; i < count; i++) // Iterate through all sessions on the server |
444 |
|
|
{ |
445 |
|
|
WTS_SESSION_INFO si = (WTS_SESSION_INFO)Marshal.PtrToStructure((System.IntPtr)current, typeof(WTS_SESSION_INFO)); |
446 |
|
|
current += dataSize; |
447 |
|
|
CurrentSession.sessionID = si.SessionID; |
448 |
|
|
CurrentSession.ipAddress = GetTSClientAddress(si.SessionID, server); |
449 |
|
|
CurrentSession.name = GetTSClientName(si.SessionID, server); |
450 |
|
|
CurrentSession.username = GetTSUserName(si.SessionID, server); |
451 |
|
|
CurrentSession.state = si.State; |
452 |
|
|
if (CurrentSession.name != "") |
453 |
|
|
{ |
454 |
|
|
CurrentSession.macAddress = ProSupport.GetMacAddressFromNameAndDatabase(CurrentSession.name); |
455 |
|
|
} |
456 |
|
|
else |
457 |
|
|
{ |
458 |
|
|
CurrentSession.macAddress = ""; |
459 |
|
|
} |
460 |
|
|
|
461 |
|
|
GetTSClientDisplay( |
462 |
|
|
si.SessionID, |
463 |
|
|
server, |
464 |
|
|
out CurrentSession.HorizontalResolution, |
465 |
|
|
out CurrentSession.VerticalResolution, |
466 |
|
|
out CurrentSession.ColorDepth); |
467 |
|
|
ret.Add(CurrentSession); |
468 |
|
|
} |
469 |
|
|
|
470 |
|
|
WTSFreeMemory(ppSessionInfo); |
471 |
|
|
} |
472 |
|
|
} |
473 |
|
|
|
474 |
|
|
finally |
475 |
|
|
{ |
476 |
|
|
try |
477 |
|
|
{ |
478 |
|
|
CloseServer(server); |
479 |
|
|
} |
480 |
william |
46 |
catch(Exception e) |
481 |
william |
4 |
{ |
482 |
|
|
MessageBox.Show("Error could not close terminal server connection (63210)"); |
483 |
william |
46 |
using (log4net.NDC.Push(string.Format("SqlException: MESSAGE={0}{1}Diagnostics:{1}{2}", e.Message, System.Environment.NewLine, e.ToString()))) |
484 |
|
|
{ |
485 |
|
|
Logging.ATSAdminLog.Error("Error could not close terminal server connection (63210)"); |
486 |
|
|
} |
487 |
william |
4 |
} |
488 |
|
|
} |
489 |
|
|
return ret; |
490 |
|
|
} |
491 |
|
|
|
492 |
|
|
|
493 |
|
|
// List all sessions on the terminal server and adds them to list with selected data for each session. |
494 |
|
|
// Returns error message or "" if everything went ok. |
495 |
|
|
public static string ListSessions(List<TS_SESSION_INFO> SessionInfo, String serverName) |
496 |
|
|
{ |
497 |
|
|
IntPtr server = IntPtr.Zero; |
498 |
|
|
server = OpenServer(serverName); |
499 |
|
|
string strError = "Could not retrieve session data from server '" + serverName + "'"; // Assume something went wrong |
500 |
|
|
if (server != IntPtr.Zero) |
501 |
|
|
{ |
502 |
|
|
try |
503 |
|
|
{ |
504 |
|
|
IntPtr ppSessionInfo = IntPtr.Zero; |
505 |
|
|
|
506 |
|
|
Int32 count = 0; |
507 |
|
|
Int32 retval = WTSEnumerateSessions(server, 0, 1, ref ppSessionInfo, ref count); |
508 |
|
|
Int32 dataSize = Marshal.SizeOf(typeof(WTS_SESSION_INFO)); |
509 |
|
|
Int32 current = (int)ppSessionInfo; |
510 |
|
|
TS_SESSION_INFO CurrentClientInfo; |
511 |
|
|
|
512 |
|
|
if (retval != 0) |
513 |
|
|
{ |
514 |
|
|
for (int i = 0; i < count; i++) |
515 |
|
|
{ |
516 |
|
|
WTS_SESSION_INFO si = (WTS_SESSION_INFO)Marshal.PtrToStructure((System.IntPtr)current, typeof(WTS_SESSION_INFO)); |
517 |
|
|
current += dataSize; |
518 |
|
|
CurrentClientInfo.sessionID = si.SessionID; |
519 |
|
|
CurrentClientInfo.ipAddress = GetTSClientAddress(si.SessionID, server); |
520 |
|
|
CurrentClientInfo.name = GetTSClientName(si.SessionID, server); |
521 |
|
|
CurrentClientInfo.username = GetTSUserName(si.SessionID, server); |
522 |
|
|
CurrentClientInfo.state = si.State; |
523 |
|
|
if (CurrentClientInfo.name != "") |
524 |
|
|
{ |
525 |
|
|
CurrentClientInfo.macAddress = ProSupport.GetMacAddressFromNameAndDatabase(CurrentClientInfo.name); |
526 |
|
|
} |
527 |
|
|
else |
528 |
|
|
{ |
529 |
|
|
CurrentClientInfo.macAddress = ""; |
530 |
|
|
} |
531 |
|
|
GetTSClientDisplay( |
532 |
|
|
si.SessionID, |
533 |
|
|
server, |
534 |
|
|
out CurrentClientInfo.HorizontalResolution, |
535 |
|
|
out CurrentClientInfo.VerticalResolution, |
536 |
|
|
out CurrentClientInfo.ColorDepth); |
537 |
|
|
|
538 |
|
|
SessionInfo.Add(CurrentClientInfo); |
539 |
|
|
} |
540 |
|
|
|
541 |
|
|
WTSFreeMemory(ppSessionInfo); |
542 |
|
|
} |
543 |
|
|
} |
544 |
|
|
|
545 |
|
|
finally |
546 |
|
|
{ |
547 |
|
|
try |
548 |
|
|
{ |
549 |
|
|
CloseServer(server); |
550 |
|
|
} |
551 |
|
|
finally |
552 |
|
|
{ |
553 |
|
|
// Catch exeception |
554 |
|
|
} |
555 |
|
|
} |
556 |
|
|
strError = ""; // Everything went ok |
557 |
|
|
} // end if (server != null) |
558 |
|
|
return strError; |
559 |
|
|
} |
560 |
|
|
|
561 |
|
|
// List all sessions on the terminal server and adds them to list with selected data for each session. |
562 |
|
|
// Returns error message or "" if everything went ok. |
563 |
|
|
public static string ListSessions(List<AtsSession> SessionInfo, String serverName) |
564 |
|
|
{ |
565 |
|
|
IntPtr server = IntPtr.Zero; |
566 |
|
|
server = OpenServer(serverName); |
567 |
|
|
string strError = "Could not retrieve session data from server '" + serverName + "'"; // Assume something went wrong |
568 |
|
|
if (server != IntPtr.Zero) |
569 |
|
|
{ |
570 |
|
|
try |
571 |
|
|
{ |
572 |
|
|
IntPtr ppSessionInfo = IntPtr.Zero; |
573 |
|
|
|
574 |
|
|
Int32 count = 0; |
575 |
|
|
Int32 retval = WTSEnumerateSessions(server, 0, 1, ref ppSessionInfo, ref count); |
576 |
|
|
Int32 dataSize = Marshal.SizeOf(typeof(WTS_SESSION_INFO)); |
577 |
|
|
Int32 current = (int)ppSessionInfo; |
578 |
|
|
|
579 |
|
|
if (retval != 0) |
580 |
|
|
{ |
581 |
|
|
for (int i = 0; i < count; i++) |
582 |
|
|
{ |
583 |
|
|
AtsSession currentSession = new AtsSession(); |
584 |
|
|
WTS_SESSION_INFO si = (WTS_SESSION_INFO)Marshal.PtrToStructure((System.IntPtr)current, typeof(WTS_SESSION_INFO)); |
585 |
|
|
current += dataSize; |
586 |
|
|
currentSession.TerminalServerName = serverName; |
587 |
|
|
currentSession.sessionID = si.SessionID; |
588 |
|
|
currentSession.ipAddress = GetTSClientAddress(si.SessionID, server); |
589 |
|
|
currentSession.name = GetTSClientName(si.SessionID, server); |
590 |
|
|
currentSession.username = GetTSUserName(si.SessionID, server); |
591 |
|
|
currentSession.state = si.State; |
592 |
|
|
if (currentSession.name != "") |
593 |
|
|
{ |
594 |
|
|
currentSession.macAddress = ProSupport.GetMacAddressFromNameAndDatabase(currentSession.name); |
595 |
|
|
} |
596 |
|
|
else |
597 |
|
|
{ |
598 |
|
|
currentSession.macAddress = ""; |
599 |
|
|
} |
600 |
|
|
GetTSClientDisplay( |
601 |
|
|
si.SessionID, |
602 |
|
|
server, |
603 |
|
|
out currentSession.HorizontalResolution, |
604 |
|
|
out currentSession.VerticalResolution, |
605 |
|
|
out currentSession.ColorDepth); |
606 |
|
|
|
607 |
|
|
SessionInfo.Add(currentSession); |
608 |
|
|
} |
609 |
|
|
|
610 |
|
|
WTSFreeMemory(ppSessionInfo); |
611 |
|
|
} |
612 |
|
|
} |
613 |
|
|
finally |
614 |
|
|
{ |
615 |
|
|
try |
616 |
|
|
{ |
617 |
|
|
CloseServer(server); |
618 |
|
|
} |
619 |
|
|
finally |
620 |
|
|
{ |
621 |
|
|
// Catch exeception |
622 |
|
|
} |
623 |
|
|
} |
624 |
|
|
strError = ""; // Everything went ok |
625 |
|
|
} // end if (server != null) |
626 |
|
|
|
627 |
|
|
return strError; |
628 |
|
|
} |
629 |
|
|
|
630 |
|
|
// Return matching session for a macAddress, or null, if the mac address is not used in any session. |
631 |
|
|
// Called when a child node selected in the tree view |
632 |
|
|
public static AtsSession GetSession(string macAddress) |
633 |
|
|
{ |
634 |
|
|
foreach (AtsTerminalServer ts in AtsEnvironment.TerminalServers) |
635 |
|
|
{ |
636 |
|
|
foreach (AtsSession session in ts.Session) |
637 |
|
|
{ |
638 |
|
|
// Try to find the MAC adress for the selected client in any of the sessions. |
639 |
|
|
if (session.macAddress == macAddress) |
640 |
|
|
{ |
641 |
|
|
return session; |
642 |
|
|
} |
643 |
|
|
} |
644 |
|
|
} |
645 |
|
|
// Session not found, return null. |
646 |
|
|
return null; |
647 |
|
|
} |
648 |
|
|
|
649 |
|
|
// Convert session state to string |
650 |
|
|
public static string StateToString(WTS_CONNECTSTATE_CLASS state) |
651 |
|
|
{ |
652 |
|
|
switch (state) |
653 |
|
|
{ |
654 |
|
|
case WTS_CONNECTSTATE_CLASS.WTSActive: |
655 |
|
|
return "User logged on"; |
656 |
|
|
case WTS_CONNECTSTATE_CLASS.WTSConnected: |
657 |
|
|
return "Connected to client"; |
658 |
|
|
case WTS_CONNECTSTATE_CLASS.WTSConnectQuery: |
659 |
|
|
return "Connecting to client"; |
660 |
|
|
case WTS_CONNECTSTATE_CLASS.WTSShadow: |
661 |
|
|
return "Shadowing"; |
662 |
|
|
case WTS_CONNECTSTATE_CLASS.WTSDisconnected: |
663 |
|
|
return "Logged on without client"; |
664 |
|
|
case WTS_CONNECTSTATE_CLASS.WTSIdle: |
665 |
|
|
return "Waiting for client to connect"; |
666 |
|
|
case WTS_CONNECTSTATE_CLASS.WTSListen: |
667 |
|
|
return "Listening for connection"; |
668 |
|
|
case WTS_CONNECTSTATE_CLASS.WTSReset: |
669 |
|
|
return "Being reset"; |
670 |
|
|
case WTS_CONNECTSTATE_CLASS.WTSDown: |
671 |
|
|
return "Down due to error"; |
672 |
|
|
case WTS_CONNECTSTATE_CLASS.WTSInit: |
673 |
|
|
return "In initialization"; |
674 |
|
|
default: |
675 |
|
|
return "Unknown state (error!)"; |
676 |
|
|
} |
677 |
|
|
} |
678 |
|
|
public static string GetMyName() |
679 |
|
|
{ |
680 |
|
|
return GetTSClientName(WTS_CURRENT_SESSION, System.IntPtr.Zero); |
681 |
|
|
} |
682 |
|
|
|
683 |
|
|
} // Class TSManager |
684 |
|
|
} // Namespace TerminalServices |