db-derby-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From rhille...@apache.org
Subject svn commit: r892272 [1/2] - in /db/derby/code/trunk/java: engine/org/apache/derby/iapi/sql/compile/ engine/org/apache/derby/iapi/sql/dictionary/ engine/org/apache/derby/impl/sql/catalog/ engine/org/apache/derby/impl/sql/compile/ engine/org/apache/derby...
Date Fri, 18 Dec 2009 15:15:36 GMT
Author: rhillegas
Date: Fri Dec 18 15:15:02 2009
New Revision: 892272

URL: http://svn.apache.org/viewvc?rev=892272&view=rev
Log:
DERBY-651: Add support for USAGE privilege on UDTs and the beginning of support for USAGE privilege on SEQUENCES.

Added:
    db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/PrivilegedSQLObject.java   (with props)
    db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementGenericPermission.java   (with props)
    db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/execute/GenericPrivilegeInfo.java   (with props)
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/UDTPermsTest.java   (with props)
Modified:
    db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/compile/CompilerContext.java
    db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/AliasDescriptor.java
    db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/DataDictionary.java
    db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/PermDescriptor.java
    db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/SequenceDescriptor.java
    db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementPermission.java
    db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementRoutinePermission.java
    db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/CoreDDFinderClassInfo.java
    db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/DDdependableFinder.java
    db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/DataDictionaryImpl.java
    db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/PermissionsCacheable.java
    db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/SYSPERMSRowFactory.java
    db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/CompilerContextImpl.java
    db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/PrivilegeNode.java
    db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/QueryTreeNode.java
    db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/sqlgrammar.jj
    db/derby/code/trunk/java/engine/org/apache/derby/loc/messages.xml
    db/derby/code/trunk/java/shared/org/apache/derby/shared/common/reference/SQLState.java
    db/derby/code/trunk/java/storeless/org/apache/derby/impl/storeless/EmptyDictionary.java
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/GeneratedColumnsHelper.java
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/SystemCatalogTest.java
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/UDTTest.java
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/_Suite.java

Modified: db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/compile/CompilerContext.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/compile/CompilerContext.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/compile/CompilerContext.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/compile/CompilerContext.java Fri Dec 18 15:15:02 2009
@@ -34,6 +34,7 @@
 import org.apache.derby.iapi.sql.dictionary.AliasDescriptor;
 import org.apache.derby.iapi.sql.dictionary.ColumnDescriptor;
 import org.apache.derby.iapi.sql.dictionary.TableDescriptor;
+import org.apache.derby.iapi.sql.dictionary.PrivilegedSQLObject;
 import org.apache.derby.iapi.sql.dictionary.SchemaDescriptor;
 
 import org.apache.derby.iapi.sql.depend.Dependent;
@@ -565,6 +566,13 @@
 	public void addRequiredRoutinePriv( AliasDescriptor routine);
 
 	/**
+	 * Add a usage privilege to the list of required privileges.
+	 *
+	 * @param usableObject
+	 */
+	public void addRequiredUsagePriv( PrivilegedSQLObject usableObject );
+
+	/**
 	 * Add a required role privilege to the list of privileges.
 	 *
 	 * @see CompilerContext#addRequiredRolePriv

Modified: db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/AliasDescriptor.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/AliasDescriptor.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/AliasDescriptor.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/AliasDescriptor.java Fri Dec 18 15:15:02 2009
@@ -32,6 +32,7 @@
 
 import	org.apache.derby.catalog.AliasInfo;
 import org.apache.derby.catalog.types.RoutineAliasInfo;
+import	org.apache.derby.catalog.types.UDTAliasInfo;
 
 import org.apache.derby.catalog.UUID;
 
@@ -59,7 +60,7 @@
 
 public final class AliasDescriptor 
 	extends TupleDescriptor
-	implements UniqueTupleDescriptor, Provider, Dependent
+	implements PrivilegedSQLObject, Provider, Dependent
 {
 	private final UUID		aliasID;
 	private final String		aliasName;
@@ -70,6 +71,7 @@
 	private final boolean		systemAlias;
 	private final AliasInfo	aliasInfo;
 	private final String		specificName;
+    private final SchemaDescriptor schemaDescriptor;
 
 	/**
 	 * Constructor for a AliasDescriptor
@@ -89,12 +91,14 @@
 							  String aliasName, UUID schemaID, String javaClassName,
 							  char aliasType, char nameSpace, boolean systemAlias,
 							  AliasInfo aliasInfo, String specificName)
+        throws StandardException
 	{
 		super( dataDictionary );
 
 		this.aliasID = aliasID;
 		this.aliasName = aliasName;
 		this.schemaID = schemaID;
+		this.schemaDescriptor = dataDictionary.getSchemaDescriptor(schemaID, null);
 		this.javaClassName = javaClassName;
 		this.aliasType = aliasType;
 		this.nameSpace = nameSpace;
@@ -117,6 +121,26 @@
 		return aliasID;
 	}
 
+   /**
+	 * @see PrivilegedSQLObject#getObjectTypeName
+	 */
+	public String getObjectTypeName()
+	{
+        if ( aliasInfo instanceof UDTAliasInfo )
+        {
+            return PermDescriptor.UDT_TYPE;
+        }
+        else
+        {
+            if( SanityManager.DEBUG)
+            {
+                SanityManager.THROWASSERT( "Unsupported alias type: " + aliasInfo.getClass().getName() );
+            }
+
+            return null;  // should never get here
+        }
+	}
+
 	/**
 	 * Gets the UUID  of the schema for this method alias.
 	 *
@@ -128,6 +152,26 @@
 	}
 
 	/**
+	 * Gets the SchemaDescriptor for this alias.
+	 *
+	 * @return SchemaDescriptor	The SchemaDescriptor.
+	 */
+	public final SchemaDescriptor getSchemaDescriptor()
+	{
+		return schemaDescriptor;
+	}
+
+	/**
+	 * Gets the name of the alias.
+	 *
+	 * @return	A String containing the name of the statement.
+	 */
+	public final String	getName()
+	{
+		return aliasName;
+	}
+
+	/**
 	 * Gets the name of the schema that the alias lives in.
 	 *
 	 * @return	A String containing the name of the schema that the alias
@@ -135,7 +179,7 @@
 	 */
 	public String	getSchemaName() throws StandardException
 	{
-		return getDataDictionary().getSchemaDescriptor( schemaID, null ).getSchemaName();
+		return schemaDescriptor.getSchemaName();
 	}
 
 	/**

Modified: db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/DataDictionary.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/DataDictionary.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/DataDictionary.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/DataDictionary.java Fri Dec 18 15:15:02 2009
@@ -2023,13 +2023,16 @@
      * Get permissions granted to one user for an object using the object's Id
      * and the user's authorization Id.
      *
-     * @param objectUUID
+     * @param objectUUID ID of the object being protected
+     * @param objectType Type of the object (e.g., PermDescriptor.SEQUENCE_TYPE)
+     * @param privilege The kind of privilege needed (e.g., PermDescriptor.USAGE_PRIV)
+     * @param granteeAuthid The user who needs the permission
      *
      * @return The descriptor of the permissions for the object
      *
      * @exception StandardException
      */
-    public PermDescriptor getPermissions(UUID objectUUID, String granteeAuthId)
+    public PermDescriptor getGenericPermissions(UUID objectUUID, String objectType, String privilege, String granteeAuthId)
         throws StandardException;
 
     /**
@@ -2041,7 +2044,7 @@
      *
      * @exception StandardException
      */
-    public PermDescriptor getPermissions(UUID permUUID)
+    public PermDescriptor getGenericPermissions(UUID permUUID)
     throws StandardException;
 
     /**

Modified: db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/PermDescriptor.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/PermDescriptor.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/PermDescriptor.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/PermDescriptor.java Fri Dec 18 15:15:02 2009
@@ -1,6 +1,6 @@
 /*
 
-   Derby - Class org.apache.derby.iapi.sql.dictionary.SequenceDescriptor
+   Derby - Class org.apache.derby.iapi.sql.dictionary.PermDescriptor
 
    Licensed to the Apache Software Foundation (ASF) under one or more
    contributor license agreements.  See the NOTICE file distributed with
@@ -25,17 +25,29 @@
 import org.apache.derby.catalog.DependableFinder;
 import org.apache.derby.catalog.Dependable;
 import org.apache.derby.iapi.error.StandardException;
+import org.apache.derby.iapi.reference.SQLState;
 import org.apache.derby.iapi.services.sanity.SanityManager;
 import org.apache.derby.iapi.services.io.StoredFormatIds;
 import org.apache.derby.iapi.sql.depend.Provider;
 import org.apache.derby.impl.sql.catalog.DDdependableFinder;
+import org.apache.derby.iapi.sql.dictionary.PrivilegedSQLObject;
 
 /**
  * This class describes rows in the SYS.SYSPERMS system table, which keeps track of the
  * permissions that have been granted but not revoked.
  */
 public class PermDescriptor extends PermissionsDescriptor
-        implements Provider {
+        implements Provider
+{
+    // object types
+    public static final String SEQUENCE_TYPE = "SEQUENCE";
+    public static final String UDT_TYPE = "TYPE";
+
+    // permissions
+    public static final String USAGE_PRIV = "USAGE";
+
+    // state
+    
     private String objectType;
     private UUID permObjectId;
     private String permission;
@@ -45,8 +57,13 @@
      * Constructor
      *
      * @param dataDictionary data dictionary
-     * @param permUUID       unique identification in time and space of this perm
-     *                       descriptor
+     * @param permUUID       unique identification in time and space of this perm descriptor
+     * @param objectType     E.g., SEQUENCE_TYPE
+     * @param permObjectId   Unique id of the object being protected
+     * @param permission     E.g., USAGE_PRIV
+     * @param grantor        Authorization id which confers the privilege
+     * @param grantee        Authorization id which receives the privilege
+     * @param isGrantable    True if the privilege can be granted onwards
      */
 
     public PermDescriptor(DataDictionary dataDictionary, UUID permUUID, String objectType,
@@ -110,26 +127,50 @@
             return false;
         PermDescriptor otherPerm = (PermDescriptor) other;
         return super.keyEquals(otherPerm) &&
-                oid.equals(otherPerm.oid);
+                permObjectId.equals(otherPerm.permObjectId);
     }
 
     /**
      * @return the hashCode for the key part of this permissions descriptor
      */
     public int hashCode() {
-        return super.keyHashCode() + oid.hashCode();
+        return super.keyHashCode() + permObjectId.hashCode();
     }
 
     /**
      * @see PermissionsDescriptor#checkOwner
      */
-    public boolean checkOwner(String authorizationId) throws StandardException {
-        UUID sd = getDataDictionary().getAliasDescriptor(oid).getSchemaUUID();
-        if (getDataDictionary().getSchemaDescriptor(sd, null).getAuthorizationId()
-                .equals(authorizationId)) {
-            return true;
-        } else {
-            return false;
+    public boolean checkOwner( String authorizationId ) throws StandardException
+    {
+        DataDictionary dd = getDataDictionary();
+        PrivilegedSQLObject pso = getProtectedObject( dd, permObjectId, objectType );
+        
+        return pso.getSchemaDescriptor().getAuthorizationId().equals(authorizationId);
+    }
+
+    /**
+     * Get the protected object.
+     *
+     * @param dd Metadata
+     * @param objectID Unique handle on the protected object
+     * @param objectType Type of the object
+     */
+    public static PrivilegedSQLObject getProtectedObject
+        ( DataDictionary dd, UUID objectID, String objectType ) throws StandardException
+    {
+        if ( PermDescriptor.SEQUENCE_TYPE.equals( objectType ) )
+        {
+            return dd.getSequenceDescriptor( objectID );
+        }
+        else if ( PermDescriptor.UDT_TYPE.equals( objectType ) )
+        {
+            return dd.getAliasDescriptor( objectID );
+        }
+        else
+        {
+            // oops, still need to implement support for this kind
+            // of privileged object
+            throw StandardException.newException( SQLState.BTREE_UNIMPLEMENTED_FEATURE );
         }
     }
 
@@ -144,8 +185,14 @@
      *
      * @return String   The name of this provider.
      */
-    public String getObjectName() {
-        return permission + "privilege on " + objectType;
+    public String getObjectName()
+    {
+        try {
+            DataDictionary dd = getDataDictionary();
+            PrivilegedSQLObject pso = getProtectedObject( dd, permObjectId, objectType );
+        
+            return pso.getName();
+        } catch (StandardException se) { return objectType; }
     }
 
     /**

Added: db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/PrivilegedSQLObject.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/PrivilegedSQLObject.java?rev=892272&view=auto
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/PrivilegedSQLObject.java (added)
+++ db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/PrivilegedSQLObject.java Fri Dec 18 15:15:02 2009
@@ -0,0 +1,34 @@
+/*
+
+   Derby - Class org.apache.derby.iapi.sql.dictionary.PrivilegedSQLObject
+
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to you under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+
+ */
+
+package org.apache.derby.iapi.sql.dictionary;
+
+import org.apache.derby.iapi.sql.depend.Provider;
+
+/**
+ * This is a descriptor for schema object which can have privileges granted on it.
+ */
+public interface PrivilegedSQLObject extends UniqueSQLObjectDescriptor, Provider
+{
+    /** Get the type of the object for storage in SYS.SYSPERMS */
+    public String getObjectTypeName();
+    
+}

Propchange: db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/PrivilegedSQLObject.java
------------------------------------------------------------------------------
    svn:eol-style = native

Modified: db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/SequenceDescriptor.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/SequenceDescriptor.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/SequenceDescriptor.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/SequenceDescriptor.java Fri Dec 18 15:15:02 2009
@@ -39,7 +39,8 @@
  * This class is used by rows in the SYS.SYSSEQUENCES system table.
  */
 public class SequenceDescriptor extends TupleDescriptor
-        implements Provider, Dependent, UniqueSQLObjectDescriptor {
+        implements Provider, Dependent, PrivilegedSQLObject
+{
 
     private UUID sequenceUUID;
     private String sequenceName;
@@ -93,6 +94,14 @@
 		return sequenceUUID;
 	}
 
+   /**
+	 * @see PrivilegedSQLObject#getObjectTypeName
+	 */
+	public String getObjectTypeName()
+	{
+		return PermDescriptor.SEQUENCE_TYPE;
+	}
+
     public String toString() {
         if (SanityManager.DEBUG) {
             return "sequenceUUID: " + sequenceUUID + "\n" +
@@ -267,10 +276,6 @@
         return sequenceName;
     }
 
-    public UUID getSequenceUUID() {
-        return sequenceUUID;
-    }
-
     public UUID getSchemaId() {
         return schemaId;
     }

Added: db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementGenericPermission.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementGenericPermission.java?rev=892272&view=auto
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementGenericPermission.java (added)
+++ db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementGenericPermission.java Fri Dec 18 15:15:02 2009
@@ -0,0 +1,118 @@
+/*
+
+   Derby - Class org.apache.derby.iapi.sql.dictionary.StatementGenericPermission
+
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to you under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+	  http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+
+ */
+
+package org.apache.derby.iapi.sql.dictionary;
+
+import org.apache.derby.iapi.error.StandardException;
+import org.apache.derby.catalog.UUID;
+import org.apache.derby.iapi.sql.conn.Authorizer;
+import org.apache.derby.iapi.sql.conn.LanguageConnectionContext;
+import org.apache.derby.iapi.reference.SQLState;
+import org.apache.derby.iapi.sql.dictionary.PermDescriptor;
+import org.apache.derby.iapi.store.access.TransactionController;
+import org.apache.derby.iapi.sql.Activation;
+import org.apache.derby.iapi.sql.execute.ExecPreparedStatement;
+import org.apache.derby.iapi.sql.depend.DependencyManager;
+import org.apache.derby.iapi.services.context.ContextManager;
+
+/**
+ * This class describes a generic permission (such as USAGE)
+ * required by a statement.
+ */
+
+public final class StatementGenericPermission extends StatementPermission
+{
+	private UUID _objectID;
+    private String _objectType; // e.g., PermDescriptor.SEQUENCE_TYPE
+    private String _privilege; // e.g., PermDescriptor.USAGE_PRIV
+
+	public StatementGenericPermission( UUID objectID, String objectType, String privilege )
+	{
+		_objectID = objectID;
+        _objectType = objectType;
+        _privilege = privilege;
+	}
+
+    // accessors
+	public UUID getObjectID() { return _objectID; }
+    public String getPrivilege() { return _privilege; }
+
+	/**
+	 * @see StatementPermission#getObjectType
+	 */
+    public String getObjectType() { return _objectType; }
+
+	/**
+	 * @see StatementPermission#check
+	 */
+	public void check( LanguageConnectionContext lcc,
+					   String authorizationId,
+					   boolean forGrant,
+					   Activation activation) throws StandardException
+	{
+        genericCheck( lcc, authorizationId, forGrant, activation, _privilege );
+	}
+
+
+	/**
+	 * @see StatementPermission#isCorrectPermission
+	 */
+    public boolean isCorrectPermission( PermissionsDescriptor raw )
+    {
+        if ( (raw == null) || !( raw instanceof PermDescriptor) ) { return false; }
+
+        PermDescriptor pd = (PermDescriptor) raw;
+        
+        return
+            pd.getPermObjectId().equals( _objectID ) &&
+            pd.getObjectType().equals( _objectType ) &&
+            pd.getPermission().equals( _privilege )
+            ;
+    }
+
+	/**
+	 * @see StatementPermission#getPrivilegedObject
+	 */
+    public PrivilegedSQLObject getPrivilegedObject( DataDictionary dd ) throws StandardException
+    {
+        if ( PermDescriptor.UDT_TYPE.equals( _objectType ) ) { return dd.getAliasDescriptor( _objectID ); }
+        else if ( PermDescriptor.SEQUENCE_TYPE.equals( _objectType ) ) { return dd.getSequenceDescriptor( _objectID ); }
+        else
+        {
+            throw StandardException.newException( SQLState.BTREE_UNIMPLEMENTED_FEATURE );
+        }
+    }
+
+	/**
+	 * @see StatementPermission#getPermissionDescriptor
+	 */
+	public PermissionsDescriptor getPermissionDescriptor(String authid, DataDictionary dd)
+	throws StandardException
+	{
+		return dd.getGenericPermissions( _objectID, _objectType, _privilege, authid );
+	}
+
+
+	public String toString()
+	{
+		return "StatementGenericPermission( " + _objectID + ", " + _objectType + ", " + _privilege + " )";
+	}
+}

Propchange: db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementGenericPermission.java
------------------------------------------------------------------------------
    svn:eol-style = native

Modified: db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementPermission.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementPermission.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementPermission.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementPermission.java Fri Dec 18 15:15:02 2009
@@ -21,9 +21,15 @@
 
 package org.apache.derby.iapi.sql.dictionary;
 
+import org.apache.derby.iapi.reference.SQLState;
+import org.apache.derby.iapi.sql.conn.Authorizer;
 import org.apache.derby.iapi.sql.conn.LanguageConnectionContext;
 import org.apache.derby.iapi.error.StandardException;
 import org.apache.derby.iapi.sql.Activation;
+import org.apache.derby.iapi.store.access.TransactionController;
+import org.apache.derby.iapi.sql.execute.ExecPreparedStatement;
+import org.apache.derby.iapi.sql.depend.DependencyManager;
+import org.apache.derby.iapi.services.context.ContextManager;
 
 /**
  * This class describes a permission require by a statement.
@@ -55,7 +61,7 @@
 
 	/**
 	 * 
-	 * Get the PermissionDescriptor for the passed authorization id for this
+	 * Get the PermissionsDescriptor for the passed authorization id for this
 	 * object. This method gets called during the execution phase of create 
 	 * view/constraint/trigger. The return value of this method is saved in
 	 * dependency system to keep track of views/constraints/triggers 
@@ -68,11 +74,150 @@
 	 * @param authid	AuthorizationId
 	 * @param dd	DataDictionary
 	 * 
-	 * @return PermissionsDescriptor	The PermissionDescriptor for the passed
+	 * @return PermissionsDescriptor	The PermissionsDescriptor for the passed
 	 *  authorization id on this object
 	 * 
 	 * @exception StandardException
 	 */
 	public abstract PermissionsDescriptor getPermissionDescriptor(String authid, DataDictionary dd)
 	throws StandardException;
+
+    /**
+     * Return true if the passed in permission matches the one required by this
+     * StatementPermission.
+     */
+    public boolean isCorrectPermission( PermissionsDescriptor pd ) throws StandardException
+    { return false; }
+
+    /**
+     * Get the privileged object associated with this permission.
+     */
+    public PrivilegedSQLObject getPrivilegedObject( DataDictionary dd ) throws StandardException
+    { return null; }
+
+    /**
+     * Get the type of the privileged object.
+     */
+    public String getObjectType()
+    { return null; }
+
+    /**
+     * Generic logic called by check() for USAGE and EXECUTE privileges. Throws
+     * an exception if the correct permission cannot be found.
+     */
+	public void genericCheck
+        (
+         LanguageConnectionContext lcc,
+         String authorizationId,
+         boolean forGrant,
+         Activation activation,
+         String privilegeType )
+        throws StandardException
+	{
+		DataDictionary dd = lcc.getDataDictionary();
+		TransactionController tc = lcc.getTransactionExecute();
+		ExecPreparedStatement ps = activation.getPreparedStatement();
+		
+		PermissionsDescriptor perm = getPermissionDescriptor( authorizationId, dd );
+		if( !isCorrectPermission( perm ) ) { perm = getPermissionDescriptor(Authorizer.PUBLIC_AUTHORIZATION_ID, dd ); }
+
+        // if the user has the correct permission, we're done
+		if ( isCorrectPermission( perm ) ) { return; }
+
+		boolean resolved = false;
+
+		// Since no permission exists for the current user or PUBLIC,
+		// check if a permission exists for the current role (if set).
+		String role = lcc.getCurrentRoleId(activation);
+
+		if (role != null) {
+
+			// Check that role is still granted to current user or
+			// to PUBLIC: A revoked role which is current for this
+			// session, is lazily set to none when it is attemped
+			// used.
+			String dbo = dd.getAuthorizationDatabaseOwner();
+			RoleGrantDescriptor rd = dd.getRoleGrantDescriptor
+				(role, authorizationId, dbo);
+
+			if (rd == null) {
+				rd = dd.getRoleGrantDescriptor(
+					role,
+					Authorizer.PUBLIC_AUTHORIZATION_ID,
+					dbo);
+			}
+
+			if (rd == null) {
+				// We have lost the right to set this role, so we can't
+				// make use of any permission granted to it or its
+				// ancestors.
+				lcc.setCurrentRole(activation, null);
+			} else {
+				// The current role is OK, so we can make use of
+				// any permission granted to it.
+				//
+				// Look at the current role and, if necessary, the
+				// transitive closure of roles granted to current role to
+				// see if permission has been granted to any of the
+				// applicable roles.
+
+				RoleClosureIterator rci =
+					dd.createRoleClosureIterator
+					(activation.getTransactionController(),
+					 role, true );
+
+				String r;
+				while (!resolved && (r = rci.next()) != null)
+                {
+					perm = getPermissionDescriptor( r, dd );
+
+					if ( isCorrectPermission( perm ) ) { resolved = true; }
+				}
+			}
+
+			if (resolved ) {
+				// Also add a dependency on the role (qua provider), so that if
+				// role is no longer available to the current user (e.g. grant
+				// is revoked, role is dropped, another role has been set), we
+				// are able to invalidate the ps or activation (the latter is
+				// used if the current role changes).
+				DependencyManager dm = dd.getDependencyManager();
+				RoleGrantDescriptor rgd = dd.getRoleDefinitionDescriptor(role);
+				ContextManager cm = lcc.getContextManager();
+				dm.addDependency(ps, rgd, cm);
+				dm.addDependency(activation, rgd, cm);
+			}
+		}
+
+		if (!resolved)
+        {
+            PrivilegedSQLObject pso = getPrivilegedObject( dd );
+
+			if( pso == null )
+            {
+				throw StandardException.newException
+                    ( SQLState.AUTH_INTERNAL_BAD_UUID, getObjectType() );
+            }
+
+			SchemaDescriptor sd = pso.getSchemaDescriptor();
+
+			if( sd == null)
+            {
+				throw StandardException.newException(
+					SQLState.AUTH_INTERNAL_BAD_UUID, "SCHEMA");
+            }
+
+			throw StandardException.newException(
+				(forGrant
+				 ? SQLState.AUTH_NO_GENERIC_PERMISSION_FOR_GRANT
+				 : SQLState.AUTH_NO_GENERIC_PERMISSION),
+				authorizationId,
+                privilegeType,
+				getObjectType(),
+				sd.getSchemaName(),
+				pso.getName());
+		}
+
+	} // end of genericCheck
+
 }

Modified: db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementRoutinePermission.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementRoutinePermission.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementRoutinePermission.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/iapi/sql/dictionary/StatementRoutinePermission.java Fri Dec 18 15:15:02 2009
@@ -64,111 +64,26 @@
 					   boolean forGrant,
 					   Activation activation) throws StandardException
 	{
-		DataDictionary dd = lcc.getDataDictionary();
-		TransactionController tc = lcc.getTransactionExecute();
-		ExecPreparedStatement ps = activation.getPreparedStatement();
-		
-		RoutinePermsDescriptor perms = dd.getRoutinePermissions( routineUUID, authorizationId);
-		if( perms == null || ! perms.getHasExecutePermission())
-			perms = dd.getRoutinePermissions(routineUUID, Authorizer.PUBLIC_AUTHORIZATION_ID);
-
-		if (perms != null && perms.getHasExecutePermission()) {
-			// The user or PUBLIC has execute permission, all is well.
-			return;
-		}
-
-		boolean resolved = false;
-
-		// Since no permission exists for the current user or PUBLIC,
-		// check if a permission exists for the current role (if set).
-		String role = lcc.getCurrentRoleId(activation);
-
-		if (role != null) {
-
-			// Check that role is still granted to current user or
-			// to PUBLIC: A revoked role which is current for this
-			// session, is lazily set to none when it is attemped
-			// used.
-			String dbo = dd.getAuthorizationDatabaseOwner();
-			RoleGrantDescriptor rd = dd.getRoleGrantDescriptor
-				(role, authorizationId, dbo);
-
-			if (rd == null) {
-				rd = dd.getRoleGrantDescriptor(
-					role,
-					Authorizer.PUBLIC_AUTHORIZATION_ID,
-					dbo);
-			}
-
-			if (rd == null) {
-				// We have lost the right to set this role, so we can't
-				// make use of any permission granted to it or its
-				// ancestors.
-				lcc.setCurrentRole(activation, null);
-			} else {
-				// The current role is OK, so we can make use of
-				// any permission granted to it.
-				//
-				// Look at the current role and, if necessary, the
-				// transitive closure of roles granted to current role to
-				// see if permission has been granted to any of the
-				// applicable roles.
-
-				RoleClosureIterator rci =
-					dd.createRoleClosureIterator
-					(activation.getTransactionController(),
-					 role, true /* inverse relation*/);
-
-				String r;
-				while (!resolved && (r = rci.next()) != null) {
-					perms = dd.
-						getRoutinePermissions(routineUUID, r);
-
-					if (perms != null &&
-							perms.getHasExecutePermission()) {
-						resolved = true;
-					}
-				}
-			}
-
-			if (resolved /* using a role*/) {
-				// Also add a dependency on the role (qua provider), so that if
-				// role is no longer available to the current user (e.g. grant
-				// is revoked, role is dropped, another role has been set), we
-				// are able to invalidate the ps or activation (the latter is
-				// used if the current role changes).
-				DependencyManager dm = dd.getDependencyManager();
-				RoleGrantDescriptor rgd = dd.getRoleDefinitionDescriptor(role);
-				ContextManager cm = lcc.getContextManager();
-				dm.addDependency(ps, rgd, cm);
-				dm.addDependency(activation, rgd, cm);
-			}
-		}
-
-		if (!resolved) {
-			AliasDescriptor ad = dd.getAliasDescriptor( routineUUID);
-
-			if( ad == null)
-				throw StandardException.newException(
-					SQLState.AUTH_INTERNAL_BAD_UUID, "routine");
-
-			SchemaDescriptor sd = dd.getSchemaDescriptor(
-				ad.getSchemaUUID(), tc);
-
-			if( sd == null)
-				throw StandardException.newException(
-					SQLState.AUTH_INTERNAL_BAD_UUID, "schema");
-
-			throw StandardException.newException(
-				(forGrant
-				 ? SQLState.AUTH_NO_EXECUTE_PERMISSION_FOR_GRANT
-				 : SQLState.AUTH_NO_EXECUTE_PERMISSION),
-				authorizationId,
-				ad.getDescriptorType(),
-				sd.getSchemaName(),
-				ad.getDescriptorName());
-		}
-	} // end of check
+        genericCheck( lcc, authorizationId, forGrant, activation, "EXECUTE" );
+	}
+
+	/**
+	 * @see StatementPermission#isCorrectPermission
+	 */
+    public boolean isCorrectPermission( PermissionsDescriptor raw )
+    {
+        if ( (raw == null) || !( raw instanceof RoutinePermsDescriptor) ) { return false; }
+
+        RoutinePermsDescriptor pd = (RoutinePermsDescriptor) raw;
+        
+        return pd.getHasExecutePermission();
+    }
+
+	/**
+	 * @see StatementPermission#getPrivilegedObject
+	 */
+    public PrivilegedSQLObject getPrivilegedObject( DataDictionary dd ) throws StandardException
+    { return dd.getAliasDescriptor( routineUUID); }
 
 	/**
 	 * @see StatementPermission#getPermissionDescriptor
@@ -179,6 +94,10 @@
 		return dd.getRoutinePermissions(routineUUID,authid);
 	}
 
+	/**
+	 * @see StatementPermission#getObjectType
+	 */
+    public String getObjectType() { return "ROUTINE"; }
 
 	public String toString()
 	{

Modified: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/CoreDDFinderClassInfo.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/CoreDDFinderClassInfo.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/CoreDDFinderClassInfo.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/CoreDDFinderClassInfo.java Fri Dec 18 15:15:02 2009
@@ -52,6 +52,8 @@
 			case StoredFormatIds.TABLE_PERMISSION_FINDER_V01_ID:
 			case StoredFormatIds.ROUTINE_PERMISSION_FINDER_V01_ID:
 			case StoredFormatIds.COLUMNS_PERMISSION_FINDER_V01_ID:
+		    case StoredFormatIds.SEQUENCE_DESCRIPTOR_FINDER_V01_ID:
+		    case StoredFormatIds.PERM_DESCRIPTOR_FINDER_V01_ID:
 		    case StoredFormatIds.ROLE_GRANT_FINDER_V01_ID:
 				return new DDdependableFinder(fmtId);
 			case StoredFormatIds.COLUMN_DESCRIPTOR_FINDER_V01_ID:

Modified: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/DDdependableFinder.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/DDdependableFinder.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/DDdependableFinder.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/DDdependableFinder.java Fri Dec 18 15:15:02 2009
@@ -178,6 +178,12 @@
 			case StoredFormatIds.ROLE_GRANT_FINDER_V01_ID:
 				return Dependable.ROLE_GRANT;
 
+			case StoredFormatIds.SEQUENCE_DESCRIPTOR_FINDER_V01_ID:
+				return Dependable.SEQUENCE;
+
+			case StoredFormatIds.PERM_DESCRIPTOR_FINDER_V01_ID:
+				return Dependable.PERM;
+
 			default:
 				if (SanityManager.DEBUG)
 				{
@@ -261,6 +267,12 @@
 		    case StoredFormatIds.ROLE_GRANT_FINDER_V01_ID:
 				return dd.getRoleGrantDescriptor(dependableObjectID);
 
+			case StoredFormatIds.SEQUENCE_DESCRIPTOR_FINDER_V01_ID:
+                return dd.getSequenceDescriptor(dependableObjectID);
+
+			case StoredFormatIds.PERM_DESCRIPTOR_FINDER_V01_ID:
+                return dd.getGenericPermissions(dependableObjectID);
+
 		default:
 				if (SanityManager.DEBUG)
 				{

Modified: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/DataDictionaryImpl.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/DataDictionaryImpl.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/DataDictionaryImpl.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/DataDictionaryImpl.java Fri Dec 18 15:15:02 2009
@@ -12230,20 +12230,27 @@
         if( existingRow == null)
         {
             if( ! add)
+            {
             	//we didn't find an entry in system catalog and this is revoke
             	//so that means there is nothing to revoke. Simply return.
             	//No need to reset permission descriptor's uuid because
             	//no row was ever found in system catalog for the given
             	//permission and hence uuid can't be non-null
                 return false;
-            //We didn't find an entry in system catalog and this is grant so 
-            //so that means we have to enter a new row in system catalog for
-            //this grant.
-            ExecRow row = ti.getCatalogRowFactory().makeRow( perm, (TupleDescriptor) null);
-            int insertRetCode = ti.insertRow(row, tc);
-            if( SanityManager.DEBUG)
-                SanityManager.ASSERT( insertRetCode == TabInfoImpl.ROWNOTDUPLICATE,
-                                      "Race condition in inserting table privilege.");
+            }
+            else
+            {
+                //We didn't find an entry in system catalog and this is grant so 
+                //so that means we have to enter a new row in system catalog for
+                //this grant.
+                ExecRow row = ti.getCatalogRowFactory().makeRow( perm, (TupleDescriptor) null);
+                int insertRetCode = ti.insertRow(row, tc);
+                if( SanityManager.DEBUG)
+                {
+                    SanityManager.ASSERT( insertRetCode == TabInfoImpl.ROWNOTDUPLICATE,
+                                          "Race condition in inserting table privilege.");
+                }
+            }
         }
         else
         {
@@ -12252,9 +12259,14 @@
             boolean[] indicesToUpdate = new boolean[ rf.getNumIndexes()];
             int changedColCount = 0;
             if( add)
+            {
                 changedColCount = rf.orPermissions( existingRow, perm, colsChanged);
+            }
             else
+            {
                 changedColCount = rf.removePermissions( existingRow, perm, colsChanged);
+            }
+            
             if( changedColCount == 0)
             {
             	//grant/revoke privilege didn't change anything and hence 
@@ -12285,10 +12297,12 @@
                         colsToUpdate[ changedColCount++] = i + 1;
                 }
                 if( SanityManager.DEBUG)
+                {
                     SanityManager.ASSERT(
                         changedColCount == colsToUpdate.length,
                         "return value of " + rf.getClass().getName() +
                         ".orPermissions does not match the number of booleans it set in colsChanged.");
+                }
                 ti.updateRow(key, existingRow, primaryIndexNumber,
                              indicesToUpdate, colsToUpdate, tc);
             }
@@ -12301,8 +12315,13 @@
         //If we are dealing with grant, then the caller does not need to send 
         //any invalidation actions to anyone and hence return false
         if (add)
+        {
         	return false;
-        return true;
+        }
+        else
+        {
+            return true;
+        }
     } // end of addPermissionsDescriptor
 
     /**
@@ -12786,30 +12805,47 @@
      * , null if no table-level permissions have been granted to him on the table.
      * @throws StandardException
      */
-    PermDescriptor getUncachedPermDescriptor(PermDescriptor key)
-            throws StandardException {
-
-        return (PermDescriptor)
+    PermDescriptor getUncachedGenericPermDescriptor(PermDescriptor key)
+            throws StandardException
+    {
+    	if (key.getObjectID() == null)
+    	{
+    		//the PERMISSSIONID for SYSRPERMS is not known, so use the id of the
+    		//protected object plus the
+    		//grantor and granteee to find a PermDescriptor
+            return (PermDescriptor)
                 getUncachedPermissionsDescriptor(SYSPERMS_CATALOG_NUM,
-                        SYSPERMSRowFactory.PERMS_UUID_IDX_NUM, key);
-
+                        SYSPERMSRowFactory.GRANTEE_OBJECTID_GRANTOR_INDEX_NUM, key);
+    	} else
+    	{
+    		//we know the PERMISSIONID for SYSPERMS, so use that to
+    		//find a PermDescriptor from the sytem table
+    		return (PermDescriptor)
+			getUncachedPermissionsDescriptor(SYSPERMS_CATALOG_NUM,
+					SYSPERMSRowFactory.PERMS_UUID_IDX_NUM,key);
+    	}
 
-    } // end of getUncachedPermDescriptor
+    } // end of getUncachedGenericPermDescriptor
 
     /**
      * Get permissions granted to one user for an object using the object's Id
      * and the user's authorization Id.
      *
-     * @param objectUUID
+     * @param objectUUID The id of the protected object
+     * @param objectType Type of the object (e.g., SEQUENCE)
+     * @param privilege The kind of privilege needed (e.g., PermDescriptor.USAGE_PRIV)
+     * @param granteeAuthid The user or role who wants to have permission on this object
      *
      * @return The descriptor of the permissions for the object
      *
      * @exception StandardException
      */
-    public PermDescriptor getPermissions(UUID objectUUID, String granteeAuthId)
-        throws StandardException {
-        PermDescriptor key = new PermDescriptor(this, null, null, objectUUID, null, null, granteeAuthId, false);
-        return getUncachedPermDescriptor(key);
+    public PermDescriptor getGenericPermissions(UUID objectUUID, String objectType, String privilege, String granteeAuthId)
+        throws StandardException
+    {
+        PermDescriptor key = new PermDescriptor( this, null, objectType, objectUUID, privilege, null, granteeAuthId, false );
+        
+        return (PermDescriptor) getPermissions( key);
     }
 
     /**
@@ -12819,10 +12855,10 @@
      * @return The descriptor of the user's permissions for the object.
      * @throws StandardException
      */
-    public PermDescriptor getPermissions(UUID permUUID)
+    public PermDescriptor getGenericPermissions(UUID permUUID)
             throws StandardException {
         PermDescriptor key = new PermDescriptor(this, permUUID);
-        return getUncachedPermDescriptor(key);
+        return getUncachedGenericPermDescriptor(key);
     }
 
     /**

Modified: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/PermissionsCacheable.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/PermissionsCacheable.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/PermissionsCacheable.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/PermissionsCacheable.java Fri Dec 18 15:15:02 2009
@@ -21,6 +21,8 @@
 
 package org.apache.derby.impl.sql.catalog;
 
+import org.apache.derby.catalog.UUID;
+
 import org.apache.derby.iapi.error.StandardException;
 
 import org.apache.derby.iapi.services.cache.Cacheable;
@@ -29,13 +31,14 @@
 
 import org.apache.derby.iapi.sql.conn.Authorizer;
 import org.apache.derby.iapi.sql.conn.ConnectionUtil;
-
 import org.apache.derby.iapi.sql.dictionary.TableDescriptor;
 import org.apache.derby.iapi.sql.dictionary.SchemaDescriptor;
 import org.apache.derby.iapi.sql.dictionary.AliasDescriptor;
 import org.apache.derby.iapi.sql.dictionary.TablePermsDescriptor;
+import org.apache.derby.iapi.sql.dictionary.PermDescriptor;
 import org.apache.derby.iapi.sql.dictionary.PermissionsDescriptor;
 import org.apache.derby.iapi.sql.dictionary.ColPermsDescriptor;
+import org.apache.derby.iapi.sql.dictionary.PrivilegedSQLObject;
 import org.apache.derby.iapi.sql.dictionary.RoutinePermsDescriptor;
 
 import org.apache.derby.iapi.services.sanity.SanityManager;
@@ -138,14 +141,44 @@
 				}
 			}
 		}
+		else if( key instanceof PermDescriptor)
+		{
+			PermDescriptor permKey = (PermDescriptor) key;
+			permissions = dd.getUncachedGenericPermDescriptor( permKey);
+			if( permissions == null)
+			{
+				// The owner has all privileges unless they have been revoked.
+                String objectType = permKey.getObjectType();
+                String privilege = permKey.getPermission();
+                UUID protectedObjectsID = permKey.getPermObjectId();
+                
+                
+                PrivilegedSQLObject pso = PermDescriptor.getProtectedObject( dd, protectedObjectsID, objectType );
+                SchemaDescriptor sd = pso.getSchemaDescriptor();
+                if( permKey.getGrantee().equals( sd.getAuthorizationId()))
+                {
+                    permissions = new PermDescriptor
+                        (
+                         dd,
+                         null,
+                         objectType,
+                         pso.getUUID(),
+                         privilege,
+                         Authorizer.SYSTEM_AUTHORIZATION_ID,
+                         permKey.getGrantee(),
+                         true
+                         );
+                }
+			}
+		}
 		else
 		{
 			if( SanityManager.DEBUG)
 				SanityManager.NOTREACHED();
 			return null;
 		}
-		if( permissions != null)
-			return this;
+		if( permissions != null) { return this; }
+    
 		return null;
 	} // end of setIdentity
 

Modified: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/SYSPERMSRowFactory.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/SYSPERMSRowFactory.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/SYSPERMSRowFactory.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/catalog/SYSPERMSRowFactory.java Fri Dec 18 15:15:02 2009
@@ -61,22 +61,23 @@
     private static final int[][] indexColumnPositions =
             {
                     {SYSPERMS_PERMISSIONID},
-                    {SYSPERMS_OBJECTID}
+                    {SYSPERMS_OBJECTID},
+                    {SYSPERMS_GRANTEE, SYSPERMS_OBJECTID, SYSPERMS_GRANTOR},
             };
 
-    // UUID
-    static final int PERMS_UUID_IDX_NUM = 0;
-
-    // object Id
+    // index numbers
+    public static final int PERMS_UUID_IDX_NUM = 0;
     public static final int PERMS_OBJECTID_IDX_NUM = 1;
+    public static final int GRANTEE_OBJECTID_GRANTOR_INDEX_NUM = 2;
 
-    private static final boolean[] uniqueness = { true, false };
+    private static final boolean[] uniqueness = { true, false, true };
 
     private static final String[] uuids = {
             "9810800c-0121-c5e1-a2f5-00000043e718", // catalog UUID
             "6ea6ffac-0121-c5e3-f286-00000043e718", // heap UUID
-            "5cc556fc-0121-c5e6-4e43-00000043e718",  // uuid index
-            "7a92cf84-0122-51e6-2c5e-00000047b548"   // object id index
+            "5cc556fc-0121-c5e6-4e43-00000043e718",  // PERMS_UUID_IDX_NUM
+            "7a92cf84-0122-51e6-2c5e-00000047b548",   // PERMS_OBJECTID_IDX_NUM
+            "9810800c-0125-8de5-3aa0-0000001999e8",   // GRANTEE_OBJECTID_GRANTOR_INDEX_NUM
     };
 
 
@@ -105,7 +106,18 @@
         ExecIndexRow row = null;
 
         switch (indexNumber) {
-            case PERMS_UUID_IDX_NUM:
+        case GRANTEE_OBJECTID_GRANTOR_INDEX_NUM:
+            // RESOLVE We do not support the FOR GRANT OPTION, so generic permission rows are unique on the
+            // grantee and object UUID columns. The grantor column will always have the name of the owner of the
+            // object. So the index key, used for searching the index, only has grantee and object UUID columns.
+            // It does not have a grantor column.
+            row = getExecutionFactory().getIndexableRow( 2 );
+            row.setColumn(1, getAuthorizationID( perm.getGrantee()));
+            String protectedObjectsIDStr = ((PermDescriptor) perm).getPermObjectId().toString();
+            row.setColumn(2, new SQLChar(protectedObjectsIDStr));
+            break;
+
+        case PERMS_UUID_IDX_NUM:
                 row = getExecutionFactory().getIndexableRow(1);
                 String permUUIDStr = ((PermDescriptor) perm).getUUID().toString();
                 row.setColumn(1, new SQLChar(permUUIDStr));
@@ -114,6 +126,11 @@
         return row;
     } // end of buildIndexKeyRow
 
+    public int getPrimaryKeyIndexNumber()
+    {
+        return GRANTEE_OBJECTID_GRANTOR_INDEX_NUM;
+    }
+
     /**
      * Or a set of permissions in with a row from this catalog table
      *
@@ -141,11 +158,16 @@
      */
     public int removePermissions(ExecRow row, PermissionsDescriptor perm, boolean[] colsChanged)
             throws StandardException {
-        return -1; // There is only one kind of routine privilege so delete the whole row.
+        return -1; // There is only one kind of privilege per row so delete the whole row.
     } // end of removePermissions
 
-    void setUUIDOfThePassedDescriptor(ExecRow row, PermissionsDescriptor perm) throws StandardException {
-        //To change body of implemented methods use File | Settings | File Templates.
+	/** 
+	 * @see PermissionsCatalogRowFactory#setUUIDOfThePassedDescriptor
+	 */
+    void setUUIDOfThePassedDescriptor(ExecRow row, PermissionsDescriptor perm) throws StandardException
+    {
+        DataValueDescriptor existingPermDVD = row.getColumn(SYSPERMS_PERMISSIONID);
+        perm.setUUID(getUUIDFactory().recreateUUID(existingPermDVD.getString()));
     }
 
     /**
@@ -172,6 +194,11 @@
         if (td != null) {
             PermDescriptor sd = (PermDescriptor) td;
             UUID pid = sd.getUUID();
+            if ( pid == null )
+            {
+				pid = getUUIDFactory().createUUID();
+				sd.setUUID(pid);
+            }
             permIdString = pid.toString();
 
             objectType = sd.getObjectType();

Modified: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/CompilerContextImpl.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/CompilerContextImpl.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/CompilerContextImpl.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/CompilerContextImpl.java Fri Dec 18 15:15:02 2009
@@ -38,6 +38,9 @@
 import org.apache.derby.iapi.sql.dictionary.ColumnDescriptor;
 import org.apache.derby.iapi.sql.dictionary.TableDescriptor;
 import org.apache.derby.iapi.sql.dictionary.AliasDescriptor;
+import org.apache.derby.iapi.sql.dictionary.PermDescriptor;
+import org.apache.derby.iapi.sql.dictionary.PrivilegedSQLObject;
+import org.apache.derby.iapi.sql.dictionary.StatementGenericPermission;
 import org.apache.derby.iapi.sql.dictionary.StatementTablePermission;
 import org.apache.derby.iapi.sql.dictionary.StatementSchemaPermission;
 import org.apache.derby.iapi.sql.dictionary.StatementColumnPermission;
@@ -705,6 +708,7 @@
 		requiredTablePrivileges = null;
 		requiredSchemaPrivileges = null;
 		requiredRoutinePrivileges = null;
+		requiredUsagePrivileges = null;
 		requiredRolePrivileges = null;
 		LanguageConnectionContext lcc = (LanguageConnectionContext)
 		getContextManager().getContext(LanguageConnectionContext.CONTEXT_ID);
@@ -714,6 +718,7 @@
 			requiredTablePrivileges = new HashMap();
 			requiredSchemaPrivileges = new HashMap();
 			requiredRoutinePrivileges = new HashMap();
+			requiredUsagePrivileges = new HashMap();
 			requiredRolePrivileges = new HashMap();
 		}
 	} // end of initRequiredPriv
@@ -828,6 +833,20 @@
 	}
 
 	/**
+	 * @see CompilerContext#addRequiredUsagePriv
+	 */
+	public void addRequiredUsagePriv( PrivilegedSQLObject usableObject )
+    {
+		if( requiredUsagePrivileges == null || usableObject == null) { return; }
+
+        UUID objectID = usableObject.getUUID();
+        String objectType = usableObject.getObjectTypeName();
+
+ 		if (requiredUsagePrivileges.get( objectID ) == null)
+        { requiredUsagePrivileges.put( objectID, objectType ); }
+    }
+    
+	/**
 	 * Add a required schema privilege to the list privileges.
 	 *
 	 * @see CompilerContext#addRequiredSchemaPriv
@@ -868,15 +887,17 @@
 	{
 		int size = 0;
 		if( requiredRoutinePrivileges != null)
-			size += requiredRoutinePrivileges.size();
+        { size += requiredRoutinePrivileges.size(); }
+		if( requiredUsagePrivileges != null)
+        { size += requiredUsagePrivileges.size(); }
 		if( requiredTablePrivileges != null)
-			size += requiredTablePrivileges.size();
+        { size += requiredTablePrivileges.size(); }
 		if( requiredSchemaPrivileges != null)
-			size += requiredSchemaPrivileges.size();
+        { size += requiredSchemaPrivileges.size(); }
 		if( requiredColumnPrivileges != null)
-			size += requiredColumnPrivileges.size();
+        { size += requiredColumnPrivileges.size(); }
 		if( requiredRolePrivileges != null)
-			size += requiredRolePrivileges.size();
+        { size += requiredRolePrivileges.size(); }
 		
 		ArrayList list = new ArrayList( size);
 		if( requiredRoutinePrivileges != null)
@@ -888,6 +909,15 @@
 				list.add( new StatementRoutinePermission( routineUUID));
 			}
 		}
+		if( requiredUsagePrivileges != null)
+		{
+			for( Iterator itr = requiredUsagePrivileges.keySet().iterator(); itr.hasNext();)
+			{
+				UUID objectID = (UUID) itr.next();
+				
+				list.add( new StatementGenericPermission( objectID, (String) requiredUsagePrivileges.get( objectID ), PermDescriptor.USAGE_PRIV ) );
+			}
+		}
 		if( requiredTablePrivileges != null)
 		{
 			for( Iterator itr = requiredTablePrivileges.values().iterator(); itr.hasNext();)
@@ -973,5 +1003,6 @@
 	private HashMap requiredTablePrivileges;
 	private HashMap requiredSchemaPrivileges;
 	private HashMap requiredRoutinePrivileges;
+	private HashMap requiredUsagePrivileges;
 	private HashMap requiredRolePrivileges;
 } // end of class CompilerContextImpl

Modified: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/PrivilegeNode.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/PrivilegeNode.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/PrivilegeNode.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/PrivilegeNode.java Fri Dec 18 15:15:02 2009
@@ -28,9 +28,11 @@
 import org.apache.derby.iapi.sql.dictionary.DataDictionary;
 import org.apache.derby.iapi.sql.dictionary.TableDescriptor;
 import org.apache.derby.iapi.sql.dictionary.AliasDescriptor;
+import org.apache.derby.iapi.sql.dictionary.PrivilegedSQLObject;
 import org.apache.derby.catalog.types.RoutineAliasInfo;
 import org.apache.derby.catalog.AliasInfo;
 import org.apache.derby.iapi.reference.SQLState;
+import org.apache.derby.impl.sql.execute.GenericPrivilegeInfo;
 import org.apache.derby.impl.sql.execute.PrivilegeInfo;
 import org.apache.derby.catalog.TypeDescriptor;
 
@@ -45,20 +47,34 @@
     // Privilege object type
     public static final int TABLE_PRIVILEGES = 0;
     public static final int ROUTINE_PRIVILEGES = 1;
+    public static final int SEQUENCE_PRIVILEGES = 2;
+    public static final int UDT_PRIVILEGES = 3;
 
+    //
+    // State initialized when the node is instantiated
+    //
     private int objectType;
     private TableName objectName;
     private TablePrivilegesNode specificPrivileges; // Null for routine and usage privs
     private RoutineDesignator routineDesignator; // null for table and usage privs
 
+    private String privilege;  // E.g., PermDescriptor.USAGE_PRIV
+    private boolean restrict;
+
+    //
+    // State which is filled in by the bind() logic.
+    //
+    private Provider dependencyProvider;
+    
     /**
-     * initialize a PrivilegesNode
+     * Initialize a PrivilegeNode for use against SYS.SYSTABLEPERMS and SYS.SYSROUTINEPERMS.
      *
      * @param objectType (an Integer)
      * @param objectOfPrivilege (a TableName or RoutineDesignator)
-     * @param specificPrivileges null for routines
+     * @param specificPrivileges null for routines and usage
      */
     public void init( Object objectType, Object objectOfPrivilege, Object specificPrivileges)
+        throws StandardException
     {
         this.objectType = ((Integer) objectType).intValue();
         if( SanityManager.DEBUG)
@@ -89,14 +105,27 @@
             break;
             
         default:
-            if( SanityManager.DEBUG)
-            {
-                SanityManager.THROWASSERT( "Invalid privilege objectType: " + this.objectType);
-            }
+            throw unimplementedFeature();
         }
     }
 
     /**
+     * Initialize a PrivilegeNode for use against SYS.SYSPERMS.
+     *
+     * @param objectType E.g., SEQUENCE
+     * @param objectName A possibles schema-qualified name
+     * @param privilege A PermDescriptor privilege, e.g. PermDescriptor.USAGE_PRIV
+     * @param restrict True if this is a REVOKE...RESTRICT action
+     */
+    public void init( Object objectType, Object objectName, Object privilege, Object restrict )
+    {
+        this.objectType = ((Integer) objectType).intValue();
+        this.objectName = (TableName) objectName;
+        this.privilege = (String) privilege;
+        this.restrict = ((Boolean) restrict).booleanValue();
+    }
+    
+    /**
      * Bind this GrantNode. Resolve all table, column, and routine references. Register
      * a dependency on the object of the privilege if it has not already been done
      *
@@ -111,7 +140,6 @@
      */
 	public QueryTreeNode bind( HashMap dependencies, List grantees, boolean isGrant ) throws StandardException
 	{
-        Provider dependencyProvider = null;
         SchemaDescriptor sd = getSchemaDescriptor( objectName.getSchemaName(), true);
         objectName.setSchemaName( sd.getSchemaName() );
         
@@ -229,11 +257,27 @@
             dependencyProvider = proc;
             break;
 
-        default:
-            if( SanityManager.DEBUG)
+        case SEQUENCE_PRIVILEGES:
+            
+            dependencyProvider = getDataDictionary().getSequenceDescriptor( sd, objectName.getTableName() );
+            if ( dependencyProvider == null )
+            {
+                throw StandardException.newException(SQLState.LANG_OBJECT_NOT_FOUND, "SEQUENCE", objectName.getFullTableName());
+            }
+            break;
+            
+        case UDT_PRIVILEGES:
+            
+            dependencyProvider = getDataDictionary().getAliasDescriptor
+                ( sd.getUUID().toString(), objectName.getTableName(), AliasInfo.ALIAS_NAME_SPACE_UDT_AS_CHAR  );
+            if ( dependencyProvider == null )
             {
-                SanityManager.THROWASSERT( "Invalid privilege objectType: " + this.objectType);
+                throw StandardException.newException(SQLState.LANG_OBJECT_NOT_FOUND, "TYPE", objectName.getFullTableName());
             }
+            break;
+            
+        default:
+            throw unimplementedFeature();
         }
 
         if( dependencyProvider != null)
@@ -247,10 +291,11 @@
         return this;
     } // end of bind
 
+
     /**
      * @return PrivilegeInfo for this node
      */
-    PrivilegeInfo makePrivilegeInfo()
+    PrivilegeInfo makePrivilegeInfo() throws StandardException
     {
         switch( objectType)
         {
@@ -259,7 +304,19 @@
 
         case ROUTINE_PRIVILEGES:
             return routineDesignator.makePrivilegeInfo();
+
+        case SEQUENCE_PRIVILEGES:
+        case UDT_PRIVILEGES:
+            return new GenericPrivilegeInfo( (PrivilegedSQLObject) dependencyProvider, privilege, restrict );
+
+        default:
+            throw unimplementedFeature();
         }
-        return null;
+    }
+
+    /** Report an unimplemented feature */
+    private StandardException unimplementedFeature()
+    {
+        return StandardException.newException( SQLState.BTREE_UNIMPLEMENTED_FEATURE );
     }
 }

Modified: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/QueryTreeNode.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/QueryTreeNode.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/QueryTreeNode.java (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/QueryTreeNode.java Fri Dec 18 15:15:02 2009
@@ -1652,6 +1652,8 @@
 			throw StandardException.newException(SQLState.LANG_OBJECT_NOT_FOUND, ad.getAliasType(udtNameSpace),  unqualifiedTypeName);
 		}
 
+        createTypeDependency( ad );
+
         DataTypeDescriptor result = new DataTypeDescriptor
             (
              TypeId.getUserDefinedTypeId( typeSchema.getSchemaName(), unqualifiedTypeName, ad.getJavaClassName() ),
@@ -1662,7 +1664,8 @@
     }
 
     /**
-     * Declare a dependency on a type. This is only used if the type is an ANSI UDT.
+     * Declare a dependency on a type and check that you have privilege to use
+     * it. This is only used if the type is an ANSI UDT.
      *
      * @param dtd Type which may have a dependency declared on it.
      */
@@ -1670,9 +1673,19 @@
     {
         AliasDescriptor ad = getDataDictionary().getAliasDescriptorForUDT( null, dtd );
 
-        if ( ad != null )
+        if ( ad != null ) { createTypeDependency( ad ); }
+    }
+    /**
+     * Declare a dependency on an ANSI UDT, identified by its AliasDescriptor,
+     * and check that you have privilege to use it.
+     */
+    private void createTypeDependency( AliasDescriptor ad ) throws StandardException
+    {
+        getCompilerContext().createDependency( ad );
+
+        if ( isPrivilegeCollectionRequired() )
         {
-            getCompilerContext().createDependency( ad );
+            getCompilerContext().addRequiredUsagePriv( ad );
         }
     }
     

Modified: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/sqlgrammar.jj
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/sqlgrammar.jj?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/sqlgrammar.jj (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/compile/sqlgrammar.jj Fri Dec 18 15:15:02 2009
@@ -107,6 +107,7 @@
 import org.apache.derby.impl.sql.compile.CharStream;
 import org.apache.derby.impl.sql.execute.TablePrivilegeInfo;
 import org.apache.derby.iapi.sql.dictionary.DataDictionary;
+import org.apache.derby.iapi.sql.dictionary.PermDescriptor;
 import org.apache.derby.iapi.sql.dictionary.TableDescriptor;
 import org.apache.derby.iapi.sql.dictionary.TriggerDescriptor;
 import org.apache.derby.iapi.sql.dictionary.ViewDescriptor;
@@ -1713,6 +1714,7 @@
 				tokenKind == UPDATE ||
 				tokenKind == REFERENCES ||
 				tokenKind == EXECUTE ||
+				tokenKind == USAGE ||
 				tokenKind == ALL);
 	}
 
@@ -13290,7 +13292,11 @@
 		checkVersion( DataDictionary.DD_VERSION_DERBY_10_2, "GRANT");
 		checkSqlStandardAccess( "GRANT");
 	}
-	( node = tableGrantStatement() | node = routineGrantStatement() )
+	(
+        node = tableGrantStatement() |
+        node = routineGrantStatement() |
+        node = usageGrantStatement()
+    )
 	{
 		return node;
 	}
@@ -13392,6 +13398,61 @@
 }// end of routineGrantStatement
 
 /*
+ * <A NAME="usageGrantStatement">usageGrantStatement</A>
+ */
+StatementNode
+usageGrantStatement() throws StandardException :
+{
+    List grantees;
+    TableName name;
+    Integer objectType;
+}
+{
+    <USAGE> <ON>
+    objectType = usableObjects()
+    name = qualifiedName(Limits.MAX_IDENTIFIER_LENGTH)
+    <TO> grantees = granteeList()
+    {
+		checkVersion( DataDictionary.DD_VERSION_DERBY_10_6, "GRANT USAGE");
+        PrivilegeNode privilegeNode = (PrivilegeNode) nodeFactory.getNode
+            (
+                C_NodeTypes.PRIVILEGE_NODE,
+                objectType,
+                name,
+                PermDescriptor.USAGE_PRIV,
+                Boolean.FALSE,
+                getContextManager()
+            );
+        return (StatementNode) nodeFactory.getNode
+            (
+                C_NodeTypes.GRANT_NODE,
+                privilegeNode,
+                grantees,
+                getContextManager()
+            );
+    }
+}// end of usageGrantStatement
+
+/*
+ * <A NAME="usableObjects">usableObjects</A>
+ */
+Integer
+usableObjects() throws StandardException :
+{
+}
+{
+    <SEQUENCE>
+    {
+        return ReuseFactory.getInteger( PrivilegeNode.SEQUENCE_PRIVILEGES);
+    }
+|
+    <TYPE>
+    {
+        return ReuseFactory.getInteger( PrivilegeNode.UDT_PRIVILEGES);
+    }
+}// end of routineGrantStatement
+
+/*
  * <A NAME="routineAlias">routineAlias</A>
  */
 RoutineDesignator routineDesignator() throws StandardException :
@@ -13617,7 +13678,11 @@
 		checkVersion( DataDictionary.DD_VERSION_DERBY_10_2, "REVOKE");
 		checkSqlStandardAccess( "REVOKE");
 	}
-	( node = tableRevokeStatement() | node = routineRevokeStatement() )
+	(
+        node = tableRevokeStatement() |
+        node = routineRevokeStatement() |
+        node = usageRevokeStatement()
+    )
 	{
 		return node;
 	}
@@ -13682,6 +13747,42 @@
     }
 }// end of routineRevokeStatement
 
+/*
+ * <A NAME="usageRevokeStatement">usageRevokeStatement</A>
+ */
+StatementNode
+usageRevokeStatement() throws StandardException :
+{
+    List grantees;
+    TableName name;
+    Integer objectType;
+}
+{
+    <USAGE> <ON>
+    objectType = usableObjects()
+    name = qualifiedName(Limits.MAX_IDENTIFIER_LENGTH)
+    <FROM> grantees = granteeList() <RESTRICT>
+    {
+		checkVersion( DataDictionary.DD_VERSION_DERBY_10_6, "REVOKE USAGE");
+        PrivilegeNode privilegeNode = (PrivilegeNode) nodeFactory.getNode
+            (
+                C_NodeTypes.PRIVILEGE_NODE,
+                objectType,
+                name,
+                PermDescriptor.USAGE_PRIV,
+                Boolean.TRUE,
+                getContextManager()
+            );
+        return (StatementNode) nodeFactory.getNode
+            (
+                C_NodeTypes.REVOKE_NODE,
+                privilegeNode,
+                grantees,
+                getContextManager()
+            );
+    }
+}// end of usageRevokeStatement
+
 
 /*
  * <A NAME="roleRevokeStatement">roleRevokeStatement</A>

Added: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/execute/GenericPrivilegeInfo.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/execute/GenericPrivilegeInfo.java?rev=892272&view=auto
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/execute/GenericPrivilegeInfo.java (added)
+++ db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/execute/GenericPrivilegeInfo.java Fri Dec 18 15:15:02 2009
@@ -0,0 +1,143 @@
+/*
+
+   Derby - Class org.apache.derby.impl.sql.execute.GenericPrivilegeInfo
+
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to you under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+	  http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+
+ */
+
+package org.apache.derby.impl.sql.execute;
+
+import org.apache.derby.iapi.sql.Activation;
+import org.apache.derby.iapi.services.sanity.SanityManager;
+import org.apache.derby.iapi.sql.conn.LanguageConnectionContext;
+import org.apache.derby.iapi.store.access.TransactionController;
+import org.apache.derby.iapi.sql.depend.DependencyManager;
+import org.apache.derby.iapi.sql.dictionary.DataDictionary;
+import org.apache.derby.iapi.sql.dictionary.DataDescriptorGenerator;
+import org.apache.derby.iapi.sql.dictionary.PermDescriptor;
+import org.apache.derby.iapi.sql.dictionary.SchemaDescriptor;
+import org.apache.derby.iapi.sql.dictionary.PrivilegedSQLObject;
+import org.apache.derby.iapi.sql.dictionary.TupleDescriptor;
+import org.apache.derby.iapi.error.StandardException;
+import org.apache.derby.catalog.UUID;
+
+import java.util.Iterator;
+import java.util.List;
+
+public class GenericPrivilegeInfo extends PrivilegeInfo
+{
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // CONSTANTS
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // STATE
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+
+    private PrivilegedSQLObject _tupleDescriptor;
+    private String              _privilege;
+    private boolean             _restrict;
+
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // CONSTRUCTOR
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+
+    /**
+     * Construct from the object which is protected by privileges.
+     *
+     * @param tupleDescriptor The object which is being protected
+     * @param privilege Kind of privilege (e.g., PermDescriptor.USAGE_PRIV)
+     * @param restrict True if this is a REVOKE RESTRICT action
+     */
+	public GenericPrivilegeInfo( PrivilegedSQLObject tupleDescriptor, String privilege, boolean restrict )
+	{
+		_tupleDescriptor = tupleDescriptor;
+        _privilege = privilege;
+        _restrict = restrict;
+	}
+	
+    ///////////////////////////////////////////////////////////////////////////////////
+    //
+    // PrivilegeInfo BEHAVIOR
+    //
+    ///////////////////////////////////////////////////////////////////////////////////
+
+	/**
+	 *	This is the guts of the Execution-time logic for GRANT/REVOKE generic privileges.
+	 *
+	 * @param activation
+	 * @param grant true if grant, false if revoke
+	 * @param grantees a list of authorization ids (strings)
+	 *
+	 * @exception StandardException		Thrown on failure
+	 */
+	public void executeGrantRevoke( Activation activation,
+									boolean grant,
+									List grantees)
+		throws StandardException
+	{
+		// Check that the current user has permission to grant the privileges.
+		LanguageConnectionContext lcc = activation.getLanguageConnectionContext();
+		DataDictionary dd = lcc.getDataDictionary();
+		String currentUser = lcc.getAuthorizationId();
+		TransactionController tc = lcc.getTransactionExecute();
+        SchemaDescriptor sd = _tupleDescriptor.getSchemaDescriptor();
+        UUID objectID = _tupleDescriptor.getUUID();
+        String objectTypeName = _tupleDescriptor.getObjectTypeName();
+
+		// Check that the current user has permission to grant the privileges.
+		checkOwnership( currentUser, (TupleDescriptor) _tupleDescriptor, sd, dd );
+		
+		DataDescriptorGenerator ddg = dd.getDataDescriptorGenerator();
+
+		PermDescriptor permDesc = ddg.newPermDescriptor
+            ( null, objectTypeName, objectID, _privilege, currentUser, null, false );
+
+		dd.startWriting(lcc);
+		for( Iterator itr = grantees.iterator(); itr.hasNext();)
+		{
+			// Keep track to see if any privileges are revoked by a revoke 
+			// statement. If a privilege is not revoked, we need to raise a
+			// warning.
+			boolean privileges_revoked = false;
+			String grantee = (String) itr.next();
+			if (dd.addRemovePermissionsDescriptor( grant, permDesc, grantee, tc)) 
+			{
+                //
+                // We fall in here if we are performing REVOKE.
+                //
+				privileges_revoked = true;	
+                int invalidationType = _restrict ? DependencyManager.REVOKE_PRIVILEGE_RESTRICT : DependencyManager.REVOKE_PRIVILEGE;
+
+				dd.getDependencyManager().invalidateFor( permDesc, invalidationType, lcc );
+
+				// Now invalidate all GPSs refering to the object.
+				dd.getDependencyManager().invalidateFor(_tupleDescriptor, invalidationType, lcc );
+			}
+			
+			addWarningIfPrivilegeNotRevoked(activation, grant, privileges_revoked, grantee);
+		}
+	} // end of executeGrantRevoke
+
+
+}

Propchange: db/derby/code/trunk/java/engine/org/apache/derby/impl/sql/execute/GenericPrivilegeInfo.java
------------------------------------------------------------------------------
    svn:eol-style = native

Modified: db/derby/code/trunk/java/engine/org/apache/derby/loc/messages.xml
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/loc/messages.xml?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/loc/messages.xml (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/loc/messages.xml Fri Dec 18 15:15:02 2009
@@ -1089,8 +1089,9 @@
 
             <msg>
                 <name>42504</name>
-                <text>User '{0}' does not have execute permission on {1} '{2}'.'{3}'.</text>
+                <text>User '{0}' does not have {1} permission on {2} '{3}'.'{4}'.</text>
                 <arg>authorizationID</arg>
+                <arg>permissionType</arg>
                 <arg>objectName</arg>
                 <arg>schemaName</arg>
                 <arg>tableName</arg>
@@ -1098,8 +1099,9 @@
 
             <msg>
                 <name>42505</name>
-                <text>User '{0}' does not have execute permission on {1} '{2}'.'{3}' for grant.</text>
+                <text>User '{0}' does not have {1} permission on {2} '{3}'.'{4}' for grant.</text>
                 <arg>authorizationID</arg>
+                <arg>permissionType</arg>
                 <arg>objectName</arg>
                 <arg>schemaName</arg>
                 <arg>tableName</arg>

Modified: db/derby/code/trunk/java/shared/org/apache/derby/shared/common/reference/SQLState.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/shared/org/apache/derby/shared/common/reference/SQLState.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/shared/org/apache/derby/shared/common/reference/SQLState.java (original)
+++ db/derby/code/trunk/java/shared/org/apache/derby/shared/common/reference/SQLState.java Fri Dec 18 15:15:02 2009
@@ -753,8 +753,8 @@
 	String AUTH_NO_TABLE_PERMISSION_FOR_GRANT                          = "42501";
 	String AUTH_NO_COLUMN_PERMISSION                                   = "42502";
 	String AUTH_NO_COLUMN_PERMISSION_FOR_GRANT                         = "42503";
-	String AUTH_NO_EXECUTE_PERMISSION                                  = "42504";
-	String AUTH_NO_EXECUTE_PERMISSION_FOR_GRANT                        = "42505";
+	String AUTH_NO_GENERIC_PERMISSION                                  = "42504";
+	String AUTH_NO_GENERIC_PERMISSION_FOR_GRANT                        = "42505";
 	String AUTH_NOT_OWNER                                              = "42506";
 	String AUTH_NO_ACCESS_NOT_OWNER                                    = "42507";
 	String AUTH_NOT_DATABASE_OWNER                                     = "42508";

Modified: db/derby/code/trunk/java/storeless/org/apache/derby/impl/storeless/EmptyDictionary.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/storeless/org/apache/derby/impl/storeless/EmptyDictionary.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/storeless/org/apache/derby/impl/storeless/EmptyDictionary.java (original)
+++ db/derby/code/trunk/java/storeless/org/apache/derby/impl/storeless/EmptyDictionary.java Fri Dec 18 15:15:02 2009
@@ -843,12 +843,12 @@
         return null;
     }   
 
-    public PermDescriptor getPermissions(UUID permUUID) throws StandardException {
+    public PermDescriptor getGenericPermissions(UUID permUUID) throws StandardException {
         // TODO Auto-generated method stub
         return null;
     }
 
-    public PermDescriptor getPermissions(UUID objectID, String granteeAuthId) 
+    public PermDescriptor getGenericPermissions(UUID objectID, String objectType, String privilege, String granteeAuthId) 
             throws StandardException {
         // TODO Auto-generated method stub
         return null;

Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/GeneratedColumnsHelper.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/GeneratedColumnsHelper.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/GeneratedColumnsHelper.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/GeneratedColumnsHelper.java Fri Dec 18 15:15:02 2009
@@ -81,6 +81,7 @@
     protected static  final   String  LACK_TABLE_PRIV = "42500";
     protected static  final   String  LACK_COLUMN_PRIV = "42502";
     protected static  final   String  LACK_EXECUTE_PRIV = "42504";
+    protected static  final   String  LACK_USAGE_PRIV = "42504";
     protected static  final   String  CANT_ADD_IDENTITY = "42601";
     protected static  final   String  CANT_MODIFY_IDENTITY = "42Z23";
     
@@ -88,6 +89,10 @@
     protected static  final   String  CONSTRAINT_DROPPED_WARNING = "01500";
     protected static  final   String  TRIGGER_DROPPED_WARNING = "01502";
     protected static  final   String  LANG_INVALID_USE_OF_DEFAULT = "42Y85";
+    protected static  final   String  GRANT_REVOKE_NOT_ALLOWED = "42509";
+    protected static  final   String  ROUTINE_DEPENDS_ON_TYPE = "X0Y30";
+    protected static  final   String  TABLE_DEPENDS_ON_TYPE = "X0Y29";
+    protected static  final   String  VIEW_DEPENDS_ON_PRIVILEGE = "X0Y23";
 
     ///////////////////////////////////////////////////////////////////////////////////
     //
@@ -159,6 +164,27 @@
     }
 
     /**
+     * Assert that the statement text, when compiled, raises an exception
+     */
+    protected void    expectCompilationError( Connection conn, String sqlState, String query )
+    {
+        println( "\nExpecting " + sqlState + " when preparing:\n\t" + query );
+
+        PreparedStatement ps = null;
+
+        try {
+            ps = conn.prepareStatement( query );
+        } catch (SQLException se )
+        {
+            assertSQLState( sqlState, se );
+
+            return;
+        }
+
+        fail( "Expected SQL state: " + sqlState );
+    }
+
+    /**
      * Assert that the statement text, when executed, raises an error.
      */
     protected void    expectExecutionError( Connection conn, String sqlState, String query )
@@ -351,6 +377,54 @@
     }
 
     /**
+     * Test that a privilege can't be revoked if an object depends on it.
+     */
+    protected void verifyRevokePrivilege
+        (
+         Connection grantorConnection,
+         Connection granteeConnection,
+         String grantStatement,
+         String revokeStatement,
+         String createStatement,
+         String dropStatement,
+         String badRevokeSQLState
+         ) throws Exception
+    {
+        expectExecutionError
+            (
+             granteeConnection,
+             LACK_USAGE_PRIV,
+             createStatement
+             );
+        goodStatement
+            (
+             grantorConnection,
+             grantStatement
+             );
+        goodStatement
+            (
+             granteeConnection,
+             createStatement
+             );
+        expectExecutionError
+            (
+             grantorConnection,
+             badRevokeSQLState,
+             revokeStatement
+             );
+        goodStatement
+            (
+             granteeConnection,
+             dropStatement
+             );
+        goodStatement
+            (
+             grantorConnection,
+             revokeStatement
+             );
+    }
+
+    /**
      * <p>
      * Fill an ArrayList from an array.
      * </p>

Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/SystemCatalogTest.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/SystemCatalogTest.java?rev=892272&r1=892271&r2=892272&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/SystemCatalogTest.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/lang/SystemCatalogTest.java Fri Dec 18 15:15:02 2009
@@ -372,6 +372,7 @@
 				{"SYSKEYS", "SYSKEYS_HEAP", "false"},
 				{"SYSKEYS", "SYSKEYS_INDEX1", "true"},
                 {"SYSPERMS", "SYSPERMS_HEAP", "false"},
+                {"SYSPERMS", "SYSPERMS_INDEX3", "true"},
                 {"SYSPERMS", "SYSPERMS_INDEX2", "true"},
                 {"SYSPERMS", "SYSPERMS_INDEX1", "true"},
                 {"SYSROLES", "SYSROLES_HEAP", "false"},



Mime
View raw message