fix some privilege and expr bugs
This commit is contained in:
		@ -813,29 +813,78 @@ int ObGrantResolver::resolve_col_names(
 | 
			
		||||
1. username dup
 | 
			
		||||
2. grant role can not with grant option 
 | 
			
		||||
3. grant role can not reference, index priv */
 | 
			
		||||
int ObGrantResolver::check_user_dup_and_role_grant_option(
 | 
			
		||||
int ObGrantResolver::check_user_dup(
 | 
			
		||||
    ObSchemaGetterGuard *guard,
 | 
			
		||||
    ObIArray<ObString> &user_name_array,
 | 
			
		||||
    const ObGrantStmt *grant_stmt,
 | 
			
		||||
    const ObString& user_name,
 | 
			
		||||
    const ObString& host_name,
 | 
			
		||||
    const ObString& priv_user_name)
 | 
			
		||||
    const ObString& priv_user_name,
 | 
			
		||||
    bool &contain_role,
 | 
			
		||||
    bool &is_all_role)
 | 
			
		||||
{
 | 
			
		||||
  int ret = OB_SUCCESS;
 | 
			
		||||
  CK (grant_stmt != NULL);
 | 
			
		||||
  
 | 
			
		||||
  if (ObSchemaChecker::is_ora_priv_check()) {
 | 
			
		||||
    /* 1. check user dup */
 | 
			
		||||
    if (has_exist_in_array(user_name_array, user_name)) {
 | 
			
		||||
    const ObUserInfo *user_info = NULL;
 | 
			
		||||
    uint64_t tenant_id = OB_INVALID_ID;
 | 
			
		||||
    if (OB_ISNULL(params_.session_info_) || OB_ISNULL(guard)) {
 | 
			
		||||
      ret = OB_ERR_UNEXPECTED;
 | 
			
		||||
      LOG_WARN("unexpected null", K(ret));
 | 
			
		||||
    } else if (has_exist_in_array(user_name_array, user_name)) {
 | 
			
		||||
      ret = OB_ERR_DUPLICATE_USERNAME_IN_LIST;
 | 
			
		||||
      LOG_WARN("user name dup", K(user_name), K(ret));
 | 
			
		||||
    } else if (grant_stmt->get_database_name() != user_name 
 | 
			
		||||
               && user_name == priv_user_name) {
 | 
			
		||||
      ret = OB_ERR_YOU_MAY_NOT_REVOKE_PRIVILEGES_FROM_YOURSELF;
 | 
			
		||||
      LOG_WARN("grant to self", K(user_name), K(ret));
 | 
			
		||||
    } else if (OB_FAIL(user_name_array.push_back(user_name))) {
 | 
			
		||||
      LOG_WARN("failed to push back user name", K(ret), K(user_name));
 | 
			
		||||
    } else if (FALSE_IT(tenant_id = params_.session_info_->get_effective_tenant_id())) {
 | 
			
		||||
      // do nothing
 | 
			
		||||
    } else if (OB_FAIL(guard->get_user_info(tenant_id, user_name, host_name, user_info))) {
 | 
			
		||||
      LOG_WARN("failed to get user info", K(ret), K(tenant_id), K(user_name), K(host_name));
 | 
			
		||||
    } else if (OB_ISNULL(user_info)) {
 | 
			
		||||
      ret = OB_USER_NOT_EXIST;
 | 
			
		||||
      LOG_WARN("user is not exist", K(ret), K(tenant_id), K(user_name), K(host_name));
 | 
			
		||||
    } else {
 | 
			
		||||
      OZ (user_name_array.push_back(user_name));
 | 
			
		||||
      contain_role |= user_info->is_role();
 | 
			
		||||
      is_all_role &= user_info->is_role();
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
  return ret;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int ObGrantResolver::rebuild_table_priv(
 | 
			
		||||
    ObGrantStmt *grant_stmt,
 | 
			
		||||
    bool is_owner,
 | 
			
		||||
    const bool is_all_role)
 | 
			
		||||
{
 | 
			
		||||
  int ret = OB_SUCCESS;
 | 
			
		||||
  if (OB_ISNULL(grant_stmt)) {
 | 
			
		||||
    ret = OB_ERR_UNEXPECTED;
 | 
			
		||||
    LOG_WARN("unexpected null stmt", K(ret));
 | 
			
		||||
  } else if (grant_stmt->is_grant_all_tab_priv()) {
 | 
			
		||||
    share::ObRawObjPrivArray table_priv_array;
 | 
			
		||||
    OZ (build_table_priv_arary_for_all(grant_stmt,
 | 
			
		||||
                                        table_priv_array,
 | 
			
		||||
                                        is_owner,
 | 
			
		||||
                                        is_all_role));
 | 
			
		||||
    OZ (grant_stmt->set_obj_priv_array(table_priv_array));
 | 
			
		||||
  }
 | 
			
		||||
  return ret;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int ObGrantResolver::check_role_grant_option(
 | 
			
		||||
    const ObGrantStmt *grant_stmt,
 | 
			
		||||
    const bool contain_role) {
 | 
			
		||||
  int ret = OB_SUCCESS;
 | 
			
		||||
  if (OB_ISNULL(grant_stmt)) {
 | 
			
		||||
    ret = OB_ERR_UNEXPECTED;
 | 
			
		||||
    LOG_WARN("unexpected null stmt", K(ret));
 | 
			
		||||
  } else if (ObSchemaChecker::is_ora_priv_check() && contain_role) {
 | 
			
		||||
    bool has_ref_priv = false;
 | 
			
		||||
    bool has_index_priv = false;
 | 
			
		||||
    if (has_exist_in_array(grant_stmt->get_obj_priv_array(), 
 | 
			
		||||
@ -851,30 +900,17 @@ int ObGrantResolver::check_user_dup_and_role_grant_option(
 | 
			
		||||
       2. 不能grant reference,其次优先
 | 
			
		||||
       3. 不能grant index */
 | 
			
		||||
    if (grant_stmt->get_option() == GRANT_OPTION || has_ref_priv || has_index_priv) {
 | 
			
		||||
      const ObUserInfo *user_info = NULL;
 | 
			
		||||
      CK (params_.session_info_ != NULL);
 | 
			
		||||
      uint64_t tenant_id = params_.session_info_->get_effective_tenant_id();
 | 
			
		||||
      CK (guard != NULL);
 | 
			
		||||
      OZ (guard->get_user_info(tenant_id, user_name, host_name, user_info));
 | 
			
		||||
      if (OB_SUCC(ret)) {
 | 
			
		||||
        if (NULL == user_info) {
 | 
			
		||||
          ret = OB_USER_NOT_EXIST;
 | 
			
		||||
        } else if (user_info->is_role()) {
 | 
			
		||||
          if (grant_stmt->get_option() == GRANT_OPTION) {
 | 
			
		||||
            ret = OB_ERR_CANNOT_GRANT_TO_A_ROLE_WITH_GRANT_OPTION;
 | 
			
		||||
          } else if (has_ref_priv) {
 | 
			
		||||
            ObString str = "REFERENCES";
 | 
			
		||||
            ret = OB_ERR_CANNOT_GRANT_STRING_TO_A_ROLE;
 | 
			
		||||
            LOG_USER_ERROR(OB_ERR_CANNOT_GRANT_STRING_TO_A_ROLE,
 | 
			
		||||
                           str.length(), str.ptr());
 | 
			
		||||
          } else {
 | 
			
		||||
            CK (has_index_priv);
 | 
			
		||||
            ObString str = "INDEX";
 | 
			
		||||
            ret = OB_ERR_CANNOT_GRANT_STRING_TO_A_ROLE;
 | 
			
		||||
            LOG_USER_ERROR(OB_ERR_CANNOT_GRANT_STRING_TO_A_ROLE,
 | 
			
		||||
                           str.length(), str.ptr());
 | 
			
		||||
          }
 | 
			
		||||
        }
 | 
			
		||||
      if (grant_stmt->get_option() == GRANT_OPTION) {
 | 
			
		||||
        ret = OB_ERR_CANNOT_GRANT_TO_A_ROLE_WITH_GRANT_OPTION;
 | 
			
		||||
      } else if (has_ref_priv) {
 | 
			
		||||
        ObString str = "REFERENCES";
 | 
			
		||||
        ret = OB_ERR_CANNOT_GRANT_STRING_TO_A_ROLE;
 | 
			
		||||
        LOG_USER_ERROR(OB_ERR_CANNOT_GRANT_STRING_TO_A_ROLE, str.length(), str.ptr());
 | 
			
		||||
      } else {
 | 
			
		||||
        CK (has_index_priv);
 | 
			
		||||
        ObString str = "INDEX";
 | 
			
		||||
        ret = OB_ERR_CANNOT_GRANT_STRING_TO_A_ROLE;
 | 
			
		||||
        LOG_USER_ERROR(OB_ERR_CANNOT_GRANT_STRING_TO_A_ROLE, str.length(), str.ptr());
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
@ -999,6 +1035,8 @@ int ObGrantResolver::resolve_grant_obj_privileges(
 | 
			
		||||
  if (OB_SUCC(ret)) {
 | 
			
		||||
    // oracle 模式下 grant 时,如果用户不存在,不允许创建该用户;fix #17900015
 | 
			
		||||
    bool need_create_user = false;
 | 
			
		||||
    bool contain_role = false;
 | 
			
		||||
    bool is_all_role = true;
 | 
			
		||||
    CHECK_COMPATIBILITY_MODE(session_info_);
 | 
			
		||||
    if (!lib::is_oracle_mode()) {
 | 
			
		||||
      need_create_user = (0 == (params_.session_info_->get_sql_mode()
 | 
			
		||||
@ -1086,13 +1124,17 @@ int ObGrantResolver::resolve_grant_obj_privileges(
 | 
			
		||||
            //do nothing
 | 
			
		||||
          }
 | 
			
		||||
        }
 | 
			
		||||
        OZ (check_user_dup_and_role_grant_option(params_.schema_checker_->get_schema_guard(),
 | 
			
		||||
                                                  user_name_array, 
 | 
			
		||||
                                                  grant_stmt, 
 | 
			
		||||
                                                  user_name, 
 | 
			
		||||
                                                  host_name,
 | 
			
		||||
                                                  priv_user_name));
 | 
			
		||||
        OZ (check_user_dup(params_.schema_checker_->get_schema_guard(),
 | 
			
		||||
                            user_name_array,
 | 
			
		||||
                            grant_stmt,
 | 
			
		||||
                            user_name,
 | 
			
		||||
                            host_name,
 | 
			
		||||
                            priv_user_name,
 | 
			
		||||
                            contain_role,
 | 
			
		||||
                            is_all_role));
 | 
			
		||||
      }
 | 
			
		||||
      OZ (rebuild_table_priv(grant_stmt, is_owner, is_all_role));
 | 
			
		||||
      OZ (check_role_grant_option(grant_stmt, contain_role));
 | 
			
		||||
    }
 | 
			
		||||
  }//end of resolve users
 | 
			
		||||
 | 
			
		||||
@ -1736,7 +1778,8 @@ bool ObGrantResolver::is_ora_obj_priv_type(
 | 
			
		||||
int ObGrantResolver::build_table_priv_arary_for_all(
 | 
			
		||||
    ObGrantStmt *grant_stmt,
 | 
			
		||||
    share::ObRawObjPrivArray &table_priv_array,
 | 
			
		||||
    bool is_owner)
 | 
			
		||||
    bool is_owner,
 | 
			
		||||
    bool is_role)
 | 
			
		||||
{
 | 
			
		||||
  int ret = OB_SUCCESS;
 | 
			
		||||
  CK (grant_stmt != NULL);
 | 
			
		||||
@ -1773,12 +1816,14 @@ int ObGrantResolver::build_table_priv_arary_for_all(
 | 
			
		||||
            {
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_ALTER));
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_DELETE));
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_INDEX));
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_INSERT));
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_REFERENCES));
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_SELECT));
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_UPDATE));
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_FLASHBACK));
 | 
			
		||||
              if (OB_SUCC(ret) && !is_role) {
 | 
			
		||||
                OZ (table_priv_array.push_back(OBJ_PRIV_ID_INDEX));
 | 
			
		||||
                OZ (table_priv_array.push_back(OBJ_PRIV_ID_REFERENCES));
 | 
			
		||||
              }
 | 
			
		||||
              break;
 | 
			
		||||
            }
 | 
			
		||||
          case share::schema::ObObjectType::SEQUENCE:
 | 
			
		||||
@ -1803,9 +1848,11 @@ int ObGrantResolver::build_table_priv_arary_for_all(
 | 
			
		||||
            {
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_DELETE));
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_INSERT));
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_REFERENCES));
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_SELECT));
 | 
			
		||||
              OZ (table_priv_array.push_back(OBJ_PRIV_ID_UPDATE));
 | 
			
		||||
              if (OB_SUCC(ret) && !is_role) {
 | 
			
		||||
                OZ (table_priv_array.push_back(OBJ_PRIV_ID_REFERENCES));
 | 
			
		||||
              }
 | 
			
		||||
              break;
 | 
			
		||||
            }
 | 
			
		||||
          case share::schema::ObObjectType::DIRECTORY:
 | 
			
		||||
@ -1913,9 +1960,7 @@ int ObGrantResolver::resolve_obj_priv_list_ora(
 | 
			
		||||
        } else if (OB_PRIV_TABLE_LEVEL == grant_level) {
 | 
			
		||||
          if (OB_PRIV_ALL == priv_type) {
 | 
			
		||||
            priv_set |= OB_PRIV_TABLE_ACC;
 | 
			
		||||
            OZ (build_table_priv_arary_for_all(grant_stmt, 
 | 
			
		||||
                                                table_priv_array,
 | 
			
		||||
                                                is_owner));
 | 
			
		||||
            grant_stmt->set_grant_all_tab_priv(true);
 | 
			
		||||
          } else if (priv_type & (~(OB_PRIV_TABLE_ACC | OB_PRIV_GRANT)) && 
 | 
			
		||||
                      is_ora_obj_priv_type(priv_type) == false) {
 | 
			
		||||
            ret = OB_ERR_MISSING_OR_INVALID_PRIVIEGE;
 | 
			
		||||
 | 
			
		||||
@ -102,13 +102,23 @@ public:
 | 
			
		||||
      share::schema::ObPrivLevel &grant_level,
 | 
			
		||||
      bool &is_directory,
 | 
			
		||||
      bool &explicit_db);
 | 
			
		||||
  int check_user_dup_and_role_grant_option(
 | 
			
		||||
  int check_user_dup(
 | 
			
		||||
      share::schema::ObSchemaGetterGuard *guard,
 | 
			
		||||
      ObIArray<ObString> &user_name_array,
 | 
			
		||||
      const ObGrantStmt *grant_stmt,
 | 
			
		||||
      const ObString& user_name,
 | 
			
		||||
      const ObString& host_name,
 | 
			
		||||
      const ObString& priv_user_name);
 | 
			
		||||
      const ObString& priv_user_name,
 | 
			
		||||
      bool &contain_role,
 | 
			
		||||
      bool &is_all_role);
 | 
			
		||||
  int rebuild_table_priv(
 | 
			
		||||
      ObGrantStmt *grant_stmt,
 | 
			
		||||
      bool is_owner,
 | 
			
		||||
      const bool is_all_role);
 | 
			
		||||
  int check_role_grant_option(
 | 
			
		||||
      const ObGrantStmt *grant_stmt,
 | 
			
		||||
      const bool contain_role);
 | 
			
		||||
 | 
			
		||||
  static int resolve_role_sys_obj_all_col_priv_list(const ParseNode *role_sys_list,
 | 
			
		||||
                                                    ObIArray<ObString> &role_name_array,
 | 
			
		||||
                                                    share::ObRawPrivArray &sys_priv_array);
 | 
			
		||||
@ -117,7 +127,8 @@ private:
 | 
			
		||||
  int build_table_priv_arary_for_all(
 | 
			
		||||
      ObGrantStmt *grant_stmt,
 | 
			
		||||
      share::ObRawObjPrivArray &table_priv_array,
 | 
			
		||||
      bool is_owner);
 | 
			
		||||
      bool is_owner,
 | 
			
		||||
      bool is_role);
 | 
			
		||||
  int check_obj_priv_valid(
 | 
			
		||||
      ObGrantStmt *grant_stmt,
 | 
			
		||||
      share::ObRawObjPriv ora_obj_priv);
 | 
			
		||||
 | 
			
		||||
@ -43,7 +43,8 @@ ObGrantStmt::ObGrantStmt(ObIAllocator *name_pool)
 | 
			
		||||
      ins_col_ids_(),
 | 
			
		||||
      upd_col_ids_(),
 | 
			
		||||
      ref_col_ids_(),
 | 
			
		||||
      ref_query_(NULL)
 | 
			
		||||
      ref_query_(NULL),
 | 
			
		||||
      is_grant_all_tab_priv_(false)
 | 
			
		||||
{
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -68,7 +69,8 @@ ObGrantStmt::ObGrantStmt()
 | 
			
		||||
      ins_col_ids_(),
 | 
			
		||||
      upd_col_ids_(),
 | 
			
		||||
      ref_col_ids_(),
 | 
			
		||||
      ref_query_(NULL)
 | 
			
		||||
      ref_query_(NULL),
 | 
			
		||||
      is_grant_all_tab_priv_(false)
 | 
			
		||||
{
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@ -68,6 +68,7 @@ public:
 | 
			
		||||
  int set_ref_col_ids(ObSEArray<uint64_t, 4> &col_ids) { return ref_col_ids_.assign(col_ids); }
 | 
			
		||||
  void set_ref_query(ObSelectStmt* ref_query) { ref_query_ = ref_query; }
 | 
			
		||||
  int add_grantee(const common::ObString &grantee);
 | 
			
		||||
  void set_grant_all_tab_priv(bool is_grant_all) { is_grant_all_tab_priv_ = is_grant_all; }
 | 
			
		||||
 | 
			
		||||
  const share::ObRawPrivArray& get_priv_array() const {return sys_priv_array_;}
 | 
			
		||||
  const share::ObRawObjPrivArray& get_obj_priv_array() const {return obj_priv_array_;}
 | 
			
		||||
@ -78,6 +79,7 @@ public:
 | 
			
		||||
  ObPrivSet get_priv_set() const { return priv_set_; }
 | 
			
		||||
  uint64_t get_tenant_id() const { return tenant_id_; }
 | 
			
		||||
  const common::ObStrings& get_grantees() const { return grantees_; }
 | 
			
		||||
  bool is_grant_all_tab_priv() const { return is_grant_all_tab_priv_; }
 | 
			
		||||
 | 
			
		||||
  virtual bool cause_implicit_commit() const { return true; }
 | 
			
		||||
  virtual obrpc::ObDDLArg &get_ddl_arg() { return grant_arg_; }
 | 
			
		||||
@ -107,6 +109,7 @@ private:
 | 
			
		||||
  ObSEArray<uint64_t, 4> upd_col_ids_;
 | 
			
		||||
  ObSEArray<uint64_t, 4> ref_col_ids_;
 | 
			
		||||
  ObSelectStmt *ref_query_; // 用于grant 视图时,对视图依赖的table,view等做递归权限check.
 | 
			
		||||
  bool is_grant_all_tab_priv_;
 | 
			
		||||
 | 
			
		||||
private:
 | 
			
		||||
  DISALLOW_COPY_AND_ASSIGN(ObGrantStmt);
 | 
			
		||||
 | 
			
		||||
		Reference in New Issue
	
	Block a user