Hinweis
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, sich anzumelden oder das Verzeichnis zu wechseln.
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, das Verzeichnis zu wechseln.
-
procedure ProcessFsmoRoleRequest( hDrs: DRS_HANDLE, msgIn: DRS_MSG_GETCHGREQ_V10, var msgOut: DRS_MSG_GETCHGREPLY_NATIVE)
Informative summary of behavior: The ProcessFsmoRoleRequest procedure performs the requested FSMO role operation indicated by msgIn.ulExtendedOp.
-
fsmoObj: DSName clientDsaObj: DSName serverObj: DSName: DSName rodcObj: DSNAME: DSName clientComputerObj: DSName clientRidSetObj: DSName ownerDsaObj: DSName scope: set of DSName ridAllocLoHi: ULONGLONG ridAllocHi: DWORD ridReqHi: DWORD ridAvailLoHi: ULONGLONG ridAvailLo: DWORD ridAvailHi: DWORD changedObjs: set of ObjAtts changedLinks: set of ObjAttVal /* Specific error check when at DC functional level Win2K3 */ if (DSAObj()!msDS-Behavior-Version = DS_BEHAVIOR_WIN2003) and (not DRS_WRIT_REP in msgIn.ulFlags) then msgOut.ulExtendedRet := EXOP_ERR_PARAM_ERR return endif fsmoObj := msgIn.pNC^ if not ObjExists(fsmoObj) then msgOut.ulExtendedRet := EXOP_ERR_UPDATE_ERR return endif if msgIn.uuidDsaObjDest = null then msgOut.ulExtendedRet := EXOP_ERR_UPDATE_ERR return endif clientDsaObj := select one o from ConfigNC()where o!objectGUID = msgIn.uuidDsaObjDest if clientDsaObj = null then msgOut.ulExtendedRet := EXOP_ERR_UNKNOWN_CALLER return endif scope := {}if msgIn.ulExtendedOp in {EXOP_FSMO_REQ_ROLE, EXOP_FSMO_REQ_PDC, EXOP_FSMO_RID_REQ_ROLE} then /* Change the FSMO role owner from the server to the client. */ if fsmoObj!fSMORoleOwner ≠ DSAObj() then msgOut.ulExtendedRet := EXOP_ERR_FSMO_NOT_OWNER return endif fsmoObj!fSMORoleOwner := clientDsaObj scope := GetRoleScope(fsmoObj) else if msgIn.ulExtendedOp = EXOP_FSMO_ABANDON_ROLE then /* Request a change in the FSMO role owner from the current owner * to the server. The server will refuse to take the FSMO role if * it is not a full replica and cannot own FSMO. */ if AmIRODC() then msgOut.ulExtendedRet := EXOP_ERR_FSMO_REFUSING_ROLES endif if fsmoObj!fSMORoleOwner ≠ DSAObj() then ownerDsaObj := fsmoObj!fSMORoleOwner if not ObjExists(ownerDsaObj) then msgOut.ulExtendedRet := EXOP_ERR_UNKNOWN_CALLER return else if ownerDsaObj!isDeleted = true msgOut.ulExtendedRet := EXOP_ERR_FSMO_OWNER_DELETED return endif Call IDL_DRSGetNCChanges as a client to the server identified by ownerDsaObj to perform a EXOP_FSMO_REQ_ROLE extended operation; see the client request generation and response processing sections if fsmoObj!fSMORoleOwner ≠ DSAObj() then /* Transfer failed. */ msgOut.ulExtendedRet := EXOP_ERR_COULDNT_CONTACT return endif endif else if msgIn.ulExtendedOp = EXOP_FSMO_REQ_RID_ALLOC then /* Allocate a block of RIDs for the client DC. */ if fsmoObj ≠ DefaultNC()!rIDManagerReference then msgOut.ulExtendedRet := EXOP_ERR_MISMATCH return else if fsmoObj!fSMORoleOwner ≠ DSAObj() then msgOut.ulExtendedRet := EXOP_ERR_FSMO_NOT_OWNER return endif /* Locate or create the RID Set object for the client DC. */ serverObj := clientDsaObj!parent clientComputerObj := serverObj!serverReference if clientComputerObj!rIDSetReferences = null then clientRidSetObj := An implementation-defined DSName in the default NC such that not ObjExists(clientRidSetObj) Create object with DSName clientRidSetObj such that rIDSet in clientRidSetObj!objectClass /* Windows Behavior: Windows sets clientRidSetObj to be a child * of clientComputerObj. */ clientComputerObj!rIDSetReferences := clientRidSetObj else clientRidSetObj := clientComputerObj!rIDSetReferences endif /* Get the current RID allocation for the client DC. */ ridAllocLoHi := clientRidSetObj!rIDAllocationPool ridAvailHi := most significant 32 bits of ridAvailLoHi ridReqHi := most significant 32 bits of msgIn.liFsmoInfo if ridAllocLoHi = 0 or ridAvailHi = 0 or ridReqHi ≥ ridAvailHi then /* The client DC has indeed exhausted its current allocation, * according to our records. */ /* Get the range of RIDs that have not yet been allocated to any * DC. */ ridAvailLoHi := fsmoObj!rIDAvailablePool ridAvailLo := least significant 32 bits of ridAvailLoHi ridAvailHi := most significant 32 bits of ridAvailLoHi /* Select a subset of the unallocated RIDs and allocate them to * the client. */ Assign a value to ridAllocHi according to any implementation- defined policy such that ridAvailLo < ridAllocHi < ridAvailHi. /* Windows Behavior: By default, Windows sets ridAllocHi to * ridAvailLo + 500. */ ridAllocLoHi := ridAvailLo as least significant 32 bits and ridAllocHi as most significant 32 bits ridAvailLo := ridAllocHi + 1 ridAvailLoHi := ridAvailLo as least significant 32 bits and ridAvailHi as most significant 32 bits fsmoObj!rIDAvailablePool := ridAvailLoHi clientRidSetObj!rIDAllocationPool := ridAllocLoHi clientRidSetObj!rIDPreviousAllocationPool := 0 clientRidSetObj!rIDNextRID := 0 /* Windows Behavior: rIDUsedPool [MS-ADA3] is not used anywhere, * but Windows always sets it to zero. */ clientRidSetObj!rIDUsedPool := 0 msgOut.liFsmoInfo := ridAllocLoHi endif scope := GetRoleScope(fsmoObj) + {clientComputerObj, clientRidSetObj} else if EXOP_REPL_SECRETS in msgIn.ulExtendedOp and AmILHServer() then /* Request replication of a single object with secret. * Secret replication is allowed only if these three conditions * hold: * 1. Caller is an RODC. An RODC will always be a member of * "Enterprise Read-Only Domain Controllers" (RID 498) * [MS-ADTS] section 6.1.1.6.14. * 2. The object is configured to reveal secrets. * 3. Outbound secret replication is not disabled. */ serverObj := clientDsaObj!parent rodcObj := serverObj!serverReference if CheckGroupMembership( GetCallerAuthorizationInfo(), SidFromStringSid("S-1-5-22")) and RevealSecretsForUserAllowed(rodcObj, fsmoObj) and (not NTDSDSA_OPT_DISABLE_OUTBOUND_REPL in DSAObj()!options or DRS_SYNC_FORCED in msgIn.ulFlags) then scope := {fsmoObj} else scope := {} endif else if EXOP_REPL_OBJ in msgIn.ulExtendedOp if AmILHServer() = true and NTDSDSA_OPT_DISABLE_OUTBOUND_REPL in DSAObj()!options and not DRS_SYNC_FORCED in msgIn.ulFlags then /* replication of single object is disabled */ pmsgOut.dwDRSError := ERROR_DS_DRA_SOURCE_DISABLED return endif /* Operation is invalid if destination is full replica but this server * is not, or if both are partial replicas but this server does not have * all the attributes needed by the destination in its PAS. */ if(not FullReplicaExists(GetObjectNC(msgIn.pNC^)) and not msgIn.pPartialAttrSet = null) msgOut.ulExtendedRet := EXOP_ERR_PARAM_ERR return else if not GetFilteredAttributeSet() ∩ msgIn.pPartialAttrSet = {} then msgOut.ulExtendedRet := EXOP_ERR_PARAM_ERR return endif scope := {fsmoObj} else /* Unrecognized request. */ msgOut.ulExtendedRet := EXOP_ERR_UNKNOWN_OP return endif if scope ≠ {} then /* Add updates in scope to the response. */ GetChangesInScope(scope, msgIn.pUpToDateVecDest, msgIn.ulExtendedOp, msgIn.pPartialAttrSet, msgIn.pPartialAttrSet, 0, changedObjs, changedLinks) foreach o in changedObjs AddObjToResponse( hDrs, o, GetObjectNC(msgIn.pNC^), msgIn.ulFlags, msgIn.ulExtendedOp, msgOut) endfor foreach v in changedLinks AddLinkToResponse(v, msgIn, msgOut) endfor endif msgOut.ulExtendedRet := EXOP_ERR_SUCCESS return