paddle_tensor.h 7.6 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
// Copyright (c) 2021 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

17 18
#include <functional>
#include <memory>
S
Steffy-zxf 已提交
19
#include <string>
20
#include <vector>
S
Steffy-zxf 已提交
21

22 23
#include "paddle_infer_declare.h"  // NOLINT

24 25 26 27 28
#ifdef PADDLE_WITH_ONNXRUNTIME
#include "onnxruntime_c_api.h"    // NOLINT
#include "onnxruntime_cxx_api.h"  // NOLINT
#endif

29 30 31 32
namespace paddle {
class Tensor;
}

33 34
namespace paddle_infer {

S
Steffy-zxf 已提交
35 36 37 38
/// \brief  Experimental.
/// Strings for text data.
using Strings = std::vector<std::string>;

39
using OutputTensorHookFunc = std::function<void(
40
    const std::string&, const std::string&, const paddle::Tensor&)>;
41
using InputTensorHookFunc = OutputTensorHookFunc;
42

43 44 45 46 47 48 49 50 51 52
typedef void (*CallbackFunc)(void*);

#if defined(PADDLE_WITH_TESTING) && defined(PADDLE_WITH_INFERENCE_API_TEST)
class InferApiTesterUtils;
#endif

namespace contrib {
class TensorUtils;
}

W
Wilber 已提交
53 54 55 56
namespace experimental {
class InternalUtils;
};

57 58
/// \brief Paddle data type.
enum DataType {
Y
Yuanle Liu 已提交
59
  FLOAT32,
60 61 62 63
  INT64,
  INT32,
  UINT8,
  INT8,
64
  FLOAT16,
65
  BOOL,
Y
Yuanle Liu 已提交
66
  FLOAT64,
67
  BFLOAT16,
68
  // TODO(Inference): support more data types if needed.
69 70
};

张春乔 已提交
71
enum class PlaceType { kUNK = -1, kCPU, kGPU, kXPU, kIPU, kCUSTOM };
72

73 74
enum class DataLayout { kUNK = -1, kAny, kNHWC, kNCHW };

75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90
/// \brief Represents an n-dimensional array of values.
/// The Tensor is used to store the input or output of the network.
/// Zero copy means that the tensor supports direct copy of host or device data
/// to device,
/// eliminating additional CPU copy. Tensor is only used in the
/// AnalysisPredictor.
/// It is obtained through PaddlePredictor::GetinputTensor()
/// and PaddlePredictor::GetOutputTensor() interface.
class PD_INFER_DECL Tensor {
 public:
  /// \brief Reset the shape of the tensor.
  /// Generally it's only used for the input tensor.
  /// Reshape must be called before calling mutable_data() or copy_from_cpu()
  /// \param shape The shape to set.
  void Reshape(const std::vector<int>& shape);

S
Steffy-zxf 已提交
91 92 93 94 95 96 97 98
  /// \brief Experimental interface.
  /// Reset the shape of the Strings tensor.
  /// Generally it's only used for the input tensor.
  /// Reshape must be called before calling
  /// ZeroCopyStringTensorCreate() or PaddleInferTensorCreate()
  /// \param shape The shape to set.
  void ReshapeStrings(const std::size_t& shape);

99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119
  /// \brief Get the memory pointer in CPU or GPU with specific data type.
  /// Please Reshape the tensor first before call this.
  /// It's usually used to get input data pointer.
  /// \param place The place of the tensor.
  template <typename T>
  T* mutable_data(PlaceType place);

  /// \brief Get the memory pointer directly.
  /// It's usually used to get the output data pointer.
  /// \param[out] place To get the device type of the tensor.
  /// \param[out] size To get the data size of the tensor.
  /// \return The tensor data buffer pointer.
  template <typename T>
  T* data(PlaceType* place, int* size) const;

  /// \brief Copy the host memory to tensor data.
  /// It's usually used to set the input tensor data.
  /// \param data The pointer of the data, from which the tensor will copy.
  template <typename T>
  void CopyFromCpu(const T* data);

120 121 122 123 124 125 126
  /// \brief Share the data with tensor data.
  /// It's usually used to set the tensor data.
  /// \param data The pointer of the data, from which the tensor will share.
  /// \param shape The shape of data.
  /// \param place The place of data.
  /// \param layout The layout of data. Only NCHW is supported now.
  template <typename T>
127 128
  void ShareExternalData(const T* data,
                         const std::vector<int>& shape,
129 130 131
                         PlaceType place,
                         DataLayout layout = DataLayout::kNCHW);

S
Steffy-zxf 已提交
132 133 134 135 136
  /// \brief Experimental interface.
  /// It's usually used to set the input tensor data with Strings data type.
  /// \param data The pointer of the data, from which the tensor will copy.
  void CopyStringsFromCpu(const paddle_infer::Strings* data);

137 138 139 140
  /// \brief Copy the tensor data to the host memory.
  /// It's usually used to get the output tensor data.
  /// \param[out] data The tensor will copy the data to the address.
  template <typename T>
141 142 143 144 145 146 147 148 149 150 151 152 153 154 155
  void CopyToCpu(T* data) const;

  /// \brief Copy the tensor data to the host memory asynchronously.
  /// \param[out] data The tensor will copy the data to the address.
  /// \param[out] exec_stream The tensor will excute copy in this stream(Only
  /// GPU CUDA stream suppported now).
  template <typename T>
  void CopyToCpuAsync(T* data, void* exec_stream) const;

  /// \brief Copy the tensor data to the host memory asynchronously.
  /// \param[out] data The tensor will copy the data to the address.
  /// \param[out] cb Callback function cb(cb_params) will be executed on the
  /// host after all currently enqueued items in the stream have completed .
  template <typename T>
  void CopyToCpuAsync(T* data, CallbackFunc cb, void* cb_params) const;
156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174

  /// \brief Return the shape of the Tensor.
  std::vector<int> shape() const;

  /// \brief Set lod info of the tensor.
  /// More about LOD can be seen here:
  ///  https://www.paddlepaddle.org.cn/documentation/docs/zh/beginners_guide/basic_concept/lod_tensor.html#lodtensor
  /// \param x the lod info.
  void SetLoD(const std::vector<std::vector<size_t>>& x);
  /// \brief Return the lod info of the tensor.
  std::vector<std::vector<size_t>> lod() const;
  /// \brief Return the name of the tensor.
  const std::string& name() const;

  /// \brief Return the data type of the tensor.
  /// It's usually used to get the output tensor data type.
  /// \return The data type of the tensor.
  DataType type() const;

175 176 177 178
  /// \brief Return the place type of the tensor.
  /// \return The place type of the tensor.
  PlaceType place() const;

179
 protected:
180
  explicit Tensor(void* scope, const void* device_contexs);
S
Steffy-zxf 已提交
181 182

  template <typename T>
183
  void* FindTensor() const;
S
Steffy-zxf 已提交
184

185 186 187 188
  void SetPlace(PlaceType place,
                int device = -1,
                const std::string device_type = "");

189 190
  void SetName(const std::string& name);

191
  template <typename T>
192 193 194
  void CopyToCpuImpl(T* data,
                     void* stream = nullptr,
                     CallbackFunc cb = nullptr,
195 196
                     void* cb_params = nullptr) const;

197 198 199 200 201 202 203
  std::string name_;
  // The corresponding tensor pointer inside Paddle workspace is cached for
  // performance.
  mutable void* tensor_{nullptr};
  DataType dtype_;
  bool input_or_output_;
  void* scope_{nullptr};
204
  const void* device_contexs_{nullptr};
205 206
  PlaceType place_;
  int device_;
207
  std::string device_type_;
208

209 210 211 212 213 214 215 216 217 218
#ifdef PADDLE_WITH_ONNXRUNTIME
  bool is_ort_tensor_{false};
  std::vector<int64_t> shape_;
  std::weak_ptr<Ort::IoBinding> binding_;
  int idx_{-1};

  void SetOrtMark(bool is_ort_tensor);

  void SetOrtBinding(const std::shared_ptr<Ort::IoBinding> binding);

219 220 221
  template <typename T>
  T* ORTGetMutableData();

222 223 224 225 226 227 228
  template <typename T>
  void ORTCopyFromCpu(const T* data);

  template <typename T>
  void ORTCopyToCpu(T* data) const;
#endif

229
  friend class paddle_infer::contrib::TensorUtils;
W
Wilber 已提交
230
  friend class paddle_infer::experimental::InternalUtils;
231 232 233
#if defined(PADDLE_WITH_TESTING) && defined(PADDLE_WITH_INFERENCE_API_TEST)
  friend class paddle_infer::InferApiTesterUtils;
#endif
234 235 236
};

}  // namespace paddle_infer