From c8ef1f566637051a8c4c3471c5ccab42ac40d721 Mon Sep 17 00:00:00 2001 From: TengJianPing <18241664+jacktengg@users.noreply.github.com> Date: Tue, 18 Jun 2024 09:49:48 +0800 Subject: [PATCH] [fix](intersect) fix coredump caused by intersect of nullable and not nullable children (#36401) --- be/src/vec/exec/vset_operation_node.cpp | 13 ++- .../sql/intersect_nullable_not_nullable.out | 7 ++ .../intersect_nullable_not_nullable.groovy | 98 +++++++++++++++++++ 3 files changed, 117 insertions(+), 1 deletion(-) create mode 100644 regression-test/data/query_p0/set_operations/sql/intersect_nullable_not_nullable.out create mode 100644 regression-test/suites/query_p0/set_operations/sql/intersect_nullable_not_nullable.groovy diff --git a/be/src/vec/exec/vset_operation_node.cpp b/be/src/vec/exec/vset_operation_node.cpp index 71774e972673f0..cdee3842143883 100644 --- a/be/src/vec/exec/vset_operation_node.cpp +++ b/be/src/vec/exec/vset_operation_node.cpp @@ -503,7 +503,18 @@ void VSetOperationNode::add_result_columns(RowRefListWithFlags& va auto it = value.begin(); for (auto idx = _build_col_idx.begin(); idx != _build_col_idx.end(); ++idx) { const auto& column = *_build_blocks[it->block_offset].get_by_position(idx->second).column; - _mutable_cols[idx->first]->insert_from(column, it->row_num); + if (_mutable_cols[idx->second]->is_nullable() xor column.is_nullable()) { + if (_mutable_cols[idx->second]->is_nullable()) { + ((ColumnNullable*)(_mutable_cols[idx->second].get())) + ->insert_from_not_nullable(column, it->row_num); + } else { + auto& nest_col = ((ColumnNullable&)column).get_nested_column(); + _mutable_cols[idx->first]->insert_from(nest_col, it->row_num); + } + + } else { + _mutable_cols[idx->first]->insert_from(column, it->row_num); + } } block_size++; } diff --git a/regression-test/data/query_p0/set_operations/sql/intersect_nullable_not_nullable.out b/regression-test/data/query_p0/set_operations/sql/intersect_nullable_not_nullable.out new file mode 100644 index 00000000000000..33e6f39096cb40 --- /dev/null +++ b/regression-test/data/query_p0/set_operations/sql/intersect_nullable_not_nullable.out @@ -0,0 +1,7 @@ +-- This file is automatically generated. You should know what you did if you want to edit this +-- !intersect_nullable_not_nullable_1 -- +c + +-- !intersect_nullable_not_nullable_2 -- +c + diff --git a/regression-test/suites/query_p0/set_operations/sql/intersect_nullable_not_nullable.groovy b/regression-test/suites/query_p0/set_operations/sql/intersect_nullable_not_nullable.groovy new file mode 100644 index 00000000000000..2b355db1c13f6c --- /dev/null +++ b/regression-test/suites/query_p0/set_operations/sql/intersect_nullable_not_nullable.groovy @@ -0,0 +1,98 @@ +// 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. + +suite("intersect_nullable_not_nullable") { + sql """ + drop table if exists intersect_nullable_not_nullable_t1; + """ + sql """ + drop table if exists intersect_nullable_not_nullable_t2; + """ + sql """ + drop table if exists intersect_nullable_not_nullable_t3; + """ + sql """ + drop table if exists intersect_nullable_not_nullable_t4; + """ + sql """ + create table intersect_nullable_not_nullable_t1 (k1 char(16) not null) distributed by hash(k1) properties("replication_num"="1"); + """ + sql """ + insert into intersect_nullable_not_nullable_t1 values("a"), ("b"), ("c"), ("d"), ("e"); + """ + + sql """ + create table intersect_nullable_not_nullable_t2 (kk0 int, kk1 char(16) not null) distributed by hash(kk0) properties("replication_num"="1"); + """ + sql """ + insert into intersect_nullable_not_nullable_t2 values(1, "b"), (2, "c"), (3, "d"), (4, "e"); + """ + + sql """ + create table intersect_nullable_not_nullable_t3 (kkk1 char(16) ) distributed by hash(kkk1) properties("replication_num"="1"); + """ + sql """ + insert into intersect_nullable_not_nullable_t3 values("c"), ("d"), ("e"); + """ + + sql """ + create table intersect_nullable_not_nullable_t4 (kkkk1 char(16) ) distributed by hash(kkkk1) properties("replication_num"="1"); + """ + sql """ + insert into intersect_nullable_not_nullable_t4 values("d"), ("e"); + """ + + order_qt_intersect_nullable_not_nullable_1 """ + ( + select * from intersect_nullable_not_nullable_t1 + ) + intersect + ( + select distinct kk1 from intersect_nullable_not_nullable_t2 + ) + intersect + ( + ( + select * from intersect_nullable_not_nullable_t3 + ) + except + ( + select * from intersect_nullable_not_nullable_t4 + ) + ); + """ + + order_qt_intersect_nullable_not_nullable_2 """ + ( + select * from intersect_nullable_not_nullable_t1 + ) + intersect + ( + ( + select * from intersect_nullable_not_nullable_t3 + ) + except + ( + select * from intersect_nullable_not_nullable_t4 + ) + ) + intersect + ( + select distinct kk1 from intersect_nullable_not_nullable_t2 + ); + """ +}