【问题标题】:Windows authentication token C++Windows 身份验证令牌 C++
【发布时间】:2012-02-21 15:28:56
【问题描述】:

简单地说:我可以在 C++ 中生成当前登录的 Windows 用户的某种文本信息 - 用户令牌、会话令牌、访问令牌(?),然后在某处验证此文本信息(验证用户)其他(域中的不同计算机)?

我有两台电脑。在第一个用户应该能够通过客户端应用程序连接到我在第二台计算机上运行的服务器应用程序。他必须使用 Windows 身份验证,因此服务器将使用他的 Windows 组获取一些信息 - 不发送用户名/密码。我的想法是(不知道是否可能)客户端计算机/进程知道当前用户,因此它将获取用户的访问令牌或类似的东西,将其传递给服务器(作为字符串参数),服务器将验证这个令牌字符串是有效的,并且会得到那个 windows 用户的名字和他的组来进行下一步操作,这就是我所需要的。

这是否可能仅使用从客户端发送到服务器的一个信息(此访问令牌/会话令牌或如何调用)? (http服务器,我只想通过一个登录请求发送该字符串令牌一次,该登录请求当前用于其他专有的身份验证方式,如果可能的话,没有握手/协商或类似的东西)。我正在使用 C++。

我目前找到了两种方法(可能是如何不做的方法;))

1) OpenProcessToken、GetTokenInformation 等函数 - 这让我可以访问访问令牌,但它只是句柄,我可能只能在我的进程中使用它,无法将其发送到其他地方...

2) AcquireCredentialsHandle、InitializeSecurityContext、AcquireSecurityContext 等函数 - 今天我花了很多时间在这上面 - 我使用这些函数制作了一些测试应用程序,只是在一个进程中运行,我目前不确定应该如何制作通过两台计算机之间的“文本”通信,但这并不重要 - 似乎必须进行更多轮次 - 客户端创建一些东西(上下文,凭据,令牌,......),将其发送到服务器,服务器做一些事情,回复客户端,客户端获取结果等。我可以通过创建“会话令牌”并发送它(例如,如有必要使用 domain@username)而不需要其他信息来回发送它吗?

任何帮助表示赞赏,谢谢!

编辑:基于下面的第一个 cmets,我似乎需要进一步澄清这一点: 想象一下用户运行 Web 浏览器并连接到我在其他地方的服务器应用程序。他想发送诸如“CONNECT”和“DO_STUFF”之类的命令。仅当此用户可以先连接时,服务器应用程序才会 do_stuff。但是这个用户只有在它是某个 windows 组的成员时才能连接(使用 windows 身份验证,而不是某些专有用户和密码)。所以服务器必须检查这个用户是否是该组的有效成员。但是服务器当然可以仅根据用户提供的文本信息来完成。好吧,用户可以发送他的 Windows 用户名和密码以通过服务器应用程序进行身份验证(应该由 C++ 函数 LogonUser 或其他任何方式完成),但这很危险,我不希望用户在某处输入他的用户名和密码,我只想要他到“点击登录按钮”,C++会关心其余的,因为它可以检查他当前的会话数据,他已经登录了。我的想法只是提供用户名和某种字符串用户令牌(会话令牌,访问令牌,我不知道确切的术语)将由用户客户端应用程序(使用 Kerberos,NTLM,我不知道)生成,服务器将接收此字符串信息,它将检查此令牌以验证“这是有效的有效 Windows 用户的令牌,这是他所属的组”......类似的东西。希望这个解释有所帮助。

【问题讨论】:

  • 我假设您已经考虑过远程桌面/RDP 但它不起作用?
  • 使用远程桌面是什么意思?这是 C++ 编写的应用程序,它将根据用户登录的不同计算机上的客户端应用程序提供的信息对用户进行身份验证。我需要从客户端应用程序获取一些信息以允许登录到服务器应用程序(例如,如果用户在一些特殊的 Windows 组使其变得简单)。我不想发送 win 用户名和 win 密码,我想发送 win 用户名和 win 令牌。
  • 好的,它是 C#,但这听起来像你可能正在尝试的:stackoverflow.com/questions/288796/…
  • 我还是觉得我们不了解对方。我在最初问题的末尾添加了新的详细信息。
  • 简单地说:我可以在 C++ 中生成当前登录的 Windows 用户的某种文本信息 - 用户令牌 - 然后在其他地方(域中的不同计算机)验证此文本信息(验证用户)吗?

标签: c++ windows-authentication


【解决方案1】:

AcquireCredentialsHandle、InitializeSecurityContext、AcceptSecurityContext 等函数是这里的解决方案。

查看http://msdn.microsoft.com/en-us/library/ms973911.aspx#remsspi_topic3

如果你只想对用户进行身份验证,NTLM 是可以的,但是你需要交换多条消息,不能像我最初要求的那样一步完成(需要:协商、挑战、响应),所以你是实际上发送了 3 条短信并通过上述功能进行处理。

如果您想委托(服务器可以充当客户端 - 模拟 - 甚至将权限委托给其他进程),您需要使用 Kerberos(需要 Active Directory)。一切都必须在一个域中完成。这可能可以通过根据下图从客户端向服务器发送更少的消息来实现,因为权限涉及更多,但我没有测试过这种场景。


(来源:microsoft.com

【讨论】:

    猜你喜欢
    • 2017-10-22
    • 1970-01-01
    • 2017-06-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-02-17
    • 1970-01-01
    相关资源
    最近更新 更多