// The return value is computed as follows: // If no privs were specified in this on input, return Neutral. // Otherwise : // Return All if each T specified in input 'this' // remains T in output 'this'; // Return None if each T specified in input 'this' // becomes F on output 'this'; // Return Some for other combinations. // ---------------------------------------------------------------------------- PrivMgrCoreDesc::PrivResult PrivMgrCoreDesc::grantPrivs(PrivMgrCoreDesc& param) { if ( this->isNull() ) return NEUTRAL; // Do nothing. No privs to be granted. std::bitset<NBR_OF_PRIVS> beforePriv (param.priv_); // save input values std::bitset<NBR_OF_PRIVS> beforeWgo (param.wgo_); std::bitset<NBR_OF_PRIVS> inPriv (priv_); std::bitset<NBR_OF_PRIVS> inWgo (wgo_); param.priv_ |= priv_; // param(out) gets param(in) OR this(in). param.wgo_ |= wgo_; priv_ &= ( beforePriv.flip() ); // this(out) gets this(in) wgo_ &= ( beforeWgo.flip() ); // AND NOT param(in) PrivResult result(NEUTRAL); // Look at each privilege type for ( size_t i = 0; i < NBR_OF_PRIVS; i++ ) { PrivType pType = PrivType(i); PrivMgrCoreDesc::interpretChanges(inPriv.test(pType), priv_.test(pType), result); PrivMgrCoreDesc::interpretChanges(inWgo.test(pType), wgo_.test(pType), result); } return result; }
// this object|passed param|passed param|this object // on input: | on input: | on output: | on output: // priv_ wgo_ | priv_ wgo_ | priv_ wgo_ | priv_ wgo_ // --- --- | --- --- | --- --- | --- --- // T T -> T T => F F T T // T F F F T F // F F F F F F // F T -> T T => T F F T // T F T F F F // F F F F F F // F F -> x y => x y F F // T F (does not occur -- cannot revoke priv without revoking wgo) // // The algorithm is: // Output param = input param AND NOT input this; // Output this = input this AND input param. // Return value is computed as described in grantPrivs. // ---------------------------------------------------------------------------- PrivMgrCoreDesc::PrivResult PrivMgrCoreDesc::revokePrivs(PrivMgrCoreDesc& param) { if ( this->isNull() ) return NEUTRAL; // Do nothing. No privs to be revoked. std::bitset<NBR_OF_PRIVS> beforePriv = param.priv_; // save input values. std::bitset<NBR_OF_PRIVS> beforeWgo = param.wgo_; std::bitset<NBR_OF_PRIVS> inPriv (priv_); std::bitset<NBR_OF_PRIVS> inWgo (wgo_); param.priv_ &= ( priv_.flip() ); // param(out) gets param(in) //param.priv_ &= ( priv_ ); // param(out) gets param(in) param.wgo_ &= ( wgo_.flip()); // AND NOT( this(in) ). //param.wgo_ &= ( wgo_); // AND NOT( this(in) ). param.wgo_ &= param.priv_; // Assure valid new setting. priv_ &= beforePriv; // this(out) gets this(in) wgo_ &= beforeWgo; // AND param(in). PrivResult result(NEUTRAL); // Look at each privilege type for ( size_t i = 0; i < NBR_OF_PRIVS; i++ ) { PrivType pType = PrivType(i); PrivMgrCoreDesc::interpretChanges(inPriv.test(pType), priv_.test(pType), result); PrivMgrCoreDesc::interpretChanges(inWgo.test(pType), wgo_.test(pType), result); } return result; }
// ***************************************************************************** // * * // * Function: checkAccessPrivileges * // * * // * This function determines if a user has the requesite privileges to * // * access the referenced objects that comprise the view. * // * * // ***************************************************************************** // * * // * Parameters: * // * * // * <vtul> const ParTableUsageList & In * // * is a reference to a list of objects used by the view. * // * * // * <vctcul> const ParViewColTableColsUsageList & In * // * is a reference to the list of columns used by the view. * // * * // * <privilegesBitmap> PrivMgrBitmap & Out * // * passes back the union of privileges the user has on the referenced * // * objects. * // * * // * <grantableBitmap> PrivMgrBitmap & Out * // * passes back the union of the with grant option authority the user has * // * on the referenced objects. * // * * // ***************************************************************************** // * * // * Returns: bool * // * * // * true: User has requisite privileges; bitmap unions returned. * // * false: Could not retrieve privileges or user does not have requesite * // * privileges; see diags area for error details. * // * * // ***************************************************************************** static bool checkAccessPrivileges( const ParTableUsageList & vtul, const ParViewColTableColsUsageList & vctcul, PrivMgrBitmap & privilegesBitmap, PrivMgrBitmap & grantableBitmap) { BindWA bindWA(ActiveSchemaDB(),CmpCommon::context(),FALSE/*inDDL*/); bool missingPrivilege = false; NAString extUsedObjName; // generate the lists of privileges and grantable privileges // a side effect is to return an error if basic privileges are not granted for (CollIndex i = 0; i < vtul.entries(); i++) { if (vtul[i].getSpecialType() == ExtendedQualName::SG_TABLE) continue; ComObjectName usedObjName(vtul[i].getQualifiedNameObj().getQualifiedNameAsAnsiString(), vtul[i].getAnsiNameSpace()); const NAString catalogNamePart = usedObjName.getCatalogNamePartAsAnsiString(); const NAString schemaNamePart = usedObjName.getSchemaNamePartAsAnsiString(TRUE); const NAString objectNamePart = usedObjName.getObjectNamePartAsAnsiString(TRUE); const NAString extUsedObjName = usedObjName.getExternalName(TRUE); CorrName cn(objectNamePart,STMTHEAP, schemaNamePart,catalogNamePart); NATable *naTable = bindWA.getNATable(cn); if (naTable == NULL) { SEABASEDDL_INTERNAL_ERROR("Bad NATable pointer in checkAccessPrivileges"); return false; } // Grab privileges from the NATable structure PrivMgrUserPrivs *privs = naTable->getPrivInfo(); if (privs == NULL) { *CmpCommon::diags() << DgSqlCode(-CAT_UNABLE_TO_RETRIEVE_PRIVS); return false; } // Requester must have at least select privilege if ( !privs->hasSelectPriv() ) missingPrivilege = true; // Summarize privileges privilegesBitmap &= privs->getObjectBitmap(); grantableBitmap &= privs->getGrantableBitmap(); } if (!missingPrivilege) return true; missingPrivilege = false; PrivColumnBitmap colPrivBitmap; PrivColumnBitmap colGrantableBitmap; PrivMgrPrivileges::setColumnPrivs(colPrivBitmap); PrivMgrPrivileges::setColumnPrivs(colGrantableBitmap); for (size_t i = 0; i < vctcul.entries(); i++) { const ParViewColTableColsUsage &vctcu = vctcul[i]; int32_t usingColNum = vctcu.getUsingViewColumnNumber(); const ColRefName &usedColRef = vctcu.getUsedObjectColumnName(); ComObjectName usedObjName; usedObjName = usedColRef.getCorrNameObj().getQualifiedNameObj(). getQualifiedNameAsAnsiString(); const NAString catalogNamePart = usedObjName.getCatalogNamePartAsAnsiString(); const NAString schemaNamePart = usedObjName.getSchemaNamePartAsAnsiString(TRUE); const NAString objectNamePart = usedObjName.getObjectNamePartAsAnsiString(TRUE); extUsedObjName = usedObjName.getExternalName(TRUE); CorrName cn(objectNamePart,STMTHEAP,schemaNamePart,catalogNamePart); NATable *naTable = bindWA.getNATable(cn); if (naTable == NULL) { SEABASEDDL_INTERNAL_ERROR("Bad NATable pointer in checkAccessPrivileges"); return -1; } const NAColumnArray &nacolArr = naTable->getNAColumnArray(); ComString usedObjColName(usedColRef.getColName()); const NAColumn * naCol = nacolArr.getColumn(usedObjColName); if (naCol == NULL) { *CmpCommon::diags() << DgSqlCode(-CAT_COLUMN_DOES_NOT_EXIST_ERROR) << DgColumnName(usedObjColName); return false; } int32_t usedColNumber = naCol->getPosition(); // Grab privileges from the NATable structure PrivMgrUserPrivs *privs = naTable->getPrivInfo(); if (privs == NULL) { *CmpCommon::diags() << DgSqlCode(-CAT_UNABLE_TO_RETRIEVE_PRIVS); return false; } // If the user is missing SELECT on at least one column-level privilege, // view cannot be created. No need to proceed. if (!privs->hasColSelectPriv(usedColNumber)) { missingPrivilege = true; break; } colPrivBitmap &= privs->getColumnPrivBitmap(usedColNumber); colGrantableBitmap &= privs->getColumnGrantableBitmap(usedColNumber); } if (missingPrivilege || vctcul.entries() == 0) { *CmpCommon::diags() << DgSqlCode(-4481) << DgString0("SELECT") << DgString1(extUsedObjName.data()); return false; } for (size_t i = FIRST_DML_COL_PRIV; i <= LAST_DML_COL_PRIV; i++ ) { if (colPrivBitmap.test(PrivType(i))) privilegesBitmap.set(PrivType(i)); if (colGrantableBitmap.test(PrivType(i))) grantableBitmap.set(PrivType(i)); } return true; }