问题
How can I detect if my Swing App is being run from a windows RDP session?
Java only solution preferred, but the app is guaranteed to be running on windows so I'm ok with shelling out.
回答1:
I think you'll have to invoke the native Windows libraries to pull this off. Try something like this:
import com.sun.jna.Library;
import com.sun.jna.Native;
import com.sun.jna.ptr.IntByReference;
import com.sun.jna.win32.*;
import com.sun.jna.examples.win32.Kernel32;
...
public static boolean isLocalSession() {
Kernel32 kernel32;
IntByReference pSessionId;
int consoleSessionId;
Kernel32 lib = (Kernel32) Native.loadLibrary("kernel32", Kernel32.class);
pSessionId = new IntByReference();
if (lib.ProcessIdToSessionId(lib.GetCurrentProcessId(), pSessionId)) {
consoleSessionId = lib.WTSGetActiveConsoleSessionId();
return (consoleSessionId != 0xFFFFFFFF && consoleSessionId == pSessionId.getValue());
} else return false;
}
That strange-looking condition for consoleSessionId
is from the documentation for WTSGetActiveConsoleSessionId, which says:
Return Value
The session identifier of the session that is attached to the physical console. If there is no session attached to the physical console, (for example, if the physical console session is in the process of being attached or detached), this function returns 0xFFFFFFFF.
回答2:
The above answers might work, but seem needlessly complicated. You can simply read the windows 'sessionname' environment variable to detect RDP sessions. The value of this environment variable will be 'Console' for a normal, local session. For an RDP session it will contain the phrase 'RDP'. It's easy enough just to check for that.
public static boolean isRemoteDesktopSession() {
System.getenv("sessionname").contains("RDP");
}
Tested and confirmed working under Windows7 64bit. One issue I have noticed with this technique is that it appears that environment variable values as read from System.getenv() do not change once the JVM has started. So if the JVM process was started by a console session, but then accessed by an RDP session, further calls to System.getenv("sessionname") still return 'Console.'
回答3:
Try with NativeCall ( http://johannburkard.de/software/nativecall/ )
All you need is 2 jars plus 1 DLL in your classpath.
A quick test :
import java.io.IOException;
import com.eaio.nativecall.*;
public class WindowsUtils {
public static final int SM_REMOTESESSION = 4096; // remote session
public static boolean isRemote() throws SecurityException, UnsatisfiedLinkError,
UnsupportedOperationException, IOException
{
NativeCall.init();
IntCall ic = null;
ic = new IntCall("user32", "GetSystemMetrics");
int rc = ic.executeCall(new Integer(SM_REMOTESESSION));
if (ic != null) ic.destroy();
return (rc > 0);
}
public static void main(String ... args) throws Exception {
System.out.println(WindowsUtils.isRemote());
}
}
来源:https://stackoverflow.com/questions/2015193/determine-if-java-app-is-being-run-over-an-rdp-session