From 6464c405f0a73684bdad83c57705c63154dbcaa0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D0=BB=D0=B5=D0=BA=D1=81=D0=B0=D0=BD=D0=B4=D1=80=20?= =?UTF-8?q?=D0=9D=D0=BE=D0=B2=D0=BE=D0=B6=D0=B8=D0=BB=D0=BE=D0=B2?= Date: Mon, 12 Aug 2024 21:02:32 +0300 Subject: [PATCH] Double free when accessing .AsBoxed() on Pod with 0 refcount (#7659) --- ydb/library/yql/parser/pg_wrapper/utils.h | 2 +- ydb/library/yql/public/udf/udf_value.h | 2 ++ ydb/library/yql/public/udf/udf_value_inl.h | 12 ++++++++++++ 3 files changed, 15 insertions(+), 1 deletion(-) diff --git a/ydb/library/yql/parser/pg_wrapper/utils.h b/ydb/library/yql/parser/pg_wrapper/utils.h index 2e17dce6dbdf..30f3d486a39c 100644 --- a/ydb/library/yql/parser/pg_wrapper/utils.h +++ b/ydb/library/yql/parser/pg_wrapper/utils.h @@ -65,7 +65,7 @@ inline NKikimr::NUdf::TUnboxedValuePod AnyDatumToPod(Datum datum, bool passByVal } inline Datum PointerDatumFromPod(const NKikimr::NUdf::TUnboxedValuePod& value) { - return (Datum)(((const NKikimr::NMiniKQL::TMkqlPAllocHeader*)value.AsBoxed().Get()) + 1); + return (Datum)(((const NKikimr::NMiniKQL::TMkqlPAllocHeader*)value.AsRawBoxed()) + 1); } inline Datum PointerDatumFromItem(const NKikimr::NUdf::TBlockItem& value) { diff --git a/ydb/library/yql/public/udf/udf_value.h b/ydb/library/yql/public/udf/udf_value.h index e8cf3933bf0e..035172a9a2af 100644 --- a/ydb/library/yql/public/udf/udf_value.h +++ b/ydb/library/yql/public/udf/udf_value.h @@ -827,6 +827,8 @@ friend class TUnboxedValue; inline TStringValue AsStringValue() const; inline IBoxedValuePtr AsBoxed() const; + inline TStringValue::TData* AsRawStringValue() const; + inline IBoxedValue* AsRawBoxed() const; inline bool UniqueBoxed() const; // special values diff --git a/ydb/library/yql/public/udf/udf_value_inl.h b/ydb/library/yql/public/udf/udf_value_inl.h index 7a336d8e67ac..a5ca167792c7 100644 --- a/ydb/library/yql/public/udf/udf_value_inl.h +++ b/ydb/library/yql/public/udf/udf_value_inl.h @@ -390,6 +390,18 @@ inline IBoxedValuePtr TUnboxedValuePod::AsBoxed() const return IBoxedValuePtr(Raw.Boxed.Value); } +inline TStringValue::TData* TUnboxedValuePod::AsRawStringValue() const +{ + UDF_VERIFY(IsString(), "Value is not a string"); + return Raw.String.Value; +} + +inline IBoxedValue* TUnboxedValuePod::AsRawBoxed() const +{ + UDF_VERIFY(IsBoxed(), "Value is not boxed"); + return Raw.Boxed.Value; +} + inline bool TUnboxedValuePod::UniqueBoxed() const { UDF_VERIFY(IsBoxed(), "Value is not boxed");