在我的组织中,用户必须使用SmartCard交互式登录Windows工作站(95,Vista和7)。几乎每天,我们都需要读取存储在SmartCard中的凭据,并与ActiveDirectory进行比较,而无需实现自定义凭据管理器。我们比较的字段是:userPrincialName和sAMAccountName。

您能否给我看一个代码,以演示如何从SmartCard中读取凭据,或引导我阅读Internet上的文章/代码?

互联网上的搜索建议实施凭据管理器或使用其他语言(例如C,C ++)。
另外,我遇​​到了由orouit撰写的http://www.codeproject.com/Articles/17013/Smart-Card-Framework-for-NET文章,这是使用SmartCard的框架-但对于我的简单任务来说,我认为太多了。你怎么看?

最佳答案

好吧,如果在Windows下进行开发,则一旦插入智能卡,窗口就会从智能卡中获取所有证书,并将它们放置到“我的证书”存储中。

var smartCardCerts = new List<X509Certificate2>();
var myStore = new X509Store(StoreName.My, StoreLocation.CurrentUser);
foreach(X509Certificate2 cert in myStore)
{
  if( !cert.HasPrivateKey ) continue; // not smartcard for sure
  var rsa = cert.PrivateKey as RSACryptoServiceProvider;
  if( rsa==null ) continue; // not smart card cert again
  if( rsa.CspKeyContainerInfo.HardwareDevice ) // sure - smartcard
  {
     // inspect rsa.CspKeyContainerInfo.KeyContainerName Property
     // or rsa.CspKeyContainerInfo.ProviderName (your smartcard provider, such as
     // "Schlumberger Cryptographic Service Provider" for Schlumberger Cryptoflex 4K
     // card, etc
     var name = cert.Name;
     rsa.SignData(); // to confirm presence of private key - to finally authenticate
  }
}


如今,基本上可以通过.NET使用很多加密API。但是您也可以直接使用API​​ Crypto API

例如您可以直接通过访问智能卡

CryptAcquireContext(&hProv,"\\.\<Reader Name>\<Container Name>",...)


读卡器名称是读卡器名称,容器名称是上面代码片段中的rsa.KeyContainerName。可以通过多种方式来访问此类信息,并且Crypto API并不是非常一致或简单。提示.NET版本的CryptAcquireContext是带有CspParameters的RSACryptoServiceProvider,您可以在需要时指定容器名称。

可以通过System.DirectoryServices.DirectoyEntry和System.DirectoryServices.DirectorySearcher来在ActiveDirectory中找到用户,但是不要忘记System.DirectoryServices.ActiveDirectory.Forest和相关的API,这使某些事情变得容易得多。

您将能够得到

09-04 03:04