You can not select more than 25 topics
			Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
		
		
		
		
		
			
		
			
				
					
					
						
							221 lines
						
					
					
						
							6.5 KiB
						
					
					
				
			
		
		
	
	
							221 lines
						
					
					
						
							6.5 KiB
						
					
					
				| /* Copyright (c) 2016 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 <cstdint>
 | |
| #include <cstring>
 | |
| #include <memory>
 | |
| #include <typeindex>
 | |
| #include <utility>
 | |
| #include <vector>
 | |
| #include "paddle/fluid/framework/data_layout.h"
 | |
| #include "paddle/fluid/framework/ddim.h"
 | |
| #include "paddle/fluid/framework/framework.pb.h"
 | |
| #include "paddle/fluid/memory/memory.h"
 | |
| #include "paddle/fluid/platform/device_context.h"
 | |
| #include "paddle/fluid/platform/enforce.h"
 | |
| #include "paddle/fluid/platform/place.h"
 | |
| 
 | |
| namespace paddle {
 | |
| 
 | |
| namespace framework {
 | |
| 
 | |
| class LoDTensor;
 | |
| 
 | |
| class Tensor {
 | |
| #ifdef PADDLE_WITH_MKLDNN
 | |
| 
 | |
|  public:
 | |
|   inline mkldnn::memory::format_tag format() const { return format_; }
 | |
| 
 | |
|   inline void set_format(const mkldnn::memory::format_tag format) {
 | |
|     format_ = format;
 | |
|   }
 | |
| 
 | |
|  protected:
 | |
|   /**
 | |
|    * @brief the detail format of memory block which have layout as kMKLDNN
 | |
|    *
 | |
|    * @note MKLDNN lib support various memory format like nchw, nhwc, nChw8C,
 | |
|    *       nChw16c, etc. For a MKLDNN memory block, layout will be set as
 | |
|    *       DataLayout::kMKLDNN meanwhile detail memory format will be kept in
 | |
|    *       this field.
 | |
|    */
 | |
| 
 | |
|   mkldnn::memory::format_tag format_ = mkldnn::memory::format_tag::undef;
 | |
| #endif
 | |
| 
 | |
|  public:
 | |
|   template <typename T, size_t D, int MajorType, typename IndexType>
 | |
|   friend struct EigenTensor;
 | |
| 
 | |
|   template <typename T, int MajorType, typename IndexType>
 | |
|   friend struct EigenMatrix;
 | |
| 
 | |
|   template <typename T, int MajorType, typename IndexType>
 | |
|   friend struct EigenVector;
 | |
| 
 | |
|  public:
 | |
|   Tensor() : type_(proto::VarType::FP32), offset_(0) {}
 | |
| 
 | |
|   explicit Tensor(const proto::VarType::Type&);
 | |
| 
 | |
|   /*! Return a pointer to mutable memory block. */
 | |
|   template <typename T>
 | |
|   T* data();
 | |
| 
 | |
|   /*! Return a pointer to constant memory block. */
 | |
|   template <typename T>
 | |
|   const T* data() const;
 | |
| 
 | |
|   inline bool IsInitialized() const;
 | |
| 
 | |
|   /**
 | |
|    * @brief   Return a pointer to mutable memory block.
 | |
|    * @note    If not exist, then allocation.
 | |
|    */
 | |
|   template <typename T>
 | |
|   T* mutable_data(const platform::Place& place, size_t requested_size = 0);
 | |
| 
 | |
|   void* mutable_data(const platform::Place& place, proto::VarType::Type type,
 | |
|                      size_t requested_size = 0);
 | |
| 
 | |
|   void* mutable_data(const platform::Place& place, size_t requested_size = 0);
 | |
| 
 | |
|   /**
 | |
|    * @brief     Return a pointer to mutable memory block.
 | |
|    *
 | |
|    * @param[in] dims           The dimensions of the memory block.
 | |
|    * @param[in] place          The place of the memory block.
 | |
|    * @param[in] requested_size The size of the block in bytes.
 | |
|    *
 | |
|    * @note      If not exist, then allocation.
 | |
|    */
 | |
|   template <typename T>
 | |
|   T* mutable_data(const DDim& dims, const platform::Place& place,
 | |
|                   size_t requested_size = 0);
 | |
| 
 | |
|   /*! Return the dimensions of the memory block. */
 | |
|   const DDim& dims() const;
 | |
| 
 | |
|   /*! Return the numel of the memory block. */
 | |
|   int64_t numel() const;
 | |
| 
 | |
|   /*! Resize the dimensions of the memory block. */
 | |
|   Tensor& Resize(const DDim& dims);
 | |
| 
 | |
|   /*! The internal of two tensors share the same memory block. */
 | |
|   Tensor& ShareDataWith(const Tensor& src);
 | |
| 
 | |
|   /**
 | |
|    * @brief  Return a sub-tensor of the given tensor.
 | |
|    *
 | |
|    * @param[in] begin_idx   The index of the start row(inclusive) to slice.
 | |
|    *                        The index number begins from 0.
 | |
|    * @param[in] end_idx     The index of the end row(exclusive) to slice.
 | |
|    *                        The index number begins from 0.
 | |
|    */
 | |
|   Tensor Slice(int64_t begin_idx, int64_t end_idx) const;
 | |
| 
 | |
|   const platform::Place& place() const {
 | |
|     PADDLE_ENFORCE_NOT_NULL(
 | |
|         holder_, "Tensor not initialized yet when Tensor::place() is called.");
 | |
|     return holder_->place();
 | |
|   }
 | |
| 
 | |
|   proto::VarType::Type type() const {
 | |
|     PADDLE_ENFORCE_NOT_NULL(
 | |
|         holder_, "Tensor not initialized yet when Tensor::type() is called.");
 | |
|     return type_;
 | |
|   }
 | |
| 
 | |
|   // memory size returns the holding memory size in byte.
 | |
|   size_t memory_size() const;
 | |
| 
 | |
|   void check_memory_size() const;
 | |
| 
 | |
|   DataLayout layout() const { return layout_; }
 | |
| 
 | |
|   void set_layout(const DataLayout layout) { layout_ = layout; }
 | |
| 
 | |
|   void clear() {
 | |
|     holder_ = nullptr;
 | |
|     offset_ = 0;
 | |
|   }
 | |
| 
 | |
|   void ShareBufferWith(const Tensor& tensor) {
 | |
|     holder_ = tensor.holder_;
 | |
|     offset_ = tensor.offset_;
 | |
|     type_ = tensor.type_;
 | |
|   }
 | |
| 
 | |
|   bool IsSharedBufferWith(const Tensor& src) const {
 | |
|     return holder_ && holder_ == src.Holder();
 | |
|   }
 | |
| 
 | |
|   const std::shared_ptr<memory::Allocation>& Holder() const { return holder_; }
 | |
|   size_t offset() const { return offset_; }
 | |
| 
 | |
|   std::shared_ptr<memory::Allocation> MoveMemoryHolder() {
 | |
|     return std::move(holder_);
 | |
|   }
 | |
| 
 | |
|   void ResetHolder(std::shared_ptr<memory::Allocation> holder);
 | |
| 
 | |
|   void ResetHolderWithType(std::shared_ptr<memory::Allocation> holder,
 | |
|                            const proto::VarType::Type type);
 | |
| 
 | |
|  private:
 | |
|   /*! holds the memory block if allocated. */
 | |
|   std::shared_ptr<memory::Allocation> holder_;
 | |
|   proto::VarType::Type type_;
 | |
|   /**
 | |
|    * @brief points to elements dimensions.
 | |
|    *
 | |
|    * @note dims_ do not indicate the memory block size.
 | |
|    */
 | |
| 
 | |
|   DDim dims_;
 | |
| 
 | |
|   /**
 | |
|    * @brief the layout of memory block, default is NHWC.
 | |
|    *
 | |
|    * @note the memory allocation order, describe how weight/data is stored
 | |
|    *       For example, in 4-D Tensor(rank=4), there are three commonly
 | |
|    *       used layout. They are
 | |
|    *            NCHW, NHWC, CHWN.
 | |
|    *       N,C,H,W for respectively the batch size, the number of
 | |
|    *       feature maps, the height.
 | |
|    */
 | |
|   // Fix me: here just change the default layout to kNCHW
 | |
|   // it doesn't fix the real issue, i.e. feeder should set up tensor layout
 | |
|   // according to actual input data
 | |
|   DataLayout layout_ = DataLayout::kNCHW;
 | |
| 
 | |
|   /**
 | |
|    * @brief   A PlaceHolder may be shared by more than one tensor.
 | |
|    *
 | |
|    * @note    Some of them may be slices of the others. So the offset_
 | |
|    *          is introduced here to indicate the byte offset between
 | |
|    *          PlaceHolder::ptr_ and where the tensor data really begins.
 | |
|    */
 | |
|   size_t offset_;
 | |
| };
 | |
| 
 | |
| }  // namespace framework
 | |
| }  // namespace paddle
 | |
| 
 | |
| #include "paddle/fluid/framework/tensor_impl.h"
 |