meta_tensor.cc 7.6 KB
Newer Older
1
/* Copyright (c) 2022 PaddlePaddle Authors. All Rights Reserved.
2 3 4 5 6 7 8 9 10 11 12 13 14

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. */

15
#include "paddle/phi/core/meta_tensor.h"
16

17 18
#include "glog/logging.h"

19 20 21
#include "paddle/phi/core/dense_tensor.h"
#include "paddle/phi/core/enforce.h"
#include "paddle/phi/core/selected_rows.h"
J
Jack Zhou 已提交
22 23
#include "paddle/phi/core/string_tensor.h"
#include "paddle/phi/core/string_tensor_utils.h"
24
#include "paddle/phi/core/tensor_utils.h"
25

26
namespace phi {
27

28 29 30 31 32 33
static inline void ValidCheck(const MetaTensor& meta_tensor) {
  PADDLE_ENFORCE_EQ(meta_tensor.initialized(),
                    true,
                    phi::errors::InvalidArgument(
                        "The current MetaTensor is not initialized."));
}
34

35 36 37 38
int64_t MetaTensor::numel() const {
  ValidCheck(*this);
  return tensor_->numel();
}
39

40 41 42 43
DDim MetaTensor::dims() const {
  ValidCheck(*this);
  return tensor_->dims();
}
44

45 46 47 48 49 50 51 52 53
DataType MetaTensor::dtype() const {
  ValidCheck(*this);
  return tensor_->dtype();
}

DataLayout MetaTensor::layout() const {
  ValidCheck(*this);
  return tensor_->layout();
}
54 55

void MetaTensor::set_dims(const DDim& dims) {
56
  ValidCheck(*this);
57
  if (phi::DenseTensor::classof(tensor_)) {
58 59
    DenseTensorUtils::GetMutableMeta(static_cast<DenseTensor*>(tensor_))->dims =
        dims;
J
Jack Zhou 已提交
60 61 62
  } else if (phi::StringTensor::classof(tensor_)) {
    StringTensorUtils::GetMutableMeta(static_cast<StringTensor*>(tensor_))
        ->dims = dims;
63
  } else if (phi::SelectedRows::classof(tensor_)) {
64 65 66
    DenseTensorUtils::GetMutableMeta(
        static_cast<SelectedRows*>(tensor_)->mutable_value())
        ->dims = dims;
67 68 69 70 71 72
  } else if (phi::SparseCooTensor::classof(tensor_)) {
    DenseTensorUtils::GetMutableMeta(static_cast<SparseCooTensor*>(tensor_))
        ->dims = dims;
  } else if (phi::SparseCsrTensor::classof(tensor_)) {
    DenseTensorUtils::GetMutableMeta(static_cast<SparseCsrTensor*>(tensor_))
        ->dims = dims;
73
  } else {
74
    PADDLE_THROW(phi::errors::Unimplemented(
75 76 77 78 79
        "Unsupported setting dims for `%s`.", tensor_->type_info().name()));
  }
}

void MetaTensor::set_dtype(DataType dtype) {
80
  ValidCheck(*this);
81
  if (phi::DenseTensor::classof(tensor_)) {
82
    DenseTensorUtils::GetMutableMeta(static_cast<DenseTensor*>(tensor_))
83
        ->dtype = dtype;
J
Jack Zhou 已提交
84 85
  } else if (phi::StringTensor::classof(tensor_)) {
    // No need to set dtype
86
  } else if (phi::SelectedRows::classof(tensor_)) {
87 88 89
    DenseTensorUtils::GetMutableMeta(
        static_cast<SelectedRows*>(tensor_)->mutable_value())
        ->dtype = dtype;
90 91 92 93 94 95 96
  } else if (phi::SparseCooTensor::classof(tensor_)) {
    DenseTensorUtils::GetMutableMeta(static_cast<SparseCooTensor*>(tensor_))
        ->dtype = dtype;
  } else if (phi::SparseCsrTensor::classof(tensor_)) {
    DenseTensorUtils::GetMutableMeta(static_cast<SparseCsrTensor*>(tensor_))
        ->dtype = dtype;
    // No need to set dtype
97
  } else {
98
    PADDLE_THROW(phi::errors::Unimplemented(
99 100 101 102 103
        "Unsupported settting dtype for `%s`.", tensor_->type_info().name()));
  }
}

void MetaTensor::set_layout(DataLayout layout) {
104
  ValidCheck(*this);
105
  if (phi::DenseTensor::classof(tensor_)) {
106
    DenseTensorUtils::GetMutableMeta(static_cast<DenseTensor*>(tensor_))
107
        ->layout = layout;
J
Jack Zhou 已提交
108 109
  } else if (phi::StringTensor::classof(tensor_)) {
    // No need to set layout
110
  } else if (phi::SelectedRows::classof(tensor_)) {
111 112 113
    DenseTensorUtils::GetMutableMeta(
        static_cast<SelectedRows*>(tensor_)->mutable_value())
        ->layout = layout;
114 115 116 117 118 119
  } else if (phi::SparseCooTensor::classof(tensor_)) {
    DenseTensorUtils::GetMutableMeta(static_cast<SparseCooTensor*>(tensor_))
        ->layout = layout;
  } else if (phi::SparseCsrTensor::classof(tensor_)) {
    DenseTensorUtils::GetMutableMeta(static_cast<SparseCsrTensor*>(tensor_))
        ->layout = layout;
120
  } else {
121
    PADDLE_THROW(phi::errors::Unimplemented(
122 123 124 125 126
        "Unsupported settting layout for `%s`.", tensor_->type_info().name()));
  }
}

void MetaTensor::share_lod(const MetaTensor& meta_tensor) {
127 128
  ValidCheck(*this);
  ValidCheck(meta_tensor);
129 130 131 132
  if (phi::SparseCooTensor::classof(tensor_) ||
      phi::SparseCsrTensor::classof(tensor_)) {
    return;
  }
H
hong 已提交
133 134 135 136
  if (meta_tensor.lod().size() == 0) {
    // no need share
    return;
  }
137
  if (phi::DenseTensor::classof(tensor_)) {
138 139
    DenseTensorUtils::GetMutableMeta(static_cast<DenseTensor*>(tensor_))->lod =
        meta_tensor.lod();
140
  } else if (phi::SelectedRows::classof(tensor_)) {
141 142 143
    DenseTensorUtils::GetMutableMeta(
        static_cast<SelectedRows*>(tensor_)->mutable_value())
        ->lod = meta_tensor.lod();
144
  } else {
145
    PADDLE_THROW(
146 147
        phi::errors::Unimplemented("Unsupported sharing lod inplace for `%s`.",
                                   tensor_->type_info().name()));
148 149 150
  }
}

151
void MetaTensor::share_meta(const MetaTensor& meta_tensor) {
152
  ValidCheck(*this);
Y
YuanRisheng 已提交
153
  if (phi::DenseTensor::classof(tensor_) ||
154 155 156
      phi::SelectedRows::classof(tensor_) ||
      phi::SparseCooTensor::classof(tensor_) ||
      phi::SparseCsrTensor::classof(tensor_)) {
Y
YuanRisheng 已提交
157
    share_dims(meta_tensor);
158 159 160
    set_dtype(meta_tensor.dtype());
    set_layout(meta_tensor.layout());
    share_lod(meta_tensor);
161
  } else {
162
    PADDLE_THROW(phi::errors::Unimplemented(
163
        "Unsupported sharing meta for `%s`.", tensor_->type_info().name()));
164 165 166
  }
}

Y
YuanRisheng 已提交
167
void MetaTensor::share_dims(const MetaTensor& meta_tensor) {
168
  ValidCheck(*this);
Y
YuanRisheng 已提交
169 170
  bool is_dense_tensor = phi::DenseTensor::classof(tensor_);
  bool is_selected_rows = phi::SelectedRows::classof(tensor_);
171 172 173
  bool is_sparse_coo = phi::SparseCooTensor::classof(tensor_);
  bool is_sparse_csr = phi::SparseCsrTensor::classof(tensor_);
  if (is_dense_tensor || is_selected_rows || is_sparse_coo || is_sparse_csr) {
Y
YuanRisheng 已提交
174 175
    set_dims(meta_tensor.dims());
    if (is_selected_rows) {
C
Chen Weihang 已提交
176
      const auto in_tensor_base = meta_tensor.tensor();
Y
YuanRisheng 已提交
177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192
      PADDLE_ENFORCE_EQ(
          phi::SelectedRows::classof(in_tensor_base),
          true,
          errors::InvalidArgument("The input MetaTensor is SelectedRows, but "
                                  "the output MetaTensor is not this type."));
      auto* selected_rows_out = static_cast<SelectedRows*>(tensor_);
      auto* selected_rows_in = static_cast<SelectedRows*>(in_tensor_base);
      selected_rows_out->set_rows(selected_rows_in->rows());
      selected_rows_out->set_height(selected_rows_in->height());
    }
  } else {
    PADDLE_THROW(phi::errors::Unimplemented(
        "Unsupported sharing dims for `%s`.", tensor_->type_info().name()));
  }
}

193 194
bool MetaTensor::initialized() const { return tensor_ != nullptr; }

195 196 197 198 199 200 201
// Private Member Methods

const LoD& MetaTensor::lod() const {
  if (phi::DenseTensor::classof(tensor_)) {
    return static_cast<DenseTensor*>(tensor_)->lod();
  } else if (phi::SelectedRows::classof(tensor_)) {
    return static_cast<SelectedRows*>(tensor_)->value().lod();
202 203 204 205
  } else if (phi::SparseCooTensor::classof(tensor_)) {
    return static_cast<SparseCooTensor*>(tensor_)->non_zero_elements().lod();
  } else if (phi::SparseCsrTensor::classof(tensor_)) {
    return static_cast<SparseCsrTensor*>(tensor_)->non_zero_elements().lod();
206 207 208 209 210 211 212 213
  } else {
    PADDLE_THROW(phi::errors::Unimplemented("Unsupported getting lod of `%s`.",
                                            tensor_->type_info().name()));
  }
}

TensorBase* MetaTensor::tensor() const { return tensor_; }

214
}  // namespace phi