chore: import upstream snapshot with attribution

This commit is contained in:
wehub-resource-sync
2026-07-13 12:40:42 +08:00
commit e25996e7db
15472 changed files with 3536181 additions and 0 deletions
+12
View File
@@ -0,0 +1,12 @@
proto_library(framework_proto SRCS framework.proto)
proto_library(pass_desc_proto SRCS pass_desc.proto DEPS framework_proto)
proto_library(data_feed_proto SRCS data_feed.proto)
proto_library(trainer_desc_proto SRCS trainer_desc.proto DEPS framework_proto
data_feed_proto)
proto_library(heter_service_proto SRCS heter_service.proto)
file(
GLOB framework_cc
RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}"
"*.cc")
collect_srcs(core_srcs SRCS ${framework_cc})
+28
View File
@@ -0,0 +1,28 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#pragma once
#include "paddle/phi/core/framework/var_type_helper.h"
#include "paddle/phi/core/utils/data_type.h"
namespace phi {
inline paddle::framework::proto::VarType::Type TransToProtoVarTypeReturnType(
const DataType& dtype) {
return static_cast<paddle::framework::proto::VarType::Type>(
phi::TransToProtoVarType(dtype));
}
} // namespace phi
+67
View File
@@ -0,0 +1,67 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
syntax = "proto2";
package paddle.framework;
message Slot {
required string name = 1;
required string type = 2;
optional bool is_dense = 3 [ default = false ];
optional bool is_used = 4 [ default = false ];
repeated int32 shape = 5; // we can define N-D phi::DenseTensor
}
message MultiSlotDesc {
repeated Slot slots = 1;
optional string uid_slot = 2;
}
message GraphConfig {
optional int32 walk_degree = 1 [ default = 1 ];
optional int32 walk_len = 2 [ default = 20 ];
optional int32 window = 3 [ default = 5 ];
optional int32 once_sample_startid_len = 4 [ default = 8000 ];
optional int32 sample_times_one_chunk = 5 [ default = 10 ];
optional int32 batch_size = 6 [ default = 1 ];
optional int32 debug_mode = 7 [ default = 0 ];
optional string first_node_type = 8;
optional string meta_path = 9;
optional bool gpu_graph_training = 10 [ default = true ];
optional bool sage_mode = 11 [ default = false ];
optional string samples = 12;
optional int64 train_table_cap = 13 [ default = 80000 ];
optional int64 infer_table_cap = 14 [ default = 80000 ];
optional string excluded_train_pair = 15;
optional string infer_node_type = 16;
optional bool get_degree = 17 [ default = false ];
optional bool weighted_sample = 18 [ default = false ];
optional bool return_weight = 19 [ default = false ];
optional string pair_label = 20;
optional bool is_thread_sharding = 21 [ default = false ];
optional int32 accumulate_num = 22 [ default = 1 ];
}
message DataFeedDesc {
optional string name = 1;
optional int32 batch_size = 2 [ default = 32 ];
optional MultiSlotDesc multi_slot_desc = 3;
optional string pipe_command = 4;
optional int32 thread_num = 5;
optional string rank_offset = 6;
optional int32 pv_batch_size = 7 [ default = 32 ];
optional int32 input_type = 8 [ default = 0 ];
optional string so_parser_name = 9;
optional GraphConfig graph_config = 10;
}
@@ -0,0 +1,253 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#include "paddle/phi/core/framework/data_type_transform.h"
#include "paddle/phi/common/transform.h"
#include "paddle/phi/core/framework/convert_utils.h"
#include "paddle/phi/core/framework/selected_rows_serialize.h"
#include "paddle/phi/core/kernel_factory.h"
#if defined(PADDLE_WITH_XPU)
#include "paddle/phi/core/platform/device/device_wrapper.h"
#endif
namespace proto = paddle::framework::proto;
namespace phi {
template <typename InType, typename OutType>
struct CastDataTypeFunctor {
HOSTDEVICE inline OutType operator()(InType in) const {
#if defined(_MSC_VER)
// Avoid unsupported convert of float8/bfloat16/float16 -> complex
if constexpr (
(std::is_same_v<OutType, phi::complex64> ||
std::is_same_v<
OutType,
phi::complex128>)&&(std::is_same_v<InType, phi::float8_e4m3fn> ||
std::is_same_v<InType, phi::float8_e5m2> ||
std::is_same_v<InType, phi::bfloat16> ||
std::is_same_v<InType, phi::float16>)) {
// default valueonly to avoid compile error
return OutType(0);
} else {
return static_cast<OutType>(in);
}
#else
return static_cast<OutType>(in);
#endif
}
};
#if defined(PADDLE_WITH_XPU)
template <typename InType, typename OutType>
static void XPUCastData(const DenseTensor& in,
DenseTensor* out,
const phi::XPUContext* dev_ctx) {
using XPUInTDType = typename XPUTypeTrait<InType>::Type;
using XPUOutTDType = typename XPUTypeTrait<OutType>::Type;
int r = xpu::cast<XPUInTDType, XPUOutTDType>(
dev_ctx->x_context(),
reinterpret_cast<const XPUInTDType*>(in.data<InType>()),
reinterpret_cast<XPUOutTDType*>(dev_ctx->Alloc<OutType>(out)),
in.numel());
PADDLE_ENFORCE_XDNN_SUCCESS(r, "cast");
dev_ctx->Wait();
}
template <typename InType>
static void XPUTransDataType(
const DenseTensor& in,
DenseTensor* out,
const paddle::framework::proto::VarType::Type& dst_type,
const phi::DeviceContext* ctx) {
auto* context = static_cast<const phi::XPUContext*>(ctx);
#define XPUCastCallback(cpp_type, proto_type) \
do { \
if (dst_type == proto_type) { \
XPUCastData<InType, cpp_type>(in, out, context); \
} \
} while (0)
if (dst_type == proto::VarType::FP32 || dst_type == proto::VarType::FP16 ||
dst_type == proto::VarType::BOOL || dst_type == proto::VarType::INT16 ||
dst_type == proto::VarType::INT32 || dst_type == proto::VarType::INT64 ||
dst_type == proto::VarType::FP64) {
_ForEachDataTypeForXPU_(XPUCastCallback);
} else {
PADDLE_THROW(common::errors::Unimplemented(
"Data type (%s) is not supported in XPU when casting data type.",
VarDataTypeToString(dst_type)));
}
}
#endif
template <typename InType>
struct CastDataType {
CastDataType(const DenseTensor& in,
DenseTensor* out,
const phi::DeviceContext* ctx)
: in_(in), out_(out), ctx_(ctx) {}
const DenseTensor in_;
DenseTensor* out_;
const phi::DeviceContext* ctx_;
template <typename OutType>
void apply() {
auto* in_begin = in_.data<InType>();
auto* in_end = in_begin + in_.numel();
auto* out_begin = ctx_->Alloc<OutType>(out_);
if (phi::is_cpu_place(in_.place())) {
phi::Transform<phi::CPUContext> trans;
auto* context = static_cast<const phi::CPUContext*>(ctx_);
trans(*context,
in_begin,
in_end,
out_begin,
CastDataTypeFunctor<InType, OutType>());
#if defined(__NVCC__) || defined(__HIPCC__)
} else if (phi::is_gpu_place(in_.place())) {
phi::Transform<phi::GPUContext> trans;
auto* context = static_cast<const phi::GPUContext*>(ctx_);
trans(*context,
in_begin,
in_end,
out_begin,
CastDataTypeFunctor<InType, OutType>());
context->Wait();
#endif
#if defined(PADDLE_WITH_IPU)
} else if (phi::is_ipu_place(in_.place())) {
phi::Transform<phi::CPUContext> trans;
auto* context = static_cast<const phi::CPUContext*>(ctx_);
trans(*context,
in_begin,
in_end,
out_begin,
CastDataTypeFunctor<InType, OutType>());
#endif
} else {
PADDLE_THROW(common::errors::Unimplemented(
"Place type is not supported when casting data type."));
}
}
};
void TransDataType(const phi::KernelKey& kernel_type_for_var,
const phi::KernelKey& expected_kernel_type,
const DenseTensor& in,
DenseTensor* out) {
PADDLE_ENFORCE_EQ(in.dtype(),
kernel_type_for_var.dtype(),
common::errors::InvalidArgument(
"The src dtype(%s) of input tensor and kernel_type(%s) "
"are not consistent.",
DataTypeToString(in.dtype()),
DataTypeToString(kernel_type_for_var.dtype())));
auto dst_type =
phi::TransToProtoVarTypeReturnType(expected_kernel_type.dtype());
TransDataType(in, dst_type, out);
}
void TransDataType(const DenseTensor& in,
const paddle::framework::proto::VarType::Type& type,
DenseTensor* out) {
phi::DeviceContextPool& pool = phi::DeviceContextPool::Instance();
out->Resize(in.dims());
auto src_type = phi::TransToProtoVarTypeReturnType(in.dtype());
auto dst_type = type;
auto ctx = pool.Get(in.place());
#if defined(PADDLE_WITH_XPU)
if (phi::is_xpu_place(in.place())) {
switch (src_type) {
case proto::VarType::FP16:
XPUTransDataType<phi::float16>(in, out, dst_type, ctx);
break;
case proto::VarType::FP32:
XPUTransDataType<float>(in, out, dst_type, ctx);
break;
case proto::VarType::FP64:
XPUTransDataType<double>(in, out, dst_type, ctx);
break;
case proto::VarType::BOOL:
XPUTransDataType<bool>(in, out, dst_type, ctx);
break;
case proto::VarType::INT16:
XPUTransDataType<int16_t>(in, out, dst_type, ctx);
break;
case proto::VarType::INT32:
XPUTransDataType<int>(in, out, dst_type, ctx);
break;
case proto::VarType::INT64:
XPUTransDataType<int64_t>(in, out, dst_type, ctx);
break;
default:
PADDLE_THROW(common::errors::Unimplemented(
"Data type (%s) is not supported in XPU when casting data type.",
VarDataTypeToString(src_type)));
}
return;
}
#endif
switch (src_type) {
case proto::VarType::FP16:
phi::VisitDataType(dst_type, CastDataType<phi::float16>(in, out, ctx));
break;
case proto::VarType::BF16:
phi::VisitDataType(dst_type, CastDataType<phi::bfloat16>(in, out, ctx));
break;
case proto::VarType::FP8_E4M3FN:
phi::VisitDataType(dst_type,
CastDataType<phi::float8_e4m3fn>(in, out, ctx));
break;
case proto::VarType::FP8_E5M2:
phi::VisitDataType(dst_type,
CastDataType<phi::float8_e5m2>(in, out, ctx));
break;
case proto::VarType::FP32:
phi::VisitDataType(dst_type, CastDataType<float>(in, out, ctx));
break;
case proto::VarType::FP64:
phi::VisitDataType(dst_type, CastDataType<double>(in, out, ctx));
break;
case proto::VarType::INT32:
phi::VisitDataType(dst_type, CastDataType<int>(in, out, ctx));
break;
case proto::VarType::INT64:
phi::VisitDataType(dst_type, CastDataType<int64_t>(in, out, ctx));
break;
case proto::VarType::BOOL:
phi::VisitDataType(dst_type, CastDataType<bool>(in, out, ctx));
break;
case proto::VarType::INT16:
phi::VisitDataType(dst_type, CastDataType<int16_t>(in, out, ctx));
break;
case proto::VarType::UINT8:
phi::VisitDataType(dst_type, CastDataType<uint8_t>(in, out, ctx));
break;
default:
PADDLE_THROW(common::errors::Unimplemented(
"Data type (%s) is not supported when casting data type.",
VarDataTypeToString(src_type)));
}
}
} // namespace phi
@@ -0,0 +1,32 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#pragma once
#include <utility>
#include "paddle/phi/core/framework/var_type_helper.h"
#include "paddle/phi/core/platform/device_context.h"
#include "paddle/phi/core/tensor_utils.h"
namespace phi {
void TransDataType(const KernelKey& kernel_type_for_var,
const KernelKey& expected_kernel_type,
const DenseTensor& in,
DenseTensor* out);
void TransDataType(const DenseTensor& in,
const paddle::framework::proto::VarType::Type& type,
DenseTensor* out);
} // namespace phi
@@ -0,0 +1,130 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#include "paddle/phi/core/framework/dense_tensor_serialize.h"
#include <cstdint>
#include "paddle/phi/core/framework/convert_utils.h"
namespace phi {
void SerializeToStream(std::ostream &os,
const DenseTensor &tensor,
const DeviceContext &dev_ctx) {
constexpr uint32_t kCurTensorVersion = 0;
{ // the 1st field, uint32_t version for DenseTensor
os.write(reinterpret_cast<const char *>(&kCurTensorVersion),
sizeof(kCurTensorVersion));
}
{
// the 2nd field, LoD information
// uint64_t lod_level
// uint64_t lod_level_1 size in byte.
// int* lod_level_1 data
// ...
auto lod = tensor.lod();
uint64_t size = lod.size();
os.write(reinterpret_cast<const char *>(&size), sizeof(size));
for (auto &each : lod) {
size = each.size() * sizeof(LegacyLoD::value_type::value_type);
os.write(reinterpret_cast<const char *>(&size), sizeof(size));
os.write(reinterpret_cast<const char *>(each.data()),
static_cast<std::streamsize>(size));
}
}
// the 3rd field, Tensor
TensorToStream(os, static_cast<DenseTensor>(tensor), dev_ctx);
}
void SerializeToStream(std::ostream &os, const DenseTensor &tensor) {
DeviceContextPool &pool = DeviceContextPool::Instance();
const DeviceContext *dev_ctx = nullptr;
auto place = tensor.place();
dev_ctx = pool.Get(place);
SerializeToStream(os, tensor, *dev_ctx);
}
void DeserializeFromStream(std::istream &os, DenseTensor *tensor) {
DeviceContextPool &pool = DeviceContextPool::Instance();
const DeviceContext *dev_ctx = nullptr;
dev_ctx = pool.Get(CPUPlace());
DeserializeFromStream(os, tensor, *dev_ctx);
}
void DeserializeFromStream(std::istream &is,
DenseTensor *tensor,
const DeviceContext &dev_ctx,
const size_t &seek,
const std::vector<int64_t> &shape) {
{
// the 1st field, unit32_t version for DenseTensor
uint32_t version = 0;
is.read(reinterpret_cast<char *>(&version), sizeof(version));
PADDLE_ENFORCE_EQ(
version,
0U,
common::errors::InvalidArgument(
"Deserialize to tensor failed, maybe the loaded file is "
"not a paddle model(expected file format: 0, but %u found).",
version));
}
{
// the 2nd field, LoD information
uint64_t lod_level = 0;
is.read(reinterpret_cast<char *>(&lod_level), sizeof(lod_level));
auto &lod = *tensor->mutable_lod();
lod.resize(lod_level);
}
// the 3rd field, Tensor
TensorFromStream(
is, static_cast<DenseTensor *>(tensor), dev_ctx, seek, shape);
}
void DeserializeFromStream(std::istream &is,
DenseTensor *tensor,
const DeviceContext &dev_ctx) {
{
// the 1st field, unit32_t version for DenseTensor
uint32_t version = 0;
is.read(reinterpret_cast<char *>(&version), sizeof(version));
PADDLE_ENFORCE_EQ(
version,
0U,
common::errors::InvalidArgument(
"Deserialize to tensor failed, maybe the loaded file is "
"not a paddle model(expected file format: 0, but %u found).",
version));
}
{
// the 2nd field, LoD information
uint64_t lod_level = 0;
is.read(reinterpret_cast<char *>(&lod_level), sizeof(lod_level));
auto &lod = *tensor->mutable_lod();
lod.resize(lod_level);
for (uint64_t i = 0; i < lod_level; ++i) {
uint64_t size = 0;
is.read(reinterpret_cast<char *>(&size), sizeof(size));
std::vector<size_t> tmp(size / sizeof(size_t));
is.read(reinterpret_cast<char *>(tmp.data()),
static_cast<std::streamsize>(size));
lod[i] = tmp;
}
}
// the 3rd field, Tensor
TensorFromStream(is, static_cast<DenseTensor *>(tensor), dev_ctx);
}
} // namespace phi
@@ -0,0 +1,50 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#pragma once
#include <memory>
#include <utility>
#include "paddle/common/ddim.h"
#include "paddle/phi/common/place.h"
#include "paddle/phi/core/dense_tensor.h"
#include "paddle/phi/core/enforce.h"
#include "paddle/phi/core/framework/dense_tensor_tostream.h"
#include "paddle/phi/core/mixed_vector.h"
#include "paddle/utils/test_macros.h"
namespace phi {
/*
* Serialize/Deserialize DenseTensor to std::ostream
* You can pass ofstream or ostringstream to serialize to file
* or to a in memory string. GPU tensor will be copied to CPU.
*/
PADDLE_API void SerializeToStream(std::ostream& os,
const DenseTensor& tensor,
const DeviceContext& dev_ctx);
PADDLE_API void DeserializeFromStream(std::istream& is,
DenseTensor* tensor,
const DeviceContext& dev_ctx);
PADDLE_API void DeserializeFromStream(std::istream& is,
DenseTensor* tensor,
const DeviceContext& dev_ctx,
const size_t& seek,
const std::vector<int64_t>& shape);
PADDLE_API void SerializeToStream(std::ostream& os, const DenseTensor& tensor);
PADDLE_API void DeserializeFromStream(std::istream& os, DenseTensor* tensor);
} // namespace phi
@@ -0,0 +1,370 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#include "paddle/phi/core/framework/dense_tensor_tostream.h"
#include <algorithm>
#include <functional>
#include <limits>
#include <memory>
#include <string>
#include <utility>
#include <vector>
#include "paddle/phi/backends/context_pool.h"
#include "paddle/phi/common/memory_utils.h"
#include "paddle/phi/core/compat/convert_utils.h"
#include "paddle/phi/core/framework/convert_utils.h"
#include "paddle/phi/core/kernel_factory.h"
#include "paddle/phi/core/tensor_utils.h"
#include "paddle/phi/kernels/contiguous_kernel.h"
namespace phi {
namespace proto = paddle::framework::proto;
template <typename Context>
DenseTensor InnerTensorContiguous(const Context& dev_ctx,
const DenseTensor& tensor) {
DenseTensor dense_out;
MetaTensor meta_input(tensor);
MetaTensor meta_out(&dense_out);
UnchangedInferMeta(meta_input, &meta_out);
PD_VISIT_ALL_TYPES(tensor.dtype(), "InnerTensorContiguous", ([&] {
ContiguousKernel<data_t, Context>(
dev_ctx, tensor, &dense_out);
}));
return dense_out;
}
DenseTensor InnerTensorContiguous(const DenseTensor& tensor) {
auto& pool = DeviceContextPool::Instance();
if (tensor.place().GetType() == AllocationType::CPU) {
auto* dev_ctx = static_cast<CPUContext*>(pool.Get(tensor.place()));
return InnerTensorContiguous<CPUContext>(*dev_ctx, tensor);
#if defined(PADDLE_WITH_CUDA) || defined(PADDLE_WITH_HIP)
} else if (tensor.place().GetType() == AllocationType::GPU) {
auto* dev_ctx = static_cast<GPUContext*>(pool.Get(tensor.place()));
return InnerTensorContiguous<GPUContext>(*dev_ctx, tensor);
#endif
#ifdef PADDLE_WITH_XPU
} else if (tensor.place().GetType() == AllocationType::XPU) {
auto* dev_ctx = static_cast<XPUContext*>(pool.Get(tensor.place()));
return InnerTensorContiguous<XPUContext>(*dev_ctx, tensor);
#endif
#ifdef PADDLE_WITH_CUSTOM_DEVICE
} else if (tensor.place().GetType() == AllocationType::CUSTOM) {
auto* dev_ctx = static_cast<CustomContext*>(pool.Get(tensor.place()));
DenseTensor dense_out;
MetaTensor meta_input(tensor);
MetaTensor meta_out(&dense_out);
UnchangedInferMeta(meta_input, &meta_out);
const KernelKey& kernel_key = {TransToPhiBackend(tensor.place()),
DataLayout::ALL_LAYOUT,
tensor.dtype()};
using kernel_signature =
void (*)(const DeviceContext&, const DenseTensor&, DenseTensor*);
PD_VISIT_KERNEL("contiguous",
kernel_key,
kernel_signature,
false,
*dev_ctx,
tensor,
&dense_out);
return dense_out;
#endif
} else {
PADDLE_THROW(common::errors::Unimplemented(
"Place type is not supported when casting data type."));
}
return tensor;
}
void TensorToStream(std::ostream& os,
const DenseTensor& tensor,
const DeviceContext& dev_ctx) {
const auto ensure_contiguous = [](const DenseTensor& tensor) {
if (tensor.meta().is_contiguous()) {
return tensor;
}
return InnerTensorContiguous(tensor);
};
const DenseTensor& contiguous_tensor = ensure_contiguous(tensor);
{ // the 1st field, uint32_t version
constexpr uint32_t version = 0;
os.write(reinterpret_cast<const char*>(&version), sizeof(version));
}
{ // the 2nd field, tensor description
// int32_t size
// void* protobuf message
proto::VarType::TensorDesc desc;
desc.set_data_type(
TransToProtoVarTypeReturnType(contiguous_tensor.dtype()));
auto dims = common::vectorize(contiguous_tensor.dims());
auto* pb_dims = desc.mutable_dims();
pb_dims->Resize(static_cast<int>(dims.size()), 0);
std::copy(dims.begin(), dims.end(), pb_dims->begin());
int32_t size = static_cast<int32_t>(desc.ByteSizeLong());
os.write(reinterpret_cast<const char*>(&size), sizeof(size));
auto out = desc.SerializeAsString();
os.write(out.data(), size);
}
{ // the 3rd field, tensor data
uint64_t size =
contiguous_tensor.numel() * SizeOf(contiguous_tensor.dtype());
auto* data_ptr = contiguous_tensor.data();
PADDLE_ENFORCE_LT(size,
(std::numeric_limits<std::streamsize>::max)(),
common::errors::ResourceExhausted(
"tensor size %d overflow when writing tensor", size));
if (is_gpu_place(contiguous_tensor.place())) {
#if defined(PADDLE_WITH_CUDA) || defined(PADDLE_WITH_HIP)
constexpr size_t kBufSize = 1024 * 1024 * 64; // 64MB
std::unique_ptr<char[]> buf(new char[kBufSize]);
auto& gpu_dev_ctx = static_cast<const GPUContext&>(dev_ctx);
CPUPlace cpu;
uintptr_t data = reinterpret_cast<uintptr_t>(data_ptr);
while (size != 0) {
size_t size_to_write = std::min(kBufSize, static_cast<size_t>(size));
memory_utils::Copy(cpu,
buf.get(),
contiguous_tensor.place(),
reinterpret_cast<const void*>(data), // NOLINT
size_to_write,
gpu_dev_ctx.stream());
gpu_dev_ctx.Wait();
os.write(buf.get(), size_to_write);
data += size_to_write;
size -= size_to_write;
}
#else
PADDLE_THROW(common::errors::Unimplemented(
"CUDAPlace is not supported when not compiled with CUDA"));
#endif
} else if (is_xpu_place(contiguous_tensor.place())) {
#ifdef PADDLE_WITH_XPU
constexpr size_t kBufSize = 1024 * 1024 * 64; // 64MB
std::unique_ptr<char[]> buf(new char[kBufSize]);
auto& xpu_dev_ctx = static_cast<const XPUContext&>(dev_ctx);
CPUPlace cpu;
uintptr_t data = reinterpret_cast<uintptr_t>(data_ptr);
while (size != 0) {
size_t size_to_write = std::min(kBufSize, static_cast<size_t>(size));
memory_utils::Copy(cpu,
buf.get(),
contiguous_tensor.place(),
reinterpret_cast<const void*>(data),
size_to_write);
xpu_dev_ctx.Wait();
os.write(buf.get(), size_to_write);
data += size_to_write;
size -= size_to_write;
}
#else
PADDLE_THROW(common::errors::Unimplemented(
"XPUPlace is not supported when not compiled with XPU"));
#endif
} else if (is_custom_place(contiguous_tensor.place())) {
#ifdef PADDLE_WITH_CUSTOM_DEVICE
constexpr size_t kBufSize = 1024 * 1024 * 64; // 64MB
std::unique_ptr<char[]> buf(new char[kBufSize]); // NOLINT
auto& custom_device_context = static_cast<const CustomContext&>(dev_ctx);
CPUPlace cpu;
uintptr_t data = reinterpret_cast<uintptr_t>(data_ptr);
while (size != 0) {
size_t size_to_write = std::min(kBufSize, static_cast<size_t>(size));
memory_utils::Copy(cpu,
buf.get(),
contiguous_tensor.place(),
reinterpret_cast<const void*>(data),
size_to_write,
custom_device_context.stream());
custom_device_context.Wait();
os.write(buf.get(), size_to_write);
data += size_to_write;
size -= size_to_write;
}
#else
PADDLE_THROW(common::errors::Unimplemented(
"CustomPlace is not supported when not compiled with "
"CustomDevice"));
#endif
} else {
os.write(static_cast<const char*>(data_ptr),
static_cast<std::streamsize>(size));
}
}
}
struct DeserializedDataFunctor {
DeserializedDataFunctor(void** buf, DenseTensor* tensor, const Place& place)
: buf_(buf), tensor_(tensor), place_(place) {}
template <typename T>
void apply() {
auto& pool = DeviceContextPool::Instance();
auto* dev_ctx = pool.Get(place_);
*buf_ = dev_ctx->Alloc<T>(tensor_);
}
void** buf_;
DenseTensor* tensor_;
Place place_;
};
void TensorFromStream(std::istream& is,
DenseTensor* tensor,
const DeviceContext& dev_ctx,
const size_t& seek,
const std::vector<int64_t>& shape) {
uint32_t version = 0;
is.read(reinterpret_cast<char*>(&version), sizeof(version));
PADDLE_ENFORCE_EQ(
version,
0U,
common::errors::InvalidArgument(
"tensor version %u is not supported, Only version 0 is supported",
version));
proto::VarType::TensorDesc desc;
{ // int32_t size
// proto buffer
int32_t size = 0;
is.read(reinterpret_cast<char*>(&size), sizeof(size));
std::unique_ptr<char[]> buf(new char[size]); // NOLINT
is.read(reinterpret_cast<char*>(buf.get()), size);
PADDLE_ENFORCE_EQ(
desc.ParseFromArray(buf.get(), size),
true,
common::errors::InvalidArgument("Cannot parse tensor desc"));
}
{ // read tensor
tensor->Resize(common::make_ddim(shape));
size_t seekg = seek * SizeOfType(desc.data_type());
is.seekg(seekg, is.cur); // NOLINT
void* buf = nullptr;
CPUContext ctx;
size_t size = tensor->numel() * SizeOfType(desc.data_type());
if (is_gpu_place(dev_ctx.GetPlace()) || is_xpu_place(dev_ctx.GetPlace()) ||
is_custom_place(dev_ctx.GetPlace())) {
#if defined(PADDLE_WITH_CUDA) || defined(PADDLE_WITH_HIP) || \
defined(PADDLE_WITH_XPU) || defined(PADDLE_WITH_CUSTOM_DEVICE)
DenseTensor cpu_tensor;
cpu_tensor.Resize(common::make_ddim(shape));
VisitDataType(desc.data_type(),
DeserializedDataFunctor(&buf, &cpu_tensor, ctx.GetPlace()));
is.read(static_cast<char*>(buf), size); // NOLINT
auto dst_place = dev_ctx.GetPlace();
Copy(dev_ctx, cpu_tensor, dst_place, false, tensor);
if (is_custom_place(dev_ctx.GetPlace())) {
dev_ctx.Wait();
}
#else
if (is_gpu_place(dev_ctx.GetPlace())) {
PADDLE_THROW(common::errors::Unimplemented(
"CUDAPlace is not supported when not compiled with CUDA"));
} else if (is_xpu_place(dev_ctx.GetPlace())) {
PADDLE_THROW(common::errors::Unimplemented(
"XPUPlace is not supported when not compiled with XPU"));
}
#endif
} else {
VisitDataType(desc.data_type(),
DeserializedDataFunctor(&buf, tensor, ctx.GetPlace()));
is.read(static_cast<char*>(buf), size); // NOLINT
}
}
}
void TensorFromStream(std::istream& is,
DenseTensor* tensor,
const DeviceContext& dev_ctx) {
uint32_t version = 0;
is.read(reinterpret_cast<char*>(&version), sizeof(version));
PADDLE_ENFORCE_EQ(
version,
0U,
common::errors::InvalidArgument(
"tensor version %u is not supported, Only version 0 is supported",
version));
proto::VarType::TensorDesc desc;
{ // int32_t size
// proto buffer
int32_t size = -1;
is.read(reinterpret_cast<char*>(&size), sizeof(size));
PADDLE_ENFORCE_EQ(
is.good(),
true,
common::errors::Unavailable("Cannot read tensor desc size"));
PADDLE_ENFORCE_GE(
size,
0,
common::errors::InvalidArgument("DenseTensor desc size should >= 0"));
std::unique_ptr<char[]> buf(new char[size]); // NOLINT
is.read(reinterpret_cast<char*>(buf.get()), size);
PADDLE_ENFORCE_EQ(
desc.ParseFromArray(buf.get(), size),
true,
common::errors::InvalidArgument("Cannot parse tensor desc"));
}
{ // read tensor
std::vector<int64_t> dims;
dims.reserve(static_cast<size_t>(desc.dims().size()));
std::copy(desc.dims().begin(), desc.dims().end(), std::back_inserter(dims));
tensor->Resize(common::make_ddim(dims));
void* buf = nullptr;
CPUContext ctx;
size_t size = tensor->numel() * SizeOfType(desc.data_type());
if (is_gpu_place(dev_ctx.GetPlace()) || is_xpu_place(dev_ctx.GetPlace()) ||
is_custom_place(dev_ctx.GetPlace())) {
#if defined(PADDLE_WITH_CUDA) || defined(PADDLE_WITH_HIP) || \
defined(PADDLE_WITH_XPU) || defined(PADDLE_WITH_CUSTOM_DEVICE)
DenseTensor cpu_tensor;
cpu_tensor.Resize(common::make_ddim(dims));
VisitDataType(desc.data_type(),
DeserializedDataFunctor(&buf, &cpu_tensor, ctx.GetPlace()));
is.read(static_cast<char*>(buf), size); // NOLINT
auto dst_place = dev_ctx.GetPlace();
Copy(dev_ctx, cpu_tensor, dst_place, false, tensor);
if (is_custom_place(dev_ctx.GetPlace())) {
dev_ctx.Wait();
}
#else
if (is_gpu_place(dev_ctx.GetPlace())) {
PADDLE_THROW(common::errors::Unimplemented(
"CUDAPlace is not supported when not compiled with CUDA"));
} else if (is_xpu_place(dev_ctx.GetPlace())) {
PADDLE_THROW(common::errors::Unimplemented(
"XPUPlace is not supported when not compiled with XPU"));
} else {
PADDLE_THROW(
common::errors::Unimplemented("CustomPlace is not supported when "
"not compiled with CustomDevice"));
}
#endif
} else {
VisitDataType(desc.data_type(),
DeserializedDataFunctor(&buf, tensor, ctx.GetPlace()));
is.read(static_cast<char*>(buf), size); // NOLINT
}
}
}
} // namespace phi
@@ -0,0 +1,42 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#pragma once
#include <algorithm>
#include <codecvt>
#include <locale>
#include <string>
#include <unordered_map>
#include <vector>
#include "paddle/phi/core/dense_tensor.h"
#include "paddle/phi/core/framework/var_type_helper.h"
#include "paddle/phi/core/memory/memory.h"
#include "paddle/phi/core/platform/device_context.h"
namespace phi {
TEST_API void TensorToStream(std::ostream& os,
const DenseTensor& tensor,
const DeviceContext& dev_ctx);
TEST_API void TensorFromStream(std::istream& is,
DenseTensor* tensor,
const DeviceContext& dev_ctx);
void TensorFromStream(std::istream& is,
DenseTensor* tensor,
const DeviceContext& dev_ctx,
const size_t& seek,
const std::vector<int64_t>& shape);
} // namespace phi
@@ -0,0 +1,54 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#pragma once
#include <vector>
#include "paddle/phi/core/extended_tensor.h"
#include "paddle/phi/core/tensor_array.h"
#include "paddle/phi/core/tensor_utils.h"
#include "paddle/phi/core/vocab/string_array.h"
namespace phi {
using FeedType = phi::DenseTensor;
using FetchType = paddle::variant<phi::DenseTensor,
phi::TensorArray,
phi::Vocab,
phi::SparseCooTensor>;
template <>
struct PhiVectorType<FeedType> {
const char *type_name = "PhiVectorFeedType";
};
template <>
struct PhiVectorType<FetchType> {
const char *type_name = "PhiVectorFetchType";
};
using FeedList = PhiVector<FeedType>;
using FetchList = PhiVector<FetchType>;
using FetchUnmergedList = std::vector<std::vector<FetchType>>;
} // namespace phi
namespace paddle {
namespace framework {
using FeedType = phi::FeedType;
using FetchType = phi::FetchType;
using FeedList = phi::FeedList;
using FetchList = phi::FetchList;
using FetchUnmergedList = phi::FetchUnmergedList;
} // namespace framework
} // namespace paddle
+273
View File
@@ -0,0 +1,273 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
syntax = "proto2";
package paddle.framework.proto;
// Any incompatible changes to ProgramDesc and its dependencies should
// raise the version defined version.h.
//
// Serialization and Deserialization codes should be modified in a way
// that supports old versions following the version and compatibility policy.
message Version { optional int64 version = 1 [ default = 0 ]; }
enum AttrType {
INT = 0;
FLOAT = 1;
STRING = 2;
INTS = 3;
FLOATS = 4;
STRINGS = 5;
BOOLEAN = 6;
BOOLEANS = 7;
BLOCK = 8;
LONG = 9;
BLOCKS = 10;
LONGS = 11;
FLOAT64S = 12;
VAR = 13;
VARS = 14;
FLOAT64 = 15;
SCALAR = 16;
SCALARS = 17;
}
message Complex {
required double r = 1;
required double i = 2;
};
message Scalar {
enum Type {
BOOLEAN = 1;
LONG = 2;
FLOAT64 = 3;
COMPLEX128 = 4;
}
required Type type = 1;
optional bool b = 2;
optional int64 i = 3;
optional double r = 4;
optional Complex c = 5;
};
// OpDesc describes an instance of a C++ framework::OperatorBase
// derived class type.
message OpDesc {
message Attr {
required string name = 1;
required AttrType type = 2;
optional int32 i = 3;
optional float f = 4;
optional string s = 5;
repeated int32 ints = 6;
repeated float floats = 7;
repeated string strings = 8;
optional bool b = 10;
repeated bool bools = 11;
optional int32 block_idx = 12;
optional int64 l = 13;
repeated int32 blocks_idx = 14;
repeated int64 longs = 15;
repeated double float64s = 16;
optional string var_name = 17;
repeated string vars_name = 18;
optional double float64 = 19;
optional Scalar scalar = 20;
repeated Scalar scalars = 21;
};
message Var {
required string parameter = 1;
repeated string arguments = 2;
};
required string type = 3;
repeated Var inputs = 1;
repeated Var outputs = 2;
repeated Attr attrs = 4;
optional bool is_target = 5 [ default = false ];
};
// OpProto describes a C++ framework::OperatorBase derived class.
message OpProto {
// VarProto describes the C++ type framework::Variable.
message Var {
required string name = 1;
required string comment = 2;
optional bool duplicable = 3 [ default = false ];
optional bool intermediate = 4 [ default = false ];
optional bool dispensable = 5 [ default = false ];
optional bool extra = 6 [ default = false ];
optional bool quant = 7 [ default = false ];
}
// AttrProto describes the C++ type Attribute.
message Attr {
required string name = 1;
required AttrType type = 2;
required string comment = 3;
// If that attribute is generated, it means the Paddle third
// language binding has responsibility to fill that
// attribute. End-User should not set that attribute.
optional bool generated = 4 [ default = false ];
optional bool extra = 5 [ default = false ];
optional bool quant = 6 [ default = false ];
optional bool support_tensor = 7 [ default = false];
}
required string type = 1;
repeated Var inputs = 2;
repeated Var outputs = 3;
repeated Attr attrs = 4;
required string comment = 5;
}
message VarType {
enum Type {
// Pod Types
BOOL = 0;
INT16 = 1;
INT32 = 2;
INT64 = 3;
FP16 = 4;
FP32 = 5;
FP64 = 6;
// phi::DenseTensor<size_t> is used in C++.
SIZE_T = 19;
UINT8 = 20;
INT8 = 21;
BF16 = 22;
COMPLEX64 = 23;
COMPLEX128 = 24;
FP8_E4M3FN = 32;
FP8_E5M2 = 33;
UINT16 = 36;
UINT32 = 37;
UINT64 = 38;
// Other types that may need additional descriptions
DENSE_TENSOR = 7;
SELECTED_ROWS = 8;
FEED_MINIBATCH = 9;
FETCH_LIST = 10;
STEP_SCOPES = 11;
LOD_RANK_TABLE = 12;
DENSE_TENSOR_ARRAY = 13;
PLACE_LIST = 14;
READER = 15;
// Any runtime decided variable type is raw
// raw variables should manage their own allocations
// in operators like nccl_op
RAW = 17;
TUPLE = 18;
STRING = 25;
STRINGS = 26;
VOCAB = 27;
FEED_LIST = 28;
// The data type of phi::StringTensor
PSTRING = 29;
// the data type of phi::SparseCooTensor
SPARSE_COO = 30;
// the data type of phi::SparseCsrTensor
SPARSE_CSR = 31;
}
required Type type = 1;
message TensorDesc {
// Should only be PODType. Is enforced in C++
required Type data_type = 1;
repeated int64 dims = 2; // [UNK, 640, 480] is saved as [-1, 640, 480]
}
optional TensorDesc selected_rows = 2;
message DenseTensorDesc {
required TensorDesc tensor = 1;
optional int32 legacy_lod_level = 2 [ default = 0 ];
}
optional DenseTensorDesc dense_tensor = 3;
message DenseTensorArrayDesc {
required TensorDesc tensor = 1;
optional int32 legacy_lod_level = 2 [ default = 0 ];
}
optional DenseTensorArrayDesc tensor_array = 4;
message ReaderDesc { repeated DenseTensorDesc dense_tensor = 1; }
optional ReaderDesc reader = 5;
message Tuple { repeated Type element_type = 1; }
optional Tuple tuple = 7;
optional TensorDesc string = 8;
optional TensorDesc strings = 9;
optional TensorDesc vocab = 10;
optional TensorDesc sparse_coo = 11;
optional TensorDesc sparse_csr = 12;
}
message VarDesc {
message Attr {
required string name = 1;
required AttrType type = 2;
optional int32 i = 3;
optional string s = 4;
repeated int32 ints = 5;
};
required string name = 1;
required VarType type = 2;
optional bool persistable = 3 [ default = false ];
// True if the variable is an input data and
// have to check the feed data shape and dtype
optional bool need_check_feed = 4 [ default = false ];
optional bool is_parameter = 5 [ default = false ];
optional bool stop_gradient = 6 [ default = false ];
repeated Attr attrs = 7;
}
message BlockDesc {
required int32 idx = 1;
required int32 parent_idx = 2;
repeated VarDesc vars = 3;
repeated OpDesc ops = 4;
optional int32 forward_block_idx = 5 [ default = -1 ];
}
// In some cases, Paddle may perform operator definition iterations,
// and the operator uses OpVersionMap for compatibility testing.
message OpVersion { required int32 version = 1; }
message OpVersionMap {
message OpVersionPair {
required string op_name = 1;
required OpVersion op_version = 2;
}
repeated OpVersionPair pair = 1;
}
// TODO(panyx0718): A model can have multiple programs. Need a
// way to distinguish them. Maybe ID or name?
message ProgramDesc {
reserved 2, 3; // For backward compatibility.
repeated BlockDesc blocks = 1;
optional Version version = 4;
optional OpVersionMap op_version_map = 5;
}
@@ -0,0 +1,70 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
syntax = "proto2";
package paddle.framework;
option cc_generic_services = true;
// It can be: phi::DenseTensor、SelectedRows or NCCL_ID
enum VarType {
DENSE_TENSOR = 0;
SELECTED_ROWS = 1;
NCCL_ID = 2;
}
// VariableMessage is serialized paddle variable message.
// NOTICE(gongwb):don't modify this proto if you are not
// not familiar with how we serialize in sendrecvop_utils.h
// and deserialize it in variable_response.h.
message VariableMessage {
enum Type {
// Pod Types
BOOL = 0;
INT16 = 1;
INT32 = 2;
INT64 = 3;
FP16 = 4;
FP32 = 5;
FP64 = 6;
}
message LodData { repeated int64 lod_data = 1; }
optional string varname = 1;
// TODO(Yancey1989): reference framework::proto::VarDesc::VarType
optional VarType type = 2;
// bool persistable is not needed for sending.
// tensor info:
optional Type data_type = 3;
repeated int64 dims = 4;
// lod details:
optional int64 lod_level = 5;
repeated LodData lod = 6;
// selected_rows height, aka. original dim0
optional int64 slr_height = 7;
// tensor data
optional bytes data = 8;
}
message HeterRequest {
required int32 cmd = 1;
optional int32 cur_batch = 2;
repeated VariableMessage vars = 3;
};
message HeterResponse {
// optional VariableMessage vars = 1;
repeated VariableMessage vars = 1;
};
service HeterService { rpc service(HeterRequest) returns (HeterResponse); };
+91
View File
@@ -0,0 +1,91 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
syntax = "proto2";
import "paddle/phi/core/framework/framework.proto";
package paddle.framework.proto;
// Describes one substitute subgraph.
message PassDesc {
enum RoleType {
kVariable = 0;
kOperator = 1;
}
enum OperationType {
kAdd = 0;
kSub = 1;
kMul = 2;
kDiv = 3;
kSize = 4;
kMod = 5;
}
enum ConditionType {
kEQ = 0;
kNE = 1;
kGT = 2;
kGE = 3;
kLT = 4;
kLE = 5;
}
// Representation of attr in var or operator.
message Attr {
required RoleType role = 1;
optional string var_name = 2;
optional int32 op_index = 3;
required string name = 4;
optional string element_name = 5;
optional int32 element_index = 6;
optional OperationType operation = 7;
}
// The operation to be performed.
message Operation {
required OperationType type = 1;
optional Attr attr = 2;
optional OpDesc.Attr value = 3;
}
message VarMap {
required string pattern_var = 1;
required string replace_var = 2;
}
message AttrMap {
required Attr pattern_attr = 1;
required Attr replace_attr = 2;
optional Operation operation = 3;
}
message AttrCondition {
required Attr attr = 1;
required ConditionType type = 2;
optional Attr condition_attr = 3;
optional OpDesc.Attr condition_value = 4;
optional Operation operation = 5;
}
// A pair of subgraphs for matching and rewriting.
repeated OpDesc pattern = 1;
repeated OpDesc replace = 2;
// Mapping vars between pattern and replace subgraphs.
repeated VarMap var_maps = 3;
// Mapping attrs of vars and ops between pattern and replace subgraphs.
repeated AttrMap var_attr_maps = 4;
repeated AttrMap op_attr_maps = 5;
// Limit the attrs of vars and ops in pattern subgraph.
repeated AttrCondition var_attr_conditions = 6;
repeated AttrCondition op_attr_conditions = 7;
}
// A series of PassDesc.
message MultiPassDesc {
optional string pass_type = 1;
repeated PassDesc pass_descs = 2;
}
+80
View File
@@ -0,0 +1,80 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#include "paddle/phi/core/framework/reader.h"
#include <deque>
#include "glog/logging.h"
namespace paddle::framework {
void ReaderBase::ReadNext(phi::TensorArray *out) {
std::lock_guard<std::mutex> lock(mu_);
PADDLE_ENFORCE_EQ(status_,
ReaderStatus::kRunning,
common::errors::Unavailable(
"The current reader has stopped running and cannot "
"continue to read the next batch of data."));
ReadNextImpl(out);
}
void ReaderBase::InsertDecoratedReader(
const std::shared_ptr<ReaderBase> &decorated_reader) {
std::lock_guard<std::mutex> guard(mu_);
decorated_readers_.emplace_back(decorated_reader);
}
std::unordered_set<ReaderBase *> ReaderBase::GetEndPoints() {
std::unordered_set<ReaderBase *> result;
std::deque<ReaderBase *> queue;
queue.emplace_back(this);
while (!queue.empty()) { // BFS search
auto *front = queue.front();
queue.pop_front();
if (front->decorated_readers_.empty()) {
result.emplace(front);
} else {
for (auto &reader : front->decorated_readers_) {
if (auto *reader_ptr = reader.lock().get()) {
queue.emplace_back(reader_ptr);
}
}
}
}
return result;
}
void ReaderBase::Shutdown() {
std::lock_guard<std::mutex> lock(mu_);
if (status_ != ReaderStatus::kStopped) {
ShutdownImpl();
status_ = ReaderStatus::kStopped;
}
}
void ReaderBase::Start() {
std::lock_guard<std::mutex> lock(mu_);
if (status_ != ReaderStatus::kRunning) {
StartImpl();
status_ = ReaderStatus::kRunning;
}
}
ReaderBase::~ReaderBase() = default;
DecoratedReader::~DecoratedReader() {
VLOG(1) << "~DecoratedReader";
reader_->Shutdown();
}
} // namespace paddle::framework
+224
View File
@@ -0,0 +1,224 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#pragma once
#include <memory>
#include <unordered_set>
#include <utility>
#include <vector>
#include "paddle/common/ddim.h"
#include "paddle/phi/common/place.h"
#include "paddle/phi/core/framework/framework.pb.h"
#include "paddle/phi/core/tensor_array.h"
namespace paddle {
namespace framework {
class ReaderBase {
public:
explicit ReaderBase(const std::vector<DDim>& shapes,
const std::vector<proto::VarType::Type>& var_types,
const std::vector<bool>& need_check_feed)
: shapes_(shapes),
var_types_(var_types),
need_check_feed_(need_check_feed) {
PADDLE_ENFORCE_EQ(
shapes_.size(),
need_check_feed_.size(),
common::errors::InvalidArgument(
"Construct ReaderBase with mismatched sizes of shapes "
"and need_check_feed"));
PADDLE_ENFORCE_EQ(
var_types_.size(),
need_check_feed_.size(),
common::errors::InvalidArgument(
"Construct ReaderBase with mismatched sizes of var_types "
"and need_check_feed"));
}
PADDLE_API virtual void ReadNext(phi::TensorArray* out);
PADDLE_API virtual void Shutdown();
PADDLE_API virtual void Start();
// Return the readers which are the end of decorating chain. Basically
// they are readers just before read op.
PADDLE_API std::unordered_set<ReaderBase*> GetEndPoints();
// Returns the shapes of the fed variables
const std::vector<DDim>& Shapes() const { return shapes_; }
// Returns the dtypes of the fed variables
const std::vector<proto::VarType::Type>& VarTypes() const {
return var_types_;
}
// For Backward compatibility, old fluid.layers.data doesn't check shape.
// This function returns whether you have the check shape for this Reader.
const std::vector<bool>& NeedCheckFeed() const { return need_check_feed_; }
PADDLE_API virtual ~ReaderBase();
protected:
virtual void ReadNextImpl(phi::TensorArray* out UNUSED) {}
virtual void ShutdownImpl() {}
virtual void StartImpl() {}
enum ReaderStatus { kRunning, kStopped };
ReaderStatus status_{kRunning};
mutable std::mutex mu_;
// The shapes of the fed variables.
std::vector<DDim> shapes_;
// The dtypes of the fed variables.
std::vector<proto::VarType::Type> var_types_;
// Whether to check the shape and dtype of fed variables.
std::vector<bool> need_check_feed_;
private:
friend class DecoratedReader;
// These methods can be only invoked inside DecoratedReader to record the
// decorating chain.
PADDLE_API void InsertDecoratedReader(
const std::shared_ptr<ReaderBase>& decorated_reader);
// A set of which readers that decorated this reader.
std::vector<std::weak_ptr<ReaderBase>> decorated_readers_;
};
class DecoratedReader : public ReaderBase,
public std::enable_shared_from_this<DecoratedReader> {
public:
explicit DecoratedReader(const std::shared_ptr<ReaderBase>& reader)
: ReaderBase(
reader->Shapes(), reader->VarTypes(), reader->NeedCheckFeed()),
reader_(reader) {
PADDLE_ENFORCE_NOT_NULL(
reader_,
common::errors::InvalidArgument(
"The underlying reader of DecoratedReader should not be null"));
}
void RegisterDecorateChain() {
reader_->InsertDecoratedReader(shared_from_this());
}
PADDLE_API ~DecoratedReader();
const std::shared_ptr<ReaderBase>& UnderlyingReader() const {
return reader_;
}
protected:
void ShutdownImpl() override { reader_->Shutdown(); }
void StartImpl() override { reader_->Start(); }
std::shared_ptr<ReaderBase> reader_;
};
// FileReader is just a conceptual class.
class FileReader : public ReaderBase {
public:
explicit FileReader(const std::vector<DDim>& shapes,
const std::vector<proto::VarType::Type>& var_types,
const std::vector<bool>& need_check_feed)
: ReaderBase(shapes, var_types, need_check_feed) {}
};
// The ReaderHolder is used as reader' unified wrapper,
// making it easier to access different type reader in Variables.
class ReaderHolder {
public:
template <typename T>
void Reset(const std::shared_ptr<T>& reader) {
auto reader_base = std::dynamic_pointer_cast<ReaderBase>(reader);
PADDLE_ENFORCE_NOT_NULL(
reader_base,
common::errors::InvalidArgument(
"The underlying reader of ReaderHolder should not be null"));
reader_ = reader_base;
}
~ReaderHolder() {}
const std::shared_ptr<ReaderBase>& Get() const { return reader_; }
void ReadNext(phi::TensorArray* out) {
PADDLE_ENFORCE_NOT_NULL(
reader_,
common::errors::InvalidArgument(
"The underlying reader of ReaderHolder should not be null"));
reader_->ReadNext(out);
}
void ResetAll() {
auto end_readers = reader_->GetEndPoints();
for (auto* reader : end_readers) {
reader->Shutdown();
}
for (auto* reader : end_readers) {
reader->Start();
}
}
void Shutdown() {
PADDLE_ENFORCE_NOT_NULL(
reader_,
common::errors::InvalidArgument(
"The underlying reader of ReaderHolder should not be null"));
reader_->Shutdown();
}
void Start() {
PADDLE_ENFORCE_NOT_NULL(
reader_,
common::errors::InvalidArgument(
"The underlying reader of ReaderHolder should not be null"));
reader_->Start();
}
const std::vector<DDim>& Shapes() const { return reader_->Shapes(); }
const std::vector<proto::VarType::Type>& VarTypes() const {
return reader_->VarTypes();
}
const std::vector<bool>& NeedCheckFeed() const {
return reader_->NeedCheckFeed();
}
void Clear() { reader_.reset(); }
operator const std::shared_ptr<ReaderBase>&() const { return this->reader_; }
private:
std::shared_ptr<ReaderBase> reader_;
};
template <typename T, typename... ARGS>
inline std::shared_ptr<DecoratedReader> MakeDecoratedReader(ARGS&&... args) {
std::shared_ptr<DecoratedReader> reader(new T(std::forward<ARGS>(args)...));
reader->RegisterDecorateChain();
return reader;
}
} // namespace framework
} // namespace paddle
@@ -0,0 +1,95 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#include "paddle/phi/core/framework/selected_rows_serialize.h"
namespace phi {
void SerializeToStream(std::ostream& os,
const SelectedRows& selected_rows,
const DeviceContext& dev_ctx) {
{ // the 1st field, uint32_t version
constexpr uint32_t version = 0;
os.write(reinterpret_cast<const char*>(&version), sizeof(version));
}
{
// the 2nd field, rows information
auto& rows = selected_rows.rows();
uint64_t size = rows.size();
os.write(reinterpret_cast<const char*>(&size), sizeof(size));
for (uint64_t i = 0; i < size; ++i) {
os.write(reinterpret_cast<const char*>(&rows[i]), sizeof(rows[i]));
}
}
{
// the 3rd field, the height of SelectedRows
int64_t height = selected_rows.height();
os.write(reinterpret_cast<const char*>(&height), sizeof(height));
}
// the 4st field, Tensor data
TensorToStream(os, selected_rows.value(), dev_ctx);
}
void SerializeToStream(std::ostream& os, const SelectedRows& selected_rows) {
DeviceContextPool& pool = DeviceContextPool::Instance();
const DeviceContext* dev_ctx = nullptr;
auto place = selected_rows.place();
dev_ctx = pool.Get(place);
SerializeToStream(os, selected_rows, *dev_ctx);
}
void DeserializeFromStream(std::istream& is, SelectedRows* selected_rows) {
DeviceContextPool& pool = DeviceContextPool::Instance();
const DeviceContext* dev_ctx = nullptr;
dev_ctx = pool.Get(CPUPlace());
DeserializeFromStream(is, selected_rows, *dev_ctx);
}
void DeserializeFromStream(std::istream& is,
SelectedRows* selected_rows,
const DeviceContext& dev_ctx) {
{
// the 1st field, unit32_t version for SelectedRows
uint32_t version = 0;
is.read(reinterpret_cast<char*>(&version), sizeof(version));
PADDLE_ENFORCE_EQ(version,
0U,
common::errors::InvalidArgument(
"Only version 0 SelectedRows is supported."));
}
{
// the 2nd field, rows information
uint64_t size = 0;
is.read(reinterpret_cast<char*>(&size), sizeof(size));
PADDLE_ENFORCE_EQ(
is.good(),
true,
common::errors::Unavailable("Cannot read the number of rows."));
auto& rows = *selected_rows->mutable_rows();
rows.resize(size);
for (uint64_t i = 0; i < size; ++i) {
is.read(reinterpret_cast<char*>(&rows[i]), sizeof(int64_t));
}
}
{
// the 3rd field, the height of the SelectedRows
int64_t height = 0;
is.read(reinterpret_cast<char*>(&height), sizeof(int64_t));
selected_rows->set_height(height);
}
// the 4st field, tensor which contains the data
TensorFromStream(is, selected_rows->mutable_value(), dev_ctx);
}
} // namespace phi
@@ -0,0 +1,47 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#pragma once
#include <algorithm>
#include <memory>
#include <mutex> // NOLINT
#include <unordered_map>
#include <utility>
#include <vector>
#include "paddle/phi/core/framework/dense_tensor_tostream.h"
#include "paddle/phi/core/platform/device_context.h"
#include "paddle/phi/core/selected_rows.h"
namespace phi {
/*
* Serialize/Deserialize SelectedRows to std::ostream
* You can pass ofstream or ostringstream to serialize to file
* or to a in memory string. GPU tensor will be copied to CPU.
*/
PADDLE_API void SerializeToStream(std::ostream& os,
const SelectedRows& selected_rows,
const DeviceContext& dev_ctx);
PADDLE_API void DeserializeFromStream(std::istream& is,
SelectedRows* selected_rows,
const DeviceContext& dev_ctx);
PADDLE_API void SerializeToStream(std::ostream& os,
const SelectedRows& selected_rows);
PADDLE_API void DeserializeFromStream(std::istream& is,
SelectedRows* selected_rows);
} // namespace phi
@@ -0,0 +1,220 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
syntax = "proto2";
option optimize_for = LITE_RUNTIME;
import "paddle/phi/core/framework/data_feed.proto";
import "paddle/phi/core/framework/framework.proto";
package paddle.framework;
message TrainerDesc {
// class name for create trainer desc
// the matchness of trainer name and device worker name
// will be checked in python API
optional string class_name = 1;
// class name for creating device worker
optional string device_worker_name = 2;
// thread number
optional int32 thread_num = 3;
// if we need to binding cpu
optional bool binding_cpu = 4 [ default = false ];
repeated string filelist = 5;
optional bool debug = 6 [ default = false ];
optional FetchConfig fetch_config = 7;
optional bool use_cvm = 8 [ default = false ];
optional bool dump_slot = 9 [ default = false ];
optional float scale_datanorm = 10 [ default = -1 ];
optional int32 mpi_rank = 11 [ default = -1 ];
optional string dump_fields_path = 12;
repeated string dump_fields = 13;
optional string dump_converter = 14;
repeated string dump_param = 15;
optional int32 mpi_size = 16 [ default = -1 ];
optional int32 dump_file_num = 17 [ default = 16 ];
repeated string check_nan_var_names = 18;
optional CopyTableConfig copy_table_config = 19;
// adjust ins weight
optional AdjustInsWeightConfig adjust_ins_weight_config = 20;
optional bool no_cvm = 21 [ default = false ];
optional bool thread_barrier = 22;
repeated string loss_names = 23;
optional bool enable_random_dump = 24 [ default = false ];
optional bool random_with_lineid = 25 [ default = false ];
optional int32 dump_interval = 26 [ default = 10000 ];
repeated int32 worker_places = 27;
repeated string xpu_send_list = 28;
repeated string xpu_recv_list = 29;
optional int32 xpu_start_idx = 30;
optional int32 xpu_end_idx = 31;
optional bool use_ps_gpu = 32 [ default = false ];
optional string user_define_dump_filename = 33;
optional bool scale_sparse_gradient_with_batch_size = 34 [ default = true ];
repeated int32 trainers = 35;
optional int32 trainer_id = 36;
// add for gpu
optional string fleet_desc = 37;
optional bool is_dump_in_simple_mode = 38 [ default = false ];
optional string dump_fields_mode = 39 [ default = "w" ];
optional int32 dump_num_decimals = 40 [ default = 9 ];
optional bool use_gpu_graph = 41 [ default = false ];
// device worker parameters
optional HogwildWorkerParameter hogwild_param = 101;
optional DownpourWorkerParameter downpour_param = 103;
optional PullDenseWorkerParameter pull_dense_param = 102;
optional SectionWorkerParameter section_param = 104;
optional HeterSectionWorkerParameter heter_section_param = 105;
// datafeed desc
optional DataFeedDesc data_desc = 201;
}
message HogwildWorkerParameter {
repeated string skip_ops = 1;
repeated string stat_var_names = 2;
}
message DownpourWorkerParameter {
repeated TableParameter sparse_table = 1;
repeated TableParameter dense_table = 2;
repeated string skip_ops = 3;
repeated ProgramConfig program_config = 4;
optional bool push_sparse = 5 [ default = true ];
optional bool push_dense = 6 [ default = true ];
repeated string stat_var_names = 7;
}
message SectionWorkerParameter {
optional SectionConfig section_config = 1;
optional int32 queue_size = 2 [ default = 1 ];
optional int64 sync_steps = 3 [ default = 1 ];
optional int32 start_cpu_core_id = 4 [ default = 1 ];
repeated string param_need_sync = 5;
optional int32 num_microbatches = 6;
optional int32 num_pipeline_stages = 7 [ default = 1 ];
optional int32 pipeline_stage = 8 [ default = 1 ];
optional int32 schedule_mode = 9 [ default = 0 ];
}
message HeterSectionWorkerParameter {
optional SectionConfig section_config = 1;
optional int32 queue_size = 2 [ default = 1 ];
optional int64 sync_steps = 3 [ default = 1 ];
optional int32 start_cpu_core_id = 4 [ default = 1 ];
repeated string param_need_sync = 5;
optional int32 num_microbatches = 6;
optional int32 num_pipeline_stages = 7 [ default = 1 ];
optional int32 pipeline_stage = 8 [ default = 1 ];
}
message SectionConfig {
enum Place {
CPUPlace = 0;
CUDAPlace = 1;
CUDAPinnedPlace = 2;
}
// FIXME: How to use proto::ProgramDesc
// required string program_desc_str = 1;
optional proto.ProgramDesc program_desc = 1;
optional Place place = 2;
optional int32 concurrency = 3 [ default = 1 ];
repeated string section_in_var_names = 4;
repeated string section_out_var_names = 5;
optional int32 place_id = 6 [ default = -1 ];
}
message FetchConfig {
enum Method { PRINT = 0; }
repeated string fetch_var_names = 1;
repeated string fetch_var_str_format = 2;
optional int32 print_period = 3 [ default = 100 ];
optional Method method = 4 [ default = PRINT ];
}
message AdjustInsWeightConfig {
optional bool need_adjust = 1 [ default = false ];
optional string nid_slot = 2 [ default = "" ];
optional float nid_adjw_threshold = 3 [ default = 0.0 ];
optional float nid_adjw_ratio = 4 [ default = 0.0 ];
optional string ins_weight_slot = 5 [ default = "" ];
}
message TableDependencyMap {
required int32 key = 1;
repeated int32 values = 2;
}
message CopyTableConfig {
optional bool need_copy = 1 [ default = false ];
optional int32 batch_num = 2 [ default = 100 ];
repeated int32 src_sparse_tables = 3;
repeated int32 dest_sparse_tables = 4;
repeated int32 src_dense_tables = 5;
repeated int32 dest_dense_tables = 6;
repeated string src_var_list = 7;
repeated string dest_var_list = 8;
// when dest dense table has no grad, should pull explicitly
optional bool dense_pull_after_copy = 9 [ default = false ];
// copy feasigns or copy the whole table
optional bool sparse_copy_by_feasign = 10 [ default = true ];
// table dependency for pull/push
optional bool enable_dependency = 11 [ default = false ];
repeated TableDependencyMap table_dependency_map = 12;
}
message CondTableMap {
required int32 key = 1;
required int32 value = 2;
}
message ProgramConfig {
required string program_id = 1;
repeated int32 push_sparse_table_id = 2;
repeated int32 push_dense_table_id = 3;
repeated int32 pull_sparse_table_id = 4;
repeated int32 pull_dense_table_id = 5;
repeated CondTableMap partial_pushdense_condtable_map = 10;
}
message PullDenseWorkerParameter {
// dense table only and specialized usage
optional int32 threshold = 1 [ default = 1 ];
optional int32 device_num = 2;
optional int32 sleep_time_ms = 3 [ default = 2 ];
repeated TableParameter dense_table = 4;
}
message TableParameter {
// dense table only
optional uint64 table_id = 1;
repeated string dense_value_name = 2;
repeated string dense_grad_name = 3;
repeated int32 push_dense_wait_times = 5;
// sparse table only
repeated string sparse_key_name = 6;
repeated string sparse_value_name = 7;
repeated string sparse_grad_name = 8;
repeated int32 push_sparse_wait_times = 9;
// sparse table only and specialized usage
optional int32 emb_dim = 10;
optional int32 fea_dim = 11;
optional string label_var_name = 12;
// if table will pull sparse to local first
optional bool is_local = 13 [ default = false ];
// if table will pull sparse asynchronously in worker
optional bool is_async = 14 [ default = false ];
optional string async_wait_op_name = 15;
}
@@ -0,0 +1,154 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#include "paddle/phi/core/framework/var_type_helper.h"
#include "paddle/phi/common/pstring.h"
namespace phi {
struct DataTypeMap {
std::unordered_map<std::type_index, VarType::Type> cpp_to_proto_;
std::unordered_map<int, std::type_index> proto_to_cpp_;
std::unordered_map<int, std::string> proto_to_str_;
std::unordered_map<int, size_t> proto_to_size_;
};
static DataTypeMap* InitDataTypeMap();
// C++11 removes the need for manual locking. Concurrent execution shall wait if
// a static local variable is already being initialized.
// https://stackoverflow.com/questions/11711920/how-to-implement-multithread-safe-singleton-in-c11-without-using-mutex
static DataTypeMap& gDataTypeMap() {
static DataTypeMap* g_data_type_map_ = InitDataTypeMap();
return *g_data_type_map_;
}
template <typename T>
static inline void RegisterType(DataTypeMap* map,
VarType::Type proto_type,
const std::string& name) {
map->proto_to_cpp_.emplace(static_cast<int>(proto_type), typeid(T));
map->cpp_to_proto_.emplace(typeid(T), proto_type);
map->proto_to_str_.emplace(static_cast<int>(proto_type), name);
map->proto_to_size_.emplace(static_cast<int>(proto_type), sizeof(T));
}
static DataTypeMap* InitDataTypeMap() {
auto retv = new DataTypeMap();
#define RegType(cc_type, proto_type) \
RegisterType<cc_type>(retv, proto_type, #cc_type)
_ForEachDataType_(RegType);
// Register pstring individually
RegType(pstring, VarType::PSTRING);
RegType(::phi::dtype::float8_e5m2, VarType::FP8_E5M2);
RegType(::phi::dtype::float8_e4m3fn, VarType::FP8_E4M3FN);
#undef RegType
return retv;
}
VarType::Type ToDataType(std::type_index type) {
auto it = gDataTypeMap().cpp_to_proto_.find(type);
if (it != gDataTypeMap().cpp_to_proto_.end()) {
return it->second;
}
PADDLE_THROW(common::errors::Unimplemented(
"Not support %s as tensor data type.", common::demangle(type.name())));
}
std::type_index ToTypeIndex(VarType::Type type) {
auto it = gDataTypeMap().proto_to_cpp_.find(static_cast<int>(type));
if (it != gDataTypeMap().proto_to_cpp_.end()) {
return it->second;
}
PADDLE_THROW(common::errors::Unimplemented(
"Not support VarType::Type(%d) as tensor type.", static_cast<int>(type)));
}
std::string VarDataTypeToString(const VarType::Type type) {
auto it = gDataTypeMap().proto_to_str_.find(static_cast<int>(type));
if (it != gDataTypeMap().proto_to_str_.end()) {
return it->second;
}
// deal with RAW type
if (type == VarType::RAW) {
return "RAW(runtime decided type)";
}
PADDLE_THROW(common::errors::Unimplemented(
"Not support VarType::Type(%d) as tensor type.", static_cast<int>(type)));
}
size_t SizeOfType(VarType::Type type) {
auto it = gDataTypeMap().proto_to_size_.find(static_cast<int>(type));
if (it != gDataTypeMap().proto_to_size_.end()) {
return it->second;
}
PADDLE_THROW(common::errors::Unimplemented("Not support %s as tensor type.",
VarDataTypeToString(type)));
}
// Now only supports promotion of complex type
inline bool NeedPromoteTypes(const VarType::Type& a, const VarType::Type& b) {
return (IsComplexType(a) || IsComplexType(b));
}
int DataTypeNumAlign(const VarType::Type t) {
int cast_type_num = -1;
if (t == VarType::FP32 || t == VarType::FP64) {
cast_type_num = static_cast<int>(t) - 5;
} else if (t == VarType::COMPLEX64 || t == VarType::COMPLEX128) {
cast_type_num = static_cast<int>(t) - 21;
} else {
PADDLE_THROW(common::errors::Unavailable(
"Only supports to align data type include float32, float64, complex64 "
"and complex128, but received data type is %s.",
VarDataTypeToString(t)));
}
return cast_type_num;
}
// Now only supports promotion of complex type
VarType::Type PromoteTypesIfComplexExists(const VarType::Type type_a,
const VarType::Type type_b) {
constexpr auto f4 = VarType::FP32; // 5
constexpr auto f8 = VarType::FP64; // 6
constexpr auto c4 = VarType::COMPLEX64; // 23
constexpr auto c8 = VarType::COMPLEX128; // 24
if (!NeedPromoteTypes(type_a, type_b)) {
// NOTE(chenweihang): keep consistent with rule in original op's impl,
// kernel type based on the first input tensor's dtype
return type_a;
}
int type_an = DataTypeNumAlign(type_a);
int type_bn = DataTypeNumAlign(type_b);
// Here is a complete rules table, but some rules are not used.
// It is still written this way because array accessing is still
// more efficient than if-else
// NOLINTBEGIN(*-avoid-c-arrays)
static constexpr VarType::Type promote_types_table[4][4] = {
/* f4 f8 c4 c8*/
/* f4 */ {f4, f8, c4, c8},
/* f8 */ {f8, f8, c8, c8},
/* c4 */ {c4, c8, c4, c8},
/* c8 */ {c8, c8, c8, c8},
};
// NOLINTEND(*-avoid-c-arrays)
return promote_types_table[type_an][type_bn];
}
} // namespace phi
+275
View File
@@ -0,0 +1,275 @@
// Copyright (c) 2024 PaddlePaddle Authors. All Rights Reserved.
//
// Licensed 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.
#pragma once
#include <iostream>
#include <string>
#include <typeindex>
#include "paddle/phi/common/data_type.h"
#include "paddle/phi/core/enforce.h"
#include "paddle/phi/core/framework/framework.pb.h"
namespace phi {
using VarType = paddle::framework::proto::VarType;
PADDLE_API std::string VarDataTypeToString(const VarType::Type type);
TEST_API extern size_t SizeOfType(VarType::Type type);
template <typename T>
struct IsComplex : public std::false_type {};
template <typename T>
struct IsComplex<phi::dtype::complex<T>> : public std::true_type {};
template <typename T>
struct DataTypeTrait {};
// Stub handle for void
template <>
struct DataTypeTrait<void> {
constexpr static VarType::Type DataType() { return VarType::RAW; }
};
#define _ForEachDataTypeHelper_(callback, cpp_type, proto_type) \
callback(cpp_type, ::paddle::framework::proto::VarType::proto_type);
#define _ForEachDataType_(callback) \
_ForEachDataTypeHelper_(callback, float, FP32); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::float16, FP16); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::bfloat16, BF16); \
_ForEachDataTypeHelper_(callback, double, FP64); \
_ForEachDataTypeHelper_(callback, int, INT32); \
_ForEachDataTypeHelper_(callback, int64_t, INT64); \
_ForEachDataTypeHelper_(callback, bool, BOOL); \
_ForEachDataTypeHelper_(callback, uint8_t, UINT8); \
_ForEachDataTypeHelper_(callback, uint16_t, UINT16); \
_ForEachDataTypeHelper_(callback, uint32_t, UINT32); \
_ForEachDataTypeHelper_(callback, uint64_t, UINT64); \
_ForEachDataTypeHelper_(callback, int16_t, INT16); \
_ForEachDataTypeHelper_(callback, int8_t, INT8); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::complex<float>, COMPLEX64); \
_ForEachDataTypeHelper_( \
callback, ::phi::dtype::complex<double>, COMPLEX128); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::float8_e4m3fn, FP8_E4M3FN); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::float8_e5m2, FP8_E5M2);
#define _ForEachIntDataType_(callback) \
_ForEachDataTypeHelper_(callback, int, INT32); \
_ForEachDataTypeHelper_(callback, int64_t, INT64); \
_ForEachDataTypeHelper_(callback, uint8_t, UINT8); \
_ForEachDataTypeHelper_(callback, uint16_t, UINT16); \
_ForEachDataTypeHelper_(callback, uint32_t, UINT32); \
_ForEachDataTypeHelper_(callback, uint64_t, UINT64); \
_ForEachDataTypeHelper_(callback, int16_t, INT16); \
_ForEachDataTypeHelper_(callback, int8_t, INT8);
#define _ForEachDataTypeSmall_(callback) \
_ForEachDataTypeHelper_(callback, float, FP32); \
_ForEachDataTypeHelper_(callback, double, FP64); \
_ForEachDataTypeHelper_(callback, int, INT32); \
_ForEachDataTypeHelper_(callback, int64_t, INT64); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::complex<float>, COMPLEX64); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::complex<double>, COMPLEX128);
#define _ForEachDataTypeNormal_(callback) \
_ForEachDataTypeHelper_(callback, float, FP32); \
_ForEachDataTypeHelper_(callback, double, FP64); \
_ForEachDataTypeHelper_(callback, int, INT32); \
_ForEachDataTypeHelper_(callback, int64_t, INT64); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::float16, FP16); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::bfloat16, BF16);
// For the use of thrust, as index-type elements can be only integers.
#define _ForEachDataTypeTiny_(callback) \
_ForEachDataTypeHelper_(callback, int, INT32); \
_ForEachDataTypeHelper_(callback, int64_t, INT64);
// It's only for DataParallel in HIP, bf16 not support in HIP.
#define _ForEachDataTypeForHIP_(callback) \
_ForEachDataTypeHelper_(callback, float, FP32); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::float16, FP16); \
_ForEachDataTypeHelper_(callback, double, FP64); \
_ForEachDataTypeHelper_(callback, int, INT32); \
_ForEachDataTypeHelper_(callback, int64_t, INT64); \
_ForEachDataTypeHelper_(callback, bool, BOOL); \
_ForEachDataTypeHelper_(callback, uint8_t, UINT8); \
_ForEachDataTypeHelper_(callback, uint16_t, UINT16); \
_ForEachDataTypeHelper_(callback, uint32_t, UINT32); \
_ForEachDataTypeHelper_(callback, uint64_t, UINT64); \
_ForEachDataTypeHelper_(callback, int16_t, INT16); \
_ForEachDataTypeHelper_(callback, int8_t, INT8); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::complex<float>, COMPLEX64); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::complex<double>, COMPLEX128);
// complex and float8 are not supported on XPU.
#define _ForEachDataTypeForXPU_(callback) \
_ForEachDataTypeHelper_(callback, float, FP32); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::float16, FP16); \
_ForEachDataTypeHelper_(callback, ::phi::dtype::bfloat16, BF16); \
_ForEachDataTypeHelper_(callback, double, FP64); \
_ForEachDataTypeHelper_(callback, int, INT32); \
_ForEachDataTypeHelper_(callback, int64_t, INT64); \
_ForEachDataTypeHelper_(callback, bool, BOOL); \
_ForEachDataTypeHelper_(callback, uint8_t, UINT8); \
_ForEachDataTypeHelper_(callback, int16_t, INT16); \
_ForEachDataTypeHelper_(callback, int8_t, INT8);
#define DefineDataTypeTrait(cpp_type, proto_type) \
template <> \
struct DataTypeTrait<cpp_type> { \
constexpr static paddle::framework::proto::VarType::Type DataType() { \
return proto_type; \
} \
}
_ForEachDataType_(DefineDataTypeTrait);
#undef DefineDataTypeTrait
TEST_API extern VarType::Type ToDataType(std::type_index type);
extern std::type_index ToTypeIndex(VarType::Type type);
template <typename Visitor>
inline void VisitDataType(VarType::Type type, Visitor visitor) {
#define VisitDataTypeCallback(cpp_type, proto_type) \
do { \
if (type == proto_type) { \
visitor.template apply<cpp_type>(); \
return; \
} \
} while (0)
_ForEachDataType_(VisitDataTypeCallback);
#undef VisitDataTypeCallback
PADDLE_THROW(common::errors::Unimplemented(
"Not supported paddle::framework::proto::VarType::Type(%d) as data type.",
static_cast<int>(type)));
}
template <typename Visitor>
inline void VisitDataTypeSmall(VarType::Type type, Visitor visitor) {
#define VisitDataTypeCallbackSmall(cpp_type, proto_type) \
do { \
if (type == proto_type) { \
visitor.template apply<cpp_type>(); \
return; \
} \
} while (0)
_ForEachDataTypeSmall_(VisitDataTypeCallbackSmall);
#undef VisitDataTypeCallbackSmall
}
// for normal dtype, int, int64, float, float64, float16
template <typename Visitor>
inline void VisitDataTypeNormal(VarType::Type type, Visitor visitor) {
#define VisitDataTypeCallbackNormal(cpp_type, proto_type) \
do { \
if (type == proto_type) { \
visitor.template apply<cpp_type>(); \
return; \
} \
} while (0)
_ForEachDataTypeNormal_(VisitDataTypeCallbackNormal);
#undef VisitDataTypeCallbackNormal
}
template <typename Visitor>
inline void VisitIntDataType(VarType::Type type, Visitor visitor) {
#define VisitIntDataTypeCallback(cpp_type, proto_type) \
do { \
if (type == proto_type) { \
visitor.template apply<cpp_type>(); \
return; \
} \
} while (0)
_ForEachIntDataType_(VisitIntDataTypeCallback);
PADDLE_THROW(common::errors::Unimplemented(
"Expected integral data type, but got %s", VarDataTypeToString(type)));
#undef VisitIntDataTypeCallback
}
template <typename Visitor>
inline void VisitDataTypeTiny(VarType::Type type, Visitor visitor) {
#define VisitDataTypeCallbackTiny(cpp_type, proto_type) \
do { \
if (type == proto_type) { \
visitor.template apply<cpp_type>(); \
return; \
} \
} while (0)
_ForEachDataTypeTiny_(VisitDataTypeCallbackTiny);
#undef VisitDataTypeCallbackTiny
}
template <typename Visitor>
inline void VisitDataTypeForHIP(VarType::Type type, Visitor visitor) {
#define VisitDataTypeCallbackHIP(cpp_type, proto_type) \
do { \
if (type == proto_type) { \
visitor.template apply<cpp_type>(); \
return; \
} \
} while (0)
_ForEachDataTypeForHIP_(VisitDataTypeCallbackHIP);
#undef VisitDataTypeCallbackHIP
}
inline std::ostream& operator<<(std::ostream& out, const VarType::Type& type) {
out << VarDataTypeToString(type);
return out;
}
extern inline bool IsComplexType(const VarType::Type& type) {
return (type == VarType::COMPLEX64 || type == VarType::COMPLEX128);
}
extern VarType::Type PromoteTypesIfComplexExists(const VarType::Type type_a,
const VarType::Type type_b);
extern inline VarType::Type ToComplexType(VarType::Type t) {
switch (t) {
case VarType::FP32:
return VarType::COMPLEX64;
case VarType::FP64:
return VarType::COMPLEX128;
default:
PADDLE_THROW(common::errors::Unimplemented(
"Unknown real value data type (%s), now only support float32 and "
"float64.",
VarDataTypeToString(t)));
}
}
extern inline VarType::Type ToRealType(VarType::Type t) {
switch (t) {
case VarType::COMPLEX64:
return VarType::FP32;
case VarType::COMPLEX128:
return VarType::FP64;
default:
PADDLE_THROW(common::errors::Unimplemented(
"Unknown complex value data type (%s), now only support complex64 "
"and complex128.",
VarDataTypeToString(t)));
}
}
} // namespace phi