Retired Microsoft Blog disclaimer

This directory is a mirror of retired "Decrypt My World" MSDN blog and is provided as is. All posting authorship and copyrights belong to respective authors.

Posts on this page:

Original URL: https://blogs.msdn.microsoft.com/alejacma/2008/05/19/how-to-read-certificate-extensions-with-capicom-c/
Post name: How to read certificate extensions with CAPICOM (C#)
Original author: Alejandro Campos Magencio
Posting date: 2008-05-19T11:14:00+00:00


Hi all, welcome back,


I recently had a customer who needed to retrieveextensions from certificates the easy way in .NET 1.1, and they wanted to use CAPICOM for that. In .NET 2.0 and later we may use X509Certificate2to achieve the same results (I strongly recommend this approach), but in .NET 1.1 we only have X509Certificate class which is much more limited.


Note that the same ideas shown in the same below may be taken into account when using CAPICOM from i.e. VBScript.


The following sample shows how to use CAPICOM from a C# app to read a couple of extensions froma test cert(remember to add CAPICOM as a reference to the project first):

using CAPICOM;

...

// Load the cert
Certificate CAPICOMCertClass = new CertificateClass();
CAPICOMCertClass.Load("C:\\test.cer", null, CAPICOM_KEY_STORAGE_FLAG.CAPICOM_KEY_STORAGE_DEFAULT, CAPICOM_KEY_LOCATION.CAPICOM_CURRENT_USER_KEY);

// Find the extensions we are interested in
foreach (Extension CertExtension in CAPICOMCertClass.Extensions())
{

// Does the extension have a Friendly Name? Yes? Use it!
if (CertExtension.OID.FriendlyName == "Subject Alternative Name")
{
String stringSubjectAltName = CertExtension.EncodedData.Format(true);
MessageBox.Show(stringSubjectAltName);
}

// The extension has no Friendly Name, but we can use its OID instead
if (CertExtension.OID.Value.ToString() == "1.3.6.1.4.1.5734.1.33")
{
// For demostration purposes of Utilities class, let's assume the value of the OID is an hex string which represents the chars of a string but we need the string itself

// This property is in Hexadecimal
String stringOIDHex = CertExtension.EncodedData.Format(true).Replace(" ", "");

// We convert it to binary
Utilities utils = new UtilitiesClass();
String stringOIDBinary = utils.HexToBinary(stringOIDHex);
byte[] OIDBinary = (byte[])utils.BinaryStringToByteArray(stringOIDBinary);

// We convert it to string
String stringOID = System.Text.Encoding.ASCII.GetString(OIDBinary);
MessageBox.Show(stringOID);
}
}



References to the classes I've used: Certificate,Extensions, Extension, OID,Utilities.


I hope this helps.


Cheers,



Alex (Alejandro Campos Magencio)

Original URL: https://blogs.msdn.microsoft.com/alejacma/2008/05/12/how-to-get-antivirus-information-with-wmi-vbscript/
Post name: How to get Antivirus information with WMI (VBScript)
Original author: Alejandro Campos Magencio
Posting date: 2008-05-12T05:23:00+00:00


Hi all, welcome back,


As we read in Windows Security Center – Managing the State of Security, the vast majority of antivirus Independent Software Vendors (ISVs) support WMI integration. Windows Security Center uses it to detect antivirus and firewall solutions.


The following script shows how to get some information from those solutions:

strComputer = "."

Set oWMI = GetObject( _
"winmgmts:{impersonationLevel=impersonate}!\\" & strComputer & "\root\SecurityCenter")

Set colItems = oWMI.ExecQuery("Select * from AntiVirusProduct")

For Each objItem in colItems
With objItem
WScript.Echo .companyName
WScript.Echo .displayName
WScript.Echo .instanceGuid
WScript.Echo .onAccessScanningEnabled
WScript.Echo .pathToSignedProductExe
WScript.Echo .productHasNotifiedUser
WScript.Echo .productState
WScript.Echo .productUptoDate
WScript.Echo .productWantsWscNotifications
WScript.Echo .versionNumber
End With
Next


Cheers,



Alex (Alejandro Campos Magencio)

Original URL: https://blogs.msdn.microsoft.com/alejacma/2008/04/29/changepassword-method-may-fail-with-targetinvocationexception-net/
Post name: ChangePassword method may fail with TargetInvocationException (.NET)
Original author: Alejandro Campos Magencio
Posting date: 2008-04-29T04:03:00+00:00


Hi all, welcome back,


When working with System.DirectoryServices.DirectoryEntry in .NET, we may change the password of the user with a code like the following (C#):

user.Invoke("ChangePassword", new object[] { oldPassword, newPassword }

But invoking ChangePassword may fail with the following System.Reflection.TargetInvocationException:


"Exception has been thrown by the target of an invocation"


This error is not very descriptive, I know. I've seen several causes for this error in the past:


1) Any of the passwords is incorrect.


2) The new password doesn't meet the domain complexity requirements.


3) Minimum Password Age is > 0.


4) WinNT provider is used instead of LDAP.



By using InnerException.ToString() from the TargetInvocationException we may get a more descriptive error message. We could even see the HResult value associated to the exception. But this property is protected, so we could try to parse it from the error message string, with a code like this:

string errorMessage;
Int32 errorCode = 0;
try
{
...
}
catch (TargetInvocationException e)
{
errorMessage = e.InnerException.ToString();
try
{
string HResult = errorMessage.Substring(errorMessage.IndexOf("0x") + 2, 8);
errorCode = Int32.Parse(HResult, System.Globalization.NumberStyles.HexNumber);
}
catch
{
errorCode = -1;
}
}


I hope this helps.


Cheers,



Alex (Alejandro Campos Magencio)

Original URL: https://blogs.msdn.microsoft.com/alejacma/2008/04/23/how-to-get-a-list-of-all-users-in-an-ou-vbscript/
Post name: How to get a list of all users in an OU (VBScript)
Original author: Alejandro Campos Magencio
Posting date: 2008-04-23T11:44:00+00:00


Hi all, welcome back,


Today I'll post a very straight forward sample which gets a list of all users in an Organizational Unit (OU) in Active Directory (AD) using VBScript:

' Get OU
'
strOU = "OU=Users,DC=domain,DC=com"

' Create connection to AD
'
Set objConnection = CreateObject("ADODB.Connection")
objConnection.Open "Provider=ADsDSOObject;"

' Create command
'
Set objCommand = CreateObject("ADODB.Command")
objCommand.ActiveConnection = objConnection
objCommand.Properties("Page Size") = 1000

' Execute command to get all users in OU
'
objCommand.CommandText = _
"<LDAP://" & strOU & ">;" & _
"(&(objectclass=user)(objectcategory=person));" & _
"adspath,distinguishedname,sAMAccountName;subtree"
Set objRecordSet = objCommand.Execute

' Show info for each user in OU
'
Do Until objRecordSet.EOF

' Show required info for a user
'
WScript.Echo objRecordSet.Fields("adspath").Value
WScript.Echo objRecordSet.Fields("distinguishedname").Value
WScript.Echo objRecordSet.Fields("sAMAccountName").Value

' Move to the next user
'
objRecordSet.MoveNext

Loop

' Clean up
'
objRecordSet.Close
Set objRecordSet = Nothing
Set objCommand = Nothing
objConnection.Close
Set objConnection = Nothing



I hope this helps.


Regards,



Alex (Alejandro Campos Magencio)

Original URL: https://blogs.msdn.microsoft.com/alejacma/2008/04/21/dpapiprotectedconfigurationprovider-fails-while-decrypting-web-config-asp-net/
Post name: DpapiProtectedConfigurationProvider fails while decrypting web.config (ASP.NET)
Original author: Alejandro Campos Magencio
Posting date: 2008-04-21T10:04:00+00:00


Hi, welcome back,

The other day wefaced a very similar issue to the one I commented on this post: RSACryptoServiceProvider fails when used with ASP.NET. We were getting a very similar exception:

"System.Configuration.ConfigurationErrorsException: Failed to decrypt using provider 'MyProtectedConfigurationProvider'. Error message from the provider: The system cannot find the file specified. (Exception from HRESULT: 0x80070002)"

But this time we got it while System.Configuration.DpapiProtectedConfigurationProvider was trying to decrypt a protected configuration section of our web.config file. This provider was configured to work with user-level key storage (DpapiProtectedConfigurationProvider.UseMachineProtection set to False) but the user profile was not loaded.

"The system cannot find the file specified" is a very typical error that appears when we can't access the private key we need to decrypt information, as those keys are usually stored in files in the user profile.

Additionally, if DPAPI works with user-level key storage, it requires the user profile to be loaded in order to store i.e. the master key it uses (see Windows Data Protection for details on this).

As we saw already (check previous RSACryptoServiceProvider post for details), neither IIS nor ASP.NET will load the profile automatically. We may be able to load it by calling LoadUserProfile API or by using a dummy Windows Service (and Service Control Manager -SCM-will load the profile on our behalf). If this doesn't work for us, we will have to use machine-level key storage instead.

I hope this helps.

Cheers,

Alex (Alejandro Campos Magencio)