mirror of https://github.com/OpenIdentityPlatform/OpenDJ.git

Matthew Swift
10.28.2012 1112197854c0922ba9a48acbb986b3f20d743c8f
Fix OPENDJ-475: Incorrect behaviour/result code regarding non-critical controls

11 files modified
160 ■■■■■ changed files
opends/src/server/org/opends/server/core/ExtendedOperationBasis.java 20 ●●●● patch | view | raw | blame | history
opends/src/server/org/opends/server/workflowelement/externalchangelog/ECLSearchOperation.java 18 ●●●● patch | view | raw | blame | history
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendAddOperation.java 9 ●●●●● patch | view | raw | blame | history
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendBindOperation.java 9 ●●●●● patch | view | raw | blame | history
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendCompareOperation.java 9 ●●●●● patch | view | raw | blame | history
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendDeleteOperation.java 9 ●●●●● patch | view | raw | blame | history
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendModifyDNOperation.java 7 ●●●●● patch | view | raw | blame | history
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendModifyOperation.java 8 ●●●●● patch | view | raw | blame | history
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendSearchOperation.java 10 ●●●● patch | view | raw | blame | history
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendWorkflowElement.java 42 ●●●●● patch | view | raw | blame | history
opends/tests/unit-tests-testng/src/server/org/opends/server/authorization/dseecompat/TargetControlTestCase.java 19 ●●●● patch | view | raw | blame | history
opends/src/server/org/opends/server/core/ExtendedOperationBasis.java
@@ -23,7 +23,7 @@
 *
 *
 *      Copyright 2006-2010 Sun Microsystems, Inc.
 *      Portions copyright 2011 ForgeRock AS.
 *      Portions copyright 2011-2012 ForgeRock AS.
 */
package org.opends.server.core;
import org.opends.messages.MessageBuilder;
@@ -419,13 +419,23 @@
          try
          {
            if (!AccessControlConfigManager.getInstance()
                .getAccessControlHandler().isAllowed(
                    this.getAuthorizationDN(), this, c))
                .getAccessControlHandler()
                .isAllowed(getAuthorizationDN(), this, c))
            {
              setResultCode(ResultCode.INSUFFICIENT_ACCESS_RIGHTS);
              // As per RFC 4511 4.1.11.
              if (c.isCritical())
              {
                setResultCode(ResultCode.UNAVAILABLE_CRITICAL_EXTENSION);
              appendErrorMessage(ERR_CONTROL_INSUFFICIENT_ACCESS_RIGHTS
                  .get(c.getOID()));
              return;
              }
              else
              {
                // We don't want to process this non-critical control, so
                // remove it.
                removeRequestControl(c);
                continue;
              }
            }
          }
          catch (DirectoryException e)
opends/src/server/org/opends/server/workflowelement/externalchangelog/ECLSearchOperation.java
@@ -405,12 +405,24 @@
      {
        Control c   = requestControls.get(i);
        String  oid = c.getOID();
        if (! AccessControlConfigManager.getInstance().
            getAccessControlHandler().isAllowed(baseDN, this, c))
        if (!AccessControlConfigManager.getInstance().getAccessControlHandler()
            .isAllowed(baseDN, this, c))
        {
          throw new DirectoryException(ResultCode.INSUFFICIENT_ACCESS_RIGHTS,
          // As per RFC 4511 4.1.11.
          if (c.isCritical())
          {
            throw new DirectoryException(
                ResultCode.UNAVAILABLE_CRITICAL_EXTENSION,
              ERR_CONTROL_INSUFFICIENT_ACCESS_RIGHTS.get(oid));
        }
          else
          {
            // We don't want to process this non-critical control, so remove it.
            removeRequestControl(c);
            continue;
          }
        }
        if (oid.equals(OID_ECL_COOKIE_EXCHANGE_CONTROL))
        {
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendAddOperation.java
@@ -23,7 +23,7 @@
 *
 *
 *      Copyright 2008-2010 Sun Microsystems, Inc.
 *      Portions Copyright 2011 ForgeRock AS
 *      Portions Copyright 2011-2012 ForgeRock AS
 */
package org.opends.server.workflowelement.localbackend;
@@ -1415,11 +1415,10 @@
        Control c   = requestControls.get(i);
        String  oid = c.getOID();
        if (!AccessControlConfigManager.getInstance().
                getAccessControlHandler().isAllowed(parentDN, this, c))
        if (!LocalBackendWorkflowElement.isControlAllowed(parentDN, this, c))
        {
          throw new DirectoryException(ResultCode.INSUFFICIENT_ACCESS_RIGHTS,
                         ERR_CONTROL_INSUFFICIENT_ACCESS_RIGHTS.get(oid));
          // Skip disallowed non-critical controls.
          continue;
        }
        if (oid.equals(OID_LDAP_ASSERTION))
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendBindOperation.java
@@ -23,7 +23,7 @@
 *
 *
 *      Copyright 2008-2010 Sun Microsystems, Inc.
 *      Portions copyright 2011 ForgeRock AS.
 *      Portions copyright 2011-2012 ForgeRock AS.
 */
package org.opends.server.workflowelement.localbackend;
@@ -439,11 +439,10 @@
        Control c   = requestControls.get(i);
        String  oid = c.getOID();
        if (! AccessControlConfigManager.getInstance().
                 getAccessControlHandler(). isAllowed(bindDN, this, c))
        if (!LocalBackendWorkflowElement.isControlAllowed(bindDN, this, c))
        {
          throw new DirectoryException(ResultCode.INSUFFICIENT_ACCESS_RIGHTS,
                         ERR_CONTROL_INSUFFICIENT_ACCESS_RIGHTS.get(oid));
          // Skip disallowed non-critical controls.
          continue;
        }
        if (oid.equals(OID_AUTHZID_REQUEST))
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendCompareOperation.java
@@ -23,7 +23,7 @@
 *
 *
 *      Copyright 2008-2009 Sun Microsystems, Inc.
 *      Portions Copyright 2011 ForgeRock AS
 *      Portions Copyright 2011-2012 ForgeRock AS
 */
package org.opends.server.workflowelement.localbackend;
@@ -407,11 +407,10 @@
        Control c   = requestControls.get(i);
        String  oid = c.getOID();
        if (! AccessControlConfigManager.getInstance().
                   getAccessControlHandler().isAllowed(entryDN, this, c))
        if (!LocalBackendWorkflowElement.isControlAllowed(entryDN, this, c))
        {
          throw new DirectoryException(ResultCode.INSUFFICIENT_ACCESS_RIGHTS,
                         ERR_CONTROL_INSUFFICIENT_ACCESS_RIGHTS.get(oid));
          // Skip disallowed non-critical controls.
          continue;
        }
        if (oid.equals(OID_LDAP_ASSERTION))
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendDeleteOperation.java
@@ -23,7 +23,7 @@
 *
 *
 *      Copyright 2008-2009 Sun Microsystems, Inc.
 *      Portions Copyright 2011 ForgeRock AS
 *      Portions Copyright 2011-2012 ForgeRock AS
 */
package org.opends.server.workflowelement.localbackend;
@@ -507,11 +507,10 @@
        Control c   = requestControls.get(i);
        String  oid = c.getOID();
        if (!AccessControlConfigManager.getInstance().
                 getAccessControlHandler().isAllowed(entryDN, this, c))
        if (!LocalBackendWorkflowElement.isControlAllowed(entryDN, this, c))
        {
          throw new DirectoryException(ResultCode.INSUFFICIENT_ACCESS_RIGHTS,
                         ERR_CONTROL_INSUFFICIENT_ACCESS_RIGHTS.get(oid));
          // Skip disallowed non-critical controls.
          continue;
        }
        if (oid.equals(OID_LDAP_ASSERTION))
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendModifyDNOperation.java
@@ -724,11 +724,10 @@
        Control c   = requestControls.get(i);
        String  oid = c.getOID();
        if (! AccessControlConfigManager.getInstance().
                   getAccessControlHandler().isAllowed(entryDN,  this, c))
        if (!LocalBackendWorkflowElement.isControlAllowed(entryDN, this, c))
        {
          throw new DirectoryException(ResultCode.INSUFFICIENT_ACCESS_RIGHTS,
                         ERR_CONTROL_INSUFFICIENT_ACCESS_RIGHTS.get(oid));
          // Skip disallowed non-critical controls.
          continue;
        }
        if (oid.equals(OID_LDAP_ASSERTION))
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendModifyOperation.java
@@ -763,14 +763,12 @@
        Control c   = requestControls.get(i);
        String  oid = c.getOID();
        if (! AccessControlConfigManager.getInstance().
                   getAccessControlHandler().isAllowed(entryDN, this, c))
        if (!LocalBackendWorkflowElement.isControlAllowed(entryDN, this, c))
        {
          throw new DirectoryException(ResultCode.INSUFFICIENT_ACCESS_RIGHTS,
                         ERR_CONTROL_INSUFFICIENT_ACCESS_RIGHTS.get(oid));
          // Skip disallowed non-critical controls.
          continue;
        }
        if (oid.equals(OID_LDAP_ASSERTION))
        {
          LDAPAssertionRequestControl assertControl =
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendSearchOperation.java
@@ -23,7 +23,7 @@
 *
 *
 *      Copyright 2008-2010 Sun Microsystems, Inc.
 *      Portions copyright 2011 ForgeRock AS
 *      Portions copyright 2011-2012 ForgeRock AS
 */
package org.opends.server.workflowelement.localbackend;
@@ -350,11 +350,11 @@
      {
        Control c   = requestControls.get(i);
        String  oid = c.getOID();
        if (! AccessControlConfigManager.getInstance().
                   getAccessControlHandler().isAllowed(baseDN, this, c))
        if (!LocalBackendWorkflowElement.isControlAllowed(baseDN, this, c))
        {
          throw new DirectoryException(ResultCode.INSUFFICIENT_ACCESS_RIGHTS,
                         ERR_CONTROL_INSUFFICIENT_ACCESS_RIGHTS.get(oid));
          // Skip disallowed non-critical controls.
          continue;
        }
        if (oid.equals(OID_LDAP_ASSERTION))
opends/src/server/org/opends/server/workflowelement/localbackend/LocalBackendWorkflowElement.java
@@ -51,6 +51,7 @@
import org.opends.server.types.*;
import org.opends.server.workflowelement.LeafWorkflowElement;
import static org.opends.messages.CoreMessages.*;
import static org.opends.server.config.ConfigConstants.*;
@@ -325,6 +326,47 @@
  /**
   * Determine whether or not the provided request control is permitted by the
   * access control policy. If it is not allowed, then abort the operation if
   * the control was critical, otherwise ignore it.
   *
   * @param targetDN
   *          The operation target DN.
   * @param op
   *          The operation.
   * @param control
   *          The request control.
   * @return {@code true} if access is allowed, or {@code false} if access is
   *         not allowed, but the control is non-critical and should be ignored.
   * @throws DirectoryException
   *           If access is not allowed and the control is critical.
   */
  static boolean isControlAllowed(DN targetDN, Operation op, Control control)
      throws DirectoryException
  {
    if (!AccessControlConfigManager.getInstance().getAccessControlHandler()
        .isAllowed(targetDN, op, control))
    {
      // As per RFC 4511 4.1.11.
      if (control.isCritical())
      {
        throw new DirectoryException(ResultCode.UNAVAILABLE_CRITICAL_EXTENSION,
            ERR_CONTROL_INSUFFICIENT_ACCESS_RIGHTS.get(control.getOID()));
      }
      else
      {
        // We don't want the backend to process this non-critical control, so
        // remove it.
        op.removeRequestControl(control);
        return false;
      }
    }
    return true;
  }
  /**
   * Adds the post-read response control to the response if requested.
   *
   * @param operation
opends/tests/unit-tests-testng/src/server/org/opends/server/authorization/dseecompat/TargetControlTestCase.java
@@ -23,6 +23,7 @@
 *
 *
 *      Copyright 2008-2009 Sun Microsystems, Inc.
 *      Portions copyright 2012 ForgeRock AS.
 */
@@ -276,11 +277,11 @@
    LDAPSearchParams(level3User, PWD, null, null, null,
            superUser, filter, "aclRights mail description", true,
            true, 0);
    //This should fail since the both controls are not allowed for the
    //ou=admins, o=test suffix.
    //This should succeed since both controls are not allowed for the
    //ou=admins, o=test suffix, but both are critical.
    LDAPSearchParams(superUser, PWD, null, null, null,
            superUser, filter, "aclRights mail description", true,
            true, LDAPResultCode.INSUFFICIENT_ACCESS_RIGHTS);
            true, 0);
    deleteAttrFromEntry(peopleBase, "aci");
  }
@@ -299,12 +300,12 @@
            makeAddLDIF(ATTR_AUTHZ_GLOBAL_ACI, ACCESS_HANDLER_DN,
                    controlAdmin, controlPeople);
    LDIFAdminModify(globalControlAcis, DIR_MGR_DN, PWD);
    //Fails because geteffectiverights control not allowed on
    //ou=people, o=test
    //Succeeds because geteffectiverights control is not allowed on
    //ou=people, o=test, but it is non-critical.
    LDAPSearchParams(level3User, PWD, null,
            "dn: " + level1User, null,
            level1User, filter, "aclRights mail description",
            false, false, LDAPResultCode.INSUFFICIENT_ACCESS_RIGHTS);
            false, false, 0);
    //Ok because geteffectiverights control is allowed on
    //ou=admin, o=test
    LDAPSearchParams(level3User, PWD, null,
@@ -318,11 +319,11 @@
    String addEntryLDIF=makeAddEntryLDIF(newPeopleDN, newEntry);
    LDIFAdd(addEntryLDIF, superUser, PWD, controlStr,
            LDAPResultCode.PROTOCOL_ERROR);
    //Test add to ou=admin, o=test with assertion control,
    //Test add to ou=admin, o=test with assertion control, and critical
    //should get access denied since this control is not allowed.
    String addEntryLDIF1=makeAddEntryLDIF(newAdminDN, newEntry);
    LDIFAdd(addEntryLDIF1, superUser, PWD, controlStr,
            LDAPResultCode.INSUFFICIENT_ACCESS_RIGHTS);
            LDAPResultCode.UNAVAILABLE_CRITICAL_EXTENSION);
    deleteAttrFromAdminEntry(ACCESS_HANDLER_DN, ATTR_AUTHZ_GLOBAL_ACI);
  }
@@ -344,7 +345,7 @@
    LDAPSearchParams(superUser, PWD, null,
            "dn: " + superUser, null,
            base, filter, "aclRights mail description", false, false,
            LDAPResultCode.INSUFFICIENT_ACCESS_RIGHTS);
            0 /* disallowed but non-critical */);
    LDIFModify(aciRight, superUser, PWD, OID_LDAP_READENTRY_PREREAD,
            LDAPResultCode.INSUFFICIENT_ACCESS_RIGHTS);
    deleteAttrFromEntry (base, "aci");