Skip to content

Commit 1ee78b1

Browse files
committed
Merge remote-tracking branch 'dremio/dremio_27.0_23_19' into nanos_dremio_27.0_23_19
2 parents 7d3aa3c + 92439ac commit 1ee78b1

14 files changed

Lines changed: 939 additions & 149 deletions

cpp/src/gandiva/function_holder_maker_registry.cc

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,7 @@ FunctionHolderMakerRegistry::MakerMap FunctionHolderMakerRegistry::DefaultHolder
6262
{"to_date", HolderMaker<ToDateHolder>},
6363
{"random", HolderMaker<RandomGeneratorHolder>},
6464
{"rand", HolderMaker<RandomGeneratorHolder>},
65+
{"rand_integer", HolderMaker<RandomIntegerGeneratorHolder>},
6566
{"regexp_replace", HolderMaker<ReplaceHolder>},
6667
{"regexp_extract", HolderMaker<ExtractHolder>},
6768
{"castintervalday", HolderMaker<IntervalDaysHolder>},

cpp/src/gandiva/function_registry_math_ops.cc

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,14 @@ std::vector<NativeFunction> GetMathOpsFunctionRegistry() {
103103
"gdv_fn_random", NativeFunction::kNeedsFunctionHolder),
104104
NativeFunction("random", {"rand"}, DataTypeVector{int32()}, float64(),
105105
kResultNullNever, "gdv_fn_random_with_seed",
106+
NativeFunction::kNeedsFunctionHolder),
107+
NativeFunction("rand_integer", {}, DataTypeVector{}, int32(), kResultNullNever,
108+
"gdv_fn_rand_integer", NativeFunction::kNeedsFunctionHolder),
109+
NativeFunction("rand_integer", {}, DataTypeVector{int32()}, int32(),
110+
kResultNullNever, "gdv_fn_rand_integer_with_range",
111+
NativeFunction::kNeedsFunctionHolder),
112+
NativeFunction("rand_integer", {}, DataTypeVector{int32(), int32()}, int32(),
113+
kResultNullNever, "gdv_fn_rand_integer_with_min_max",
106114
NativeFunction::kNeedsFunctionHolder)};
107115

108116
return math_fn_registry_;

cpp/src/gandiva/gdv_function_stubs.cc

Lines changed: 38 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -70,12 +70,33 @@ double gdv_fn_random(int64_t ptr) {
7070
return (*holder)();
7171
}
7272

73-
double gdv_fn_random_with_seed(int64_t ptr, int32_t seed, bool seed_validity) {
73+
double gdv_fn_random_with_seed(int64_t ptr, int32_t /*seed*/, bool /*seed_validity*/) {
7474
gandiva::RandomGeneratorHolder* holder =
7575
reinterpret_cast<gandiva::RandomGeneratorHolder*>(ptr);
7676
return (*holder)();
7777
}
7878

79+
int32_t gdv_fn_rand_integer(int64_t ptr) {
80+
gandiva::RandomIntegerGeneratorHolder* holder =
81+
reinterpret_cast<gandiva::RandomIntegerGeneratorHolder*>(ptr);
82+
return (*holder)();
83+
}
84+
85+
int32_t gdv_fn_rand_integer_with_range(int64_t ptr, int32_t /*range*/,
86+
bool /*range_validity*/) {
87+
gandiva::RandomIntegerGeneratorHolder* holder =
88+
reinterpret_cast<gandiva::RandomIntegerGeneratorHolder*>(ptr);
89+
return (*holder)();
90+
}
91+
92+
int32_t gdv_fn_rand_integer_with_min_max(int64_t ptr, int32_t /*min*/,
93+
bool /*min_validity*/, int32_t /*max*/,
94+
bool /*max_validity*/) {
95+
gandiva::RandomIntegerGeneratorHolder* holder =
96+
reinterpret_cast<gandiva::RandomIntegerGeneratorHolder*>(ptr);
97+
return (*holder)();
98+
}
99+
79100
bool gdv_fn_in_expr_lookup_int32(int64_t ptr, int32_t value, bool in_validity) {
80101
if (!in_validity) {
81102
return false;
@@ -936,6 +957,22 @@ arrow::Status ExportedStubFunctions::AddMappings(Engine* engine) const {
936957
engine->AddGlobalMappingForFunc("gdv_fn_random_with_seed", types->double_type(), args,
937958
reinterpret_cast<void*>(gdv_fn_random_with_seed));
938959

960+
// gdv_fn_rand_integer
961+
args = {types->i64_type()};
962+
engine->AddGlobalMappingForFunc("gdv_fn_rand_integer", types->i32_type(), args,
963+
reinterpret_cast<void*>(gdv_fn_rand_integer));
964+
965+
args = {types->i64_type(), types->i32_type(), types->i1_type()};
966+
engine->AddGlobalMappingForFunc(
967+
"gdv_fn_rand_integer_with_range", types->i32_type(), args,
968+
reinterpret_cast<void*>(gdv_fn_rand_integer_with_range));
969+
970+
args = {types->i64_type(), types->i32_type(), types->i1_type(), types->i32_type(),
971+
types->i1_type()};
972+
engine->AddGlobalMappingForFunc(
973+
"gdv_fn_rand_integer_with_min_max", types->i32_type(), args,
974+
reinterpret_cast<void*>(gdv_fn_rand_integer_with_min_max));
975+
939976
// gdv_fn_dec_from_string
940977
args = {
941978
types->i64_type(), // context

cpp/src/gandiva/gdv_function_stubs_test.cc

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,8 @@
2121
#include <gmock/gmock.h>
2222
#include <gtest/gtest.h>
2323

24+
#include <limits>
25+
2426
#include "arrow/util/logging.h"
2527
#include "gandiva/execution_context.h"
2628
#include "gandiva/encrypt_utils_ecb.h"
@@ -353,6 +355,14 @@ TEST(TestGdvFnStubs, TestCastVARCHARFromInt64) {
353355
out_str = gdv_fn_castVARCHAR_int64_int64(ctx_ptr, 12345, 3, &out_len);
354356
EXPECT_EQ(std::string(out_str, out_len), "123");
355357
EXPECT_FALSE(ctx.has_error());
358+
359+
out_str = gdv_fn_castVARCHAR_int64_int64(ctx_ptr, 347, 0, &out_len);
360+
EXPECT_EQ(std::string(out_str, out_len), "");
361+
EXPECT_FALSE(ctx.has_error());
362+
363+
out_str = gdv_fn_castVARCHAR_int64_int64(ctx_ptr, 347, -1, &out_len);
364+
EXPECT_THAT(ctx.get_error(), ::testing::HasSubstr("Buffer length cannot be negative"));
365+
ctx.Reset();
356366
}
357367

358368
TEST(TestGdvFnStubs, TestCastVARCHARFromMilliseconds) {
@@ -384,6 +394,15 @@ TEST(TestGdvFnStubs, TestCastVARCHARFromMilliseconds) {
384394
out_str = gdv_fn_castVARCHAR_date64_int64(ctx_ptr, ts, 4, &out_len);
385395
EXPECT_EQ(std::string(out_str, out_len), "2008");
386396
EXPECT_FALSE(ctx.has_error());
397+
398+
ts = StringToTimestamp("2021-04-23 10:20:33");
399+
out_str = gdv_fn_castVARCHAR_date64_int64(ctx_ptr, ts, 0, &out_len);
400+
EXPECT_EQ(std::string(out_str, out_len), "");
401+
EXPECT_FALSE(ctx.has_error());
402+
403+
out_str = gdv_fn_castVARCHAR_date64_int64(ctx_ptr, ts, -1, &out_len);
404+
EXPECT_THAT(ctx.get_error(), ::testing::HasSubstr("Buffer length cannot be negative"));
405+
ctx.Reset();
387406
}
388407

389408
TEST(TestGdvFnStubs, TestCastVARCHARFromFloat) {
@@ -419,6 +438,14 @@ TEST(TestGdvFnStubs, TestCastVARCHARFromFloat) {
419438
out_str = gdv_fn_castVARCHAR_float32_int64(ctx_ptr, 1.2345f, 3, &out_len);
420439
EXPECT_EQ(std::string(out_str, out_len), "1.2");
421440
EXPECT_FALSE(ctx.has_error());
441+
442+
out_str = gdv_fn_castVARCHAR_float32_int64(ctx_ptr, 1.2345f, 0, &out_len);
443+
EXPECT_EQ(std::string(out_str, out_len), "");
444+
EXPECT_FALSE(ctx.has_error());
445+
446+
out_str = gdv_fn_castVARCHAR_float32_int64(ctx_ptr, 1.2345f, -1, &out_len);
447+
EXPECT_THAT(ctx.get_error(), ::testing::HasSubstr("Buffer length cannot be negative"));
448+
ctx.Reset();
422449
}
423450

424451
TEST(TestGdvFnStubs, TestCastVARCHARFromDouble) {
@@ -454,6 +481,25 @@ TEST(TestGdvFnStubs, TestCastVARCHARFromDouble) {
454481
out_str = gdv_fn_castVARCHAR_float64_int64(ctx_ptr, 1.2345, 3, &out_len);
455482
EXPECT_EQ(std::string(out_str, out_len), "1.2");
456483
EXPECT_FALSE(ctx.has_error());
484+
485+
out_str = gdv_fn_castVARCHAR_float64_int64(ctx_ptr, 1.2345, 0, &out_len);
486+
EXPECT_EQ(std::string(out_str, out_len), "");
487+
EXPECT_FALSE(ctx.has_error());
488+
489+
out_str = gdv_fn_castVARCHAR_float64_int64(ctx_ptr, 1.2345, -1, &out_len);
490+
EXPECT_THAT(ctx.get_error(), ::testing::HasSubstr("Buffer length cannot be negative"));
491+
ctx.Reset();
492+
493+
// test long repeating decimal (1/3) with large buffer
494+
out_str = gdv_fn_castVARCHAR_float64_int64(ctx_ptr, 1.0 / 3.0, 100, &out_len);
495+
EXPECT_EQ(std::string(out_str, out_len), "0.3333333333333333");
496+
EXPECT_FALSE(ctx.has_error());
497+
498+
// test exponential notation with large negative exponent (24 chars)
499+
out_str =
500+
gdv_fn_castVARCHAR_float64_int64(ctx_ptr, -1.2345678901234567e-100, 100, &out_len);
501+
EXPECT_EQ(std::string(out_str, out_len), "-1.2345678901234567E-100");
502+
EXPECT_FALSE(ctx.has_error());
457503
}
458504

459505
TEST(TestGdvFnStubs, TestSubstringIndex) {
@@ -529,6 +575,21 @@ TEST(TestGdvFnStubs, TestSubstringIndex) {
529575
out_str = gdv_fn_substring_index(ctx_ptr, "路学\\L", 8, "\\", 1, -1, &out_len);
530576
EXPECT_EQ(std::string(out_str, out_len), "L");
531577
EXPECT_FALSE(ctx.has_error());
578+
579+
// Large counts return full string when delimiter not found enough times
580+
out_str = gdv_fn_substring_index(ctx_ptr, "a.b.c", 5, ".", 1, -1000, &out_len);
581+
EXPECT_EQ(std::string(out_str, out_len), "a.b.c");
582+
EXPECT_FALSE(ctx.has_error());
583+
584+
out_str = gdv_fn_substring_index(ctx_ptr, "a.b.c", 5, ".", 1,
585+
std::numeric_limits<int32_t>::max(), &out_len);
586+
EXPECT_EQ(std::string(out_str, out_len), "a.b.c");
587+
EXPECT_FALSE(ctx.has_error());
588+
589+
out_str = gdv_fn_substring_index(ctx_ptr, "a.b.c", 5, ".", 1,
590+
std::numeric_limits<int32_t>::min(), &out_len);
591+
EXPECT_EQ(std::string(out_str, out_len), "a.b.c");
592+
EXPECT_FALSE(ctx.has_error());
532593
}
533594

534595
TEST(TestGdvFnStubs, TestUpper) {

0 commit comments

Comments
 (0)