代码之家  ›  专栏  ›  技术社区  ›  Allain Lalonde

确定Java应用程序是否正在RDP会话上运行?

  •  2
  • Allain Lalonde  · 技术社区  · 16 年前

    如何检测我的Swing应用程序是否正在从windows RDP会话运行?

    3 回复  |  直到 16 年前
        1
  •  4
  •   John Feminella    16 年前

    我认为您必须调用本机Windows库才能实现这一点。试着这样做:

    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;
    }
    

    这种奇怪的情况 consoleSessionId WTSGetActiveConsoleSessionId ,上面写着:

    连接到物理控制台的会话的会话标识符。如果没有会话连接到物理控制台(例如,如果物理控制台会话正在连接或分离),此函数将返回0xFFFFFF。

        2
  •  4
  •   Kirk Woll    15 年前

    上述答案可能有效,但似乎不必要地复杂。您只需读取windows“sessionname”环境变量即可检测RDP会话。对于正常的本地会话,此环境变量的值将为“Console”。对于RDP会话,它将包含短语“RDP”。检查一下就很容易了。

    public static boolean isRemoteDesktopSession() {
       System.getenv("sessionname").contains("RDP");
    }
    

    已测试并确认在Windows7 64位下工作。我注意到这种技术的一个问题是,从System.getenv()读取的环境变量值在JVM启动后似乎不会改变。因此,如果JVM进程由控制台会话启动,但随后由RDP会话访问,则对System.getenv(“sessionname”)的进一步调用仍然返回“console”

        3
  •  1
  •   RealHowTo    16 年前

    http://johannburkard.de/software/nativecall/ )

    您只需要在类路径中添加2个JAR和1个DLL。

    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());
      }
    }