From af76a3750288d90c006022829887c92601a4737c Mon Sep 17 00:00:00 2001
From: Jean-Noel Rouvignac <jean-noel.rouvignac@forgerock.com>
Date: Mon, 24 Jun 2013 11:56:44 +0000
Subject: [PATCH] OPENDJ-885 - Replication replay may lose changes if it can't acquire a writeLock
---
opends/src/server/org/opends/server/extensions/PasswordModifyExtendedOperation.java | 84 ++++++++++++++++--------------------------
1 files changed, 32 insertions(+), 52 deletions(-)
diff --git a/opends/src/server/org/opends/server/extensions/PasswordModifyExtendedOperation.java b/opends/src/server/org/opends/server/extensions/PasswordModifyExtendedOperation.java
index 4eb565a..2b2d54c 100644
--- a/opends/src/server/org/opends/server/extensions/PasswordModifyExtendedOperation.java
+++ b/opends/src/server/org/opends/server/extensions/PasswordModifyExtendedOperation.java
@@ -23,50 +23,45 @@
*
*
* Copyright 2006-2010 Sun Microsystems, Inc.
- * Portions Copyright 2011 ForgeRock AS
+ * Portions Copyright 2011-2013 ForgeRock AS
*/
package org.opends.server.extensions;
-
-import org.opends.messages.Message;
-import java.util.ArrayList;
-import java.util.LinkedHashSet;
-import java.util.List;
-import java.util.HashSet;
-import java.util.Set;
+import java.util.*;
import java.util.concurrent.locks.Lock;
+import org.opends.messages.Message;
+import org.opends.messages.MessageBuilder;
import org.opends.server.admin.server.ConfigurationChangeListener;
import org.opends.server.admin.std.server.ExtendedOperationHandlerCfg;
import org.opends.server.admin.std.server.
PasswordModifyExtendedOperationHandlerCfg;
import org.opends.server.api.*;
import org.opends.server.config.ConfigException;
+import org.opends.server.controls.PasswordPolicyErrorType;
import org.opends.server.controls.PasswordPolicyResponseControl;
import org.opends.server.controls.PasswordPolicyWarningType;
-import org.opends.server.controls.PasswordPolicyErrorType;
import org.opends.server.core.DirectoryServer;
import org.opends.server.core.ExtendedOperation;
import org.opends.server.core.ModifyOperation;
import org.opends.server.core.PasswordPolicyState;
+import org.opends.server.loggers.ErrorLogger;
import org.opends.server.loggers.debug.DebugTracer;
-import org.opends.server.protocols.asn1.*;
+import org.opends.server.protocols.asn1.ASN1;
+import org.opends.server.protocols.asn1.ASN1Reader;
+import org.opends.server.protocols.asn1.ASN1Writer;
import org.opends.server.protocols.internal.InternalClientConnection;
import org.opends.server.schema.AuthPasswordSyntax;
import org.opends.server.schema.UserPasswordSyntax;
import org.opends.server.types.*;
+import static org.opends.messages.CoreMessages.*;
+import static org.opends.messages.ExtensionMessages.*;
import static org.opends.server.extensions.ExtensionsConstants.*;
import static org.opends.server.loggers.debug.DebugLogger.*;
-import org.opends.server.loggers.ErrorLogger;
-import static org.opends.messages.ExtensionMessages.*;
-import static org.opends.messages.CoreMessages.*;
-
-import org.opends.messages.MessageBuilder;
import static org.opends.server.util.ServerConstants.*;
import static org.opends.server.util.StaticUtils.*;
-
/**
* This class implements the password modify extended operation defined in RFC
* 3062. It includes support for requiring the user's current password as well
@@ -166,6 +161,7 @@
* that is not related to the server
* configuration.
*/
+ @Override
public void initializeExtendedOperationHandler(
PasswordModifyExtendedOperationHandlerCfg config)
throws ConfigException, InitializationException
@@ -244,6 +240,7 @@
*
* @param operation The extended operation to be processed.
*/
+ @Override
public void processExtendedOperation(ExtendedOperation operation)
{
// Initialize the variables associated with components that may be included
@@ -353,25 +350,12 @@
// Retrieve a write lock on that user's entry.
userDN = requestorEntry.getDN();
- for (int i=0; i < 3; i++)
- {
- userLock = LockManager.lockWrite(userDN);
-
- if (userLock != null)
- {
- break;
- }
- }
-
+ userLock = LockManager.lockWrite(userDN);
if (userLock == null)
{
- operation.setResultCode(DirectoryServer.getServerErrorResultCode());
-
- Message message =
- ERR_EXTOP_PASSMOD_CANNOT_LOCK_USER_ENTRY.get(
- String.valueOf(userDN));
- operation.appendErrorMessage(message);
-
+ operation.setResultCode(ResultCode.BUSY);
+ operation.appendErrorMessage(ERR_EXTOP_PASSMOD_CANNOT_LOCK_USER_ENTRY
+ .get(String.valueOf(userDN)));
return;
}
@@ -1024,31 +1008,15 @@
modList.add(new Modification(ModificationType.DELETE, deleteAttr));
- // Add the new encoded values.
- LinkedHashSet<AttributeValue> addValues =
- new LinkedHashSet<AttributeValue>(encodedPasswords.size());
- for (ByteString s : encodedPasswords)
- {
- addValues.add(AttributeValues.create(attrType, s));
- }
-
builder = new AttributeBuilder(attrType);
- builder.addAll(addValues);
+ builder.addAll(toAttributeValues(attrType, encodedPasswords));
Attribute addAttr = builder.toAttribute();
modList.add(new Modification(ModificationType.ADD, addAttr));
}
else
{
- LinkedHashSet<AttributeValue> replaceValues =
- new LinkedHashSet<AttributeValue>(encodedPasswords.size());
- for (ByteString s : encodedPasswords)
- {
- replaceValues.add(
- AttributeValues.create(attrType, s));
- }
-
AttributeBuilder builder = new AttributeBuilder(attrType);
- builder.addAll(replaceValues);
+ builder.addAll(toAttributeValues(attrType, encodedPasswords));
Attribute addAttr = builder.toAttribute();
modList.add(new Modification(ModificationType.REPLACE, addAttr));
}
@@ -1241,7 +1209,17 @@
}
}
-
+ private Collection<AttributeValue> toAttributeValues(AttributeType attrType,
+ Collection<ByteString> values)
+ {
+ Set<AttributeValue> results =
+ new LinkedHashSet<AttributeValue>(values.size());
+ for (ByteString s : values)
+ {
+ results.add(AttributeValues.create(attrType, s));
+ }
+ return results;
+ }
/**
* Retrieves the entry for the specified user based on the provided DN. If
@@ -1348,6 +1326,7 @@
* @return <CODE>true</CODE> if the provided entry has an acceptable
* configuration for this component, or <CODE>false</CODE> if not.
*/
+ @Override
public boolean isConfigurationChangeAcceptable(
PasswordModifyExtendedOperationHandlerCfg config,
List<Message> unacceptableReasons)
@@ -1401,6 +1380,7 @@
*
* @return Information about the result of the configuration update.
*/
+ @Override
public ConfigChangeResult applyConfigurationChange(
PasswordModifyExtendedOperationHandlerCfg config)
{
--
Gitblit v1.10.0