#ifndef _NTTMAPI_H
NTSYSCALLAPI
NTSTATUS
NTAPI
NtCreateEnlistment(
_Out_ PHANDLE EnlistmentHandle,
_In_ ACCESS_MASK DesiredAccess,
_In_ HANDLE ResourceManagerHandle,
_In_ HANDLE TransactionHandle,
_In_opt_ POBJECT_ATTRIBUTES ObjectAttributes,
_In_opt_ ULONG CreateOptions,
_In_ NOTIFICATION_MASK NotificationMask,
_In_opt_ PVOID EnlistmentKey
);
View code on GitHub#ifndef _NTZWAPI_H
NTSYSCALLAPI
NTSTATUS
NTAPI
ZwCreateEnlistment(
_Out_ PHANDLE EnlistmentHandle,
_In_ ACCESS_MASK DesiredAccess,
_In_ HANDLE ResourceManagerHandle,
_In_ HANDLE TransactionHandle,
_In_opt_ POBJECT_ATTRIBUTES ObjectAttributes,
_In_opt_ ULONG CreateOptions,
_In_ NOTIFICATION_MASK NotificationMask,
_In_opt_ PVOID EnlistmentKey
);
View code on GitHub// wdm.h
__kernel_entry NTSYSCALLAPI NTSTATUS NtCreateEnlistment(
[out] PHANDLE EnlistmentHandle,
[in] ACCESS_MASK DesiredAccess,
[in] HANDLE ResourceManagerHandle,
[in] HANDLE TransactionHandle,
[in, optional] POBJECT_ATTRIBUTES ObjectAttributes,
[in, optional] ULONG CreateOptions,
[in] NOTIFICATION_MASK NotificationMask,
[in, optional] PVOID EnlistmentKey
);
View the official Windows Driver Kit DDI reference// wdm.h
NTSYSCALLAPI NTSTATUS ZwCreateEnlistment(
[out] PHANDLE EnlistmentHandle,
[in] ACCESS_MASK DesiredAccess,
[in] HANDLE ResourceManagerHandle,
[in] HANDLE TransactionHandle,
[in, optional] POBJECT_ATTRIBUTES ObjectAttributes,
[in, optional] ULONG CreateOptions,
[in] NOTIFICATION_MASK NotificationMask,
[in, optional] PVOID EnlistmentKey
);
View the official Windows Driver Kit DDI referenceThe ZwCreateEnlistment routine creates a new enlistment object for a transaction.
EnlistmentHandle [out]A pointer to a caller-allocated variable that receives a handle to the new enlistment object if the call to ZwCreateEnlistment succeeds.
DesiredAccess [in]An ACCESS_MASK value that specifies the caller's requested access to the enlistment object. In addition to the access rights that are defined for all kinds of objects (see ACCESS_MASK), the caller can specify any of the following access right flags for enlistment objects:
| ACCESS_MASK flag | Allows the caller to |
|---|---|
| ENLISTMENT_QUERY_INFORMATION | Query information about the enlistment (see ZwQueryInformationEnlistment). |
| ENLISTMENT_SET_INFORMATION | Set information for the enlistment (see ZwSetInformationEnlistment). |
| ENLISTMENT_RECOVER | Recover the enlistment (see ZwRecoverEnlistment). |
| ENLISTMENT_SUBORDINATE_RIGHTS | Perform operations that a resource manager that is not superior performs (see ZwRollbackEnlistment, ZwPrePrepareComplete, ZwPrepareComplete, ZwCommitComplete, ZwRollbackComplete, ZwSinglePhaseReject, ZwReadOnlyEnlistment). |
| ENLISTMENT_SUPERIOR_RIGHTS | Perform operations that a superior transaction manager must perform (see ZwPrepareEnlistment, ZwPrePrepareEnlistment, ZwCommitEnlistment). |
Alternatively, you can specify one or more of the following ACCESS_MASK bitmaps. These bitmaps combine the flags from the previous table with the STANDARD_RIGHTS_XXX flags that are described on the ACCESS_MASK reference page. You can also combine these bitmaps together with additional flags from the previous table. The following table shows how the bitmaps correspond to specific access rights.
| Generic access right | Set of specific access rights |
|---|---|
| ENLISTMENT_GENERIC_READ | STANDARD_RIGHTS_READ and ENLISTMENT_QUERY_INFORMATION |
| ENLISTMENT_GENERIC_WRITE | STANDARD_RIGHTS_WRITE, ENLISTMENT_SET_INFORMATION, ENLISTMENT_RECOVER, ENLISTMENT_REFERENCE, ENLISTMENT_SUBORDINATE_RIGHTS, and ENLISTMENT_SUPERIOR_RIGHTS |
| ENLISTMENT_GENERIC_EXECUTE | STANDARD_RIGHTS_EXECUTE, ENLISTMENT_RECOVER, ENLISTMENT_SUBORDINATE_RIGHTS, and ENLISTMENT_SUPERIOR_RIGHTS |
| ENLISTMENT_ALL_ACCESS | STANDARD_RIGHTS_REQUIRED, ENLISTMENT_GENERIC_READ, ENLISTMENT_GENERIC_WRITE, and ENLISTMENT_GENERIC_EXECUTE |
ResourceManagerHandle [in]A handle to the caller's resource manager object that was obtained by a previous call to ZwCreateResourceManager or ZwOpenResourceManager.
TransactionHandle [in]A handle to a transaction object that was obtained by a previous call to ZwCreateTransaction or ZwOpenTransaction. KTM adds this transaction to the list of transactions that the calling resource manager is handling.
ObjectAttributes [in, optional]A pointer to an OBJECT_ATTRIBUTES structure that specifies the object name and other attributes. Use the InitializeObjectAttributes routine to initialize this structure. If the caller is not running in a system thread context, it must set the OBJ_KERNEL_HANDLE attribute when it calls InitializeObjectAttributes. This parameter is optional and can be NULL.
CreateOptions [in, optional]Enlistment option flags. The following table contains the only available flag.
| CreateOptions flag | Meaning |
|---|---|
| ENLISTMENT_SUPERIOR | The caller is enlisting as a superior transaction manager for the specified transaction. |
This parameter is optional and can be zero.
NotificationMask [in]A bitwise OR of TRANSACTION_NOTIFY_XXX values that are defined in Ktmtypes.h. This mask specifies the types of transaction notifications that KTM sends to the caller.
EnlistmentKey [in, optional]A pointer to caller-defined information that uniquely identifies the enlistment. The resource manager receives this pointer when it calls ZwGetNotificationResourceManager or when KTM calls the ResourceManagerNotification callback routine. The resource manager can maintain a reference count for this key by calling TmReferenceEnlistmentKey and TmDereferenceEnlistmentKey. This parameter is optional and can be NULL.
ZwCreateEnlistment returns STATUS_SUCCESS if the operation succeeds. Otherwise, this routine might return one of the following values:
| Return code | Description |
|---|---|
| STATUS_INVALID_HANDLE | An object handle is invalid. |
| STATUS_INVALID_PARAMETER | The CreateOptions or NotificationMask parameter's value is invalid, or KTM could not find the transaction that the TransactionHandle parameter specifies. |
| STATUS_INSUFFICIENT_RESOURCES | A memory allocation failed. |
| STATUS_TRANSACTIONMANAGER_NOT_ONLINE | The enlistment failed because KTM or the resource manager is not in an operational state. |
| STATUS_TRANSACTION_NOT_ACTIVE | The enlistment failed because the transaction that the TransactionHandle parameter specifies is not active. |
| STATUS_TRANSACTION_SUPERIOR_EXISTS | The caller tried to register as a superior transaction manager but a superior transaction manager already exists. |
| STATUS_TM_VOLATILE | The caller is trying to register as a superior transaction manager, but the caller's resource manager object is volatile while the associated transaction manager object is not volatile. |
| STATUS_ACCESS_DENIED | The value of the DesiredAccess parameter is invalid. |
The routine might return other NTSTATUS values.
A resource manager calls ZwCreateEnlistment to enlist in a transaction.
Resource managers that are not superior must include the ENLISTMENT_SUBORDINATE_RIGHTS flag in their access mask.
Superior transaction managers must include the ENLISTMENT_SUPERIOR_RIGHTS flag in their access masks. Typically, a superior transaction manager includes code that calls ZwRollbackEnlistment, so it must also include the ENLISTMENT_SUBORDINATE_RIGHTS flag.
A resource manager that calls ZwCreateEnlistment must eventually call ZwClose to close the object handle.
Your resource manager can use the EnlistmentKey parameter to assign a unique value to each enlistment, such as a pointer to a data structure that contains information about the enlistment. For example, if the resource manager stores the enlistment object's handle in the structure, the resource manager can do the following:
For more information about ZwCreateEnlistment, see Creating a Resource Manager and Creating a Superior Transaction Manager.
For calls from kernel-mode drivers, the Nt*Xxx* and Zw*Xxx* versions of a Windows Native System Services routine can behave differently in the way that they handle and interpret input parameters. For more information about the relationship between the Nt*Xxx* and Zw*Xxx* versions of a routine, see Using Nt and Zw Versions of the Native System Services Routines.
Using Nt and Zw Versions of the Native System Services Routines
ZwGetNotificationResourceManager
The ZwCreateEnlistment routine creates a new enlistment object for a transaction.
EnlistmentHandle [out]A pointer to a caller-allocated variable that receives a handle to the new enlistment object if the call to ZwCreateEnlistment succeeds.
DesiredAccess [in]An ACCESS_MASK value that specifies the caller's requested access to the enlistment object. In addition to the access rights that are defined for all kinds of objects (see ACCESS_MASK), the caller can specify any of the following access right flags for enlistment objects:
| ACCESS_MASK flag | Allows the caller to |
|---|---|
| ENLISTMENT_QUERY_INFORMATION | Query information about the enlistment (see ZwQueryInformationEnlistment). |
| ENLISTMENT_SET_INFORMATION | Set information for the enlistment (see ZwSetInformationEnlistment). |
| ENLISTMENT_RECOVER | Recover the enlistment (see ZwRecoverEnlistment). |
| ENLISTMENT_SUBORDINATE_RIGHTS | Perform operations that a resource manager that is not superior performs (see ZwRollbackEnlistment, ZwPrePrepareComplete, ZwPrepareComplete, ZwCommitComplete, ZwRollbackComplete, ZwSinglePhaseReject, ZwReadOnlyEnlistment). |
| ENLISTMENT_SUPERIOR_RIGHTS | Perform operations that a superior transaction manager must perform (see ZwPrepareEnlistment, ZwPrePrepareEnlistment, ZwCommitEnlistment). |
Alternatively, you can specify one or more of the following ACCESS_MASK bitmaps. These bitmaps combine the flags from the previous table with the STANDARD_RIGHTS_XXX flags that are described on the ACCESS_MASK reference page. You can also combine these bitmaps together with additional flags from the previous table. The following table shows how the bitmaps correspond to specific access rights.
| Generic access right | Set of specific access rights |
|---|---|
| ENLISTMENT_GENERIC_READ | STANDARD_RIGHTS_READ and ENLISTMENT_QUERY_INFORMATION |
| ENLISTMENT_GENERIC_WRITE | STANDARD_RIGHTS_WRITE, ENLISTMENT_SET_INFORMATION, ENLISTMENT_RECOVER, ENLISTMENT_REFERENCE, ENLISTMENT_SUBORDINATE_RIGHTS, and ENLISTMENT_SUPERIOR_RIGHTS |
| ENLISTMENT_GENERIC_EXECUTE | STANDARD_RIGHTS_EXECUTE, ENLISTMENT_RECOVER, ENLISTMENT_SUBORDINATE_RIGHTS, and ENLISTMENT_SUPERIOR_RIGHTS |
| ENLISTMENT_ALL_ACCESS | STANDARD_RIGHTS_REQUIRED, ENLISTMENT_GENERIC_READ, ENLISTMENT_GENERIC_WRITE, and ENLISTMENT_GENERIC_EXECUTE |
ResourceManagerHandle [in]A handle to the caller's resource manager object that was obtained by a previous call to ZwCreateResourceManager or ZwOpenResourceManager.
TransactionHandle [in]A handle to a transaction object that was obtained by a previous call to ZwCreateTransaction or ZwOpenTransaction. KTM adds this transaction to the list of transactions that the calling resource manager is handling.
ObjectAttributes [in, optional]A pointer to an OBJECT_ATTRIBUTES structure that specifies the object name and other attributes. Use the InitializeObjectAttributes routine to initialize this structure. If the caller is not running in a system thread context, it must set the OBJ_KERNEL_HANDLE attribute when it calls InitializeObjectAttributes. This parameter is optional and can be NULL.
CreateOptions [in, optional]Enlistment option flags. The following table contains the only available flag.
| CreateOptions flag | Meaning |
|---|---|
| ENLISTMENT_SUPERIOR | The caller is enlisting as a superior transaction manager for the specified transaction. |
This parameter is optional and can be zero.
NotificationMask [in]A bitwise OR of TRANSACTION_NOTIFY_XXX values that are defined in Ktmtypes.h. This mask specifies the types of transaction notifications that KTM sends to the caller.
EnlistmentKey [in, optional]A pointer to caller-defined information that uniquely identifies the enlistment. The resource manager receives this pointer when it calls ZwGetNotificationResourceManager or when KTM calls the ResourceManagerNotification callback routine. The resource manager can maintain a reference count for this key by calling TmReferenceEnlistmentKey and TmDereferenceEnlistmentKey. This parameter is optional and can be NULL.
ZwCreateEnlistment returns STATUS_SUCCESS if the operation succeeds. Otherwise, this routine might return one of the following values:
| Return code | Description |
|---|---|
| STATUS_INVALID_HANDLE | An object handle is invalid. |
| STATUS_INVALID_PARAMETER | The CreateOptions or NotificationMask parameter's value is invalid, or KTM could not find the transaction that the TransactionHandle parameter specifies. |
| STATUS_INSUFFICIENT_RESOURCES | A memory allocation failed. |
| STATUS_TRANSACTIONMANAGER_NOT_ONLINE | The enlistment failed because KTM or the resource manager is not in an operational state. |
| STATUS_TRANSACTION_NOT_ACTIVE | The enlistment failed because the transaction that the TransactionHandle parameter specifies is not active. |
| STATUS_TRANSACTION_SUPERIOR_EXISTS | The caller tried to register as a superior transaction manager but a superior transaction manager already exists. |
| STATUS_TM_VOLATILE | The caller is trying to register as a superior transaction manager, but the caller's resource manager object is volatile while the associated transaction manager object is not volatile. |
| STATUS_ACCESS_DENIED | The value of the DesiredAccess parameter is invalid. |
The routine might return other NTSTATUS values.
A resource manager calls ZwCreateEnlistment to enlist in a transaction.
Resource managers that are not superior must include the ENLISTMENT_SUBORDINATE_RIGHTS flag in their access mask.
Superior transaction managers must include the ENLISTMENT_SUPERIOR_RIGHTS flag in their access masks. Typically, a superior transaction manager includes code that calls ZwRollbackEnlistment, so it must also include the ENLISTMENT_SUBORDINATE_RIGHTS flag.
A resource manager that calls ZwCreateEnlistment must eventually call ZwClose to close the object handle.
Your resource manager can use the EnlistmentKey parameter to assign a unique value to each enlistment, such as a pointer to a data structure that contains information about the enlistment. For example, if the resource manager stores the enlistment object's handle in the structure, the resource manager can do the following:
For more information about ZwCreateEnlistment, see Creating a Resource Manager and Creating a Superior Transaction Manager.
For calls from kernel-mode drivers, the Nt*Xxx* and Zw*Xxx* versions of a Windows Native System Services routine can behave differently in the way that they handle and interpret input parameters. For more information about the relationship between the Nt*Xxx* and Zw*Xxx* versions of a routine, see Using Nt and Zw Versions of the Native System Services Routines.
Using Nt and Zw Versions of the Native System Services Routines
ZwGetNotificationResourceManager