This is the first .NET-based framework used to create custom ADCS CA and NDES modules, such as exit and policy.
Exit module is a module that subscribes to desired events generated by CA engine and then notified by CA on event occurence.
Policy module is a module that allows to override or add extra logic on how requests are processed and modify them if needed.
Use NuGet to download the library and attach to your .NET project:
NuGet\Install-Package ADCS.CertMod.Managed
Two interfaces must be implemented and exposed to COM world in order to create an exit module:
ICertManageModuleICertExit2
Create a class that inherits from CertManageModule class and define the following attributes:
[ComVisible(true)]
[ClassInterface(ClassInterfaceType.None)]
[ProgId("<ModuleName>.ExitManage")]
[Guid("<00000000-0000-0000-0000-000000000000>")]
public class ExitManage : CertManageModule {
<...>
public override Object GetProperty(String strConfig, String strStorageLocation, String strPropertyName, Int32 Flags) {
// implementation goes here.
}
<...>
}<ModuleName>is module simple name. The full ProgID must look likeMyCoolExitModule.ExitManage. ProgID and CLR class name are not required to match.<00000000-0000-0000-0000-000000000000>is a randomly generated UUID that identifies your implementation.- At a minimum, only
CertManageModule.GetPropertymethod must be overriden.
Note: angle brackets are used for reference only, they are not used.
Create a class that inherits from CertExitBase class (which already implements ICertExit2 interface) and define the following attributes and method overrides:
[ComVisible(true)]
[ClassInterface(ClassInterfaceType.None)]
[ProgId("<ModuleName>.Exit")]
[Guid("<00000000-0000-0000-0000-000000000000>")]
public class MyExitClass : CertExitBase {
<...>
// implement public 'Initialize' method
public override ExitEvents Initialize(String strConfig) {
// exit module initialization logic goes here
}
// implement protected 'Notify' method with your business logic:
protected override void Notify(CertServerModule certServer, ExitEvents ExitEvent, Int32 Context) {
// exit module business logic goes here.
}
<...>
}<ModuleName>is module simple name. The full ProgID must look likeMyCoolExitModule.Exit, where.Exitsuffix is mandatory.<00000000-0000-0000-0000-000000000000>is a randomly generated UUID that identifies your implementation.ICertExit2.GetManageModulereturns an instance ofICertManageModuleimplementation (see above).
Two interfaces must be implemented and exposed to COM world in order to create an exit module:
ICertManageModuleICertPolicy2, or inherit fromCertPolicyBaseclass directly which provides some base implementation for you.
See section above.
Create a class that inherits from CertPolicyBase class (which already implements ICertPolicy2 interface) and define the following attributes and method overrides:
[ComVisible(true)]
[ClassInterface(ClassInterfaceType.None)]
[ProgId("<ModuleName>.Policy")]
[Guid("<00000000-0000-0000-0000-000000000000>")]
public class MyPolicyClass : CertPolicyBase {
<...>
// implement protected 'VerifyRequest' method with your business logic:
protected override PolicyModuleAction VerifyRequest(CertServerModule certServer, PolicyModuleAction nativeResult, Boolean bNewRequest) {
// policy module business logic goes here
}
<...>
}<ModuleName>is module simple name. The full ProgID must look likeMyCoolPolicyModule.Policy, where.Policysuffix is mandatory.<00000000-0000-0000-0000-000000000000>is a randomly generated UUID that identifies your implementation.ICertPolicy2.GetManageModulereturns an instance ofICertManageModuleimplementation (see above).
INDESPolic interface must be implemented and exposed to COM world in order to create NDES policy module.\
Create a class that inherits from NdesPolicy base (which already implements INDESPolicy interface) and define the following attributes:
[ComVisible(true)]
[ClassInterface(ClassInterfaceType.None)]
[ProgId("<ModuleName>.Policy")]
[Guid("<00000000-0000-0000-0000-000000000000>")]
public class MyNdesPolicyModule : NdesPolicyBase {
public MyNdesPolicyModule() : base(
new LogWriter("MyModule"),
new DefaultSCEPChallengeStore(new DefaultSCEPChallengeGenerator())) {
// my other implementation-specific code if needed
}
// <...> the rest of implementation is omitted for brevity
}<ModuleName>is module simple name. The full ProgID must look likeMyNdesModule.ProgID, where.Policysuffix is mandatory.<00000000-0000-0000-0000-000000000000>is a randomly generated UUID that identifies your implementation.
See this PR for more details on NDES policy module.