• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* Copyright 2019 The TensorFlow Authors. All Rights Reserved.
2 
3 Licensed under the Apache License, Version 2.0 (the "License");
4 you may not use this file except in compliance with the License.
5 You may obtain a copy of the License at
6 
7     http://www.apache.org/licenses/LICENSE-2.0
8 
9 Unless required by applicable law or agreed to in writing, software
10 distributed under the License is distributed on an "AS IS" BASIS,
11 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 See the License for the specific language governing permissions and
13 limitations under the License.
14 ==============================================================================*/
15 
16 #ifndef TENSORFLOW_C_TF_TENSOR_H_
17 #define TENSORFLOW_C_TF_TENSOR_H_
18 
19 #include <stdbool.h>
20 #include <stdint.h>
21 
22 #include "tensorflow/c/c_api_macros.h"
23 #include "tensorflow/c/tf_datatype.h"
24 #include "tensorflow/c/tf_status.h"
25 
26 // Macro to control visibility of exported symbols in the shared library (.so,
27 // .dylib, .dll).
28 // This duplicates the TF_EXPORT macro definition in
29 // tensorflow/core/platform/macros.h in order to keep this .h file independent
30 // of any other includes.
31 #ifdef SWIG
32 #define TF_CAPI_EXPORT
33 #else
34 #if defined(_WIN32)
35 #ifdef TF_COMPILE_LIBRARY
36 #define TF_CAPI_EXPORT __declspec(dllexport)
37 #else
38 #define TF_CAPI_EXPORT __declspec(dllimport)
39 #endif  // TF_COMPILE_LIBRARY
40 #else
41 #define TF_CAPI_EXPORT __attribute__((visibility("default")))
42 #endif  // _WIN32
43 #endif  // SWIG
44 
45 #ifdef __cplusplus
46 extern "C" {
47 #endif
48 
49 // Allocator Attributes used for tensor allocation.
50 typedef struct TF_AllocatorAttributes {
51   size_t struct_size;
52   // Set boolean to 1 for CPU allocation, else 0.
53   TF_Bool on_host;
54 } TF_AllocatorAttributes;
55 
56 #define TF_ALLOCATOR_ATTRIBUTES_STRUCT_SIZE \
57   TF_OFFSET_OF_END(TF_AllocatorAttributes, on_host)
58 
59 // --------------------------------------------------------------------------
60 // TF_Tensor holds a multi-dimensional array of elements of a single data type.
61 // For all types other than TF_STRING, the data buffer stores elements
62 // in row major order.  E.g. if data is treated as a vector of TF_DataType:
63 //
64 //   element 0:   index (0, ..., 0)
65 //   element 1:   index (0, ..., 1)
66 //   ...
67 //
68 // The format for TF_STRING tensors is:
69 //   start_offset: array[uint64]
70 //   data:         byte[...]
71 //
72 //   The string length (as a varint, start_offset[i + 1] - start_offset[i]),
73 //   followed by the contents of the string is encoded at data[start_offset[i]].
74 //   TF_StringEncode and TF_StringDecode facilitate this encoding.
75 
76 typedef struct TF_Tensor TF_Tensor;
77 
78 // Return a new tensor that holds the bytes data[0,len-1].
79 //
80 // The data will be deallocated by a subsequent call to TF_DeleteTensor via:
81 //      (*deallocator)(data, len, deallocator_arg)
82 // Clients must provide a custom deallocator function so they can pass in
83 // memory managed by something like numpy.
84 //
85 // May return NULL (and invoke the deallocator) if the provided data buffer
86 // (data, len) is inconsistent with a tensor of the given TF_DataType
87 // and the shape specified by (dima, num_dims).
88 TF_CAPI_EXPORT extern TF_Tensor* TF_NewTensor(
89     TF_DataType, const int64_t* dims, int num_dims, void* data, size_t len,
90     void (*deallocator)(void* data, size_t len, void* arg),
91     void* deallocator_arg);
92 
93 // Allocate and return a new Tensor.
94 //
95 // This function is an alternative to TF_NewTensor and should be used when
96 // memory is allocated to pass the Tensor to the C API. The allocated memory
97 // satisfies TensorFlow's memory alignment preferences and should be preferred
98 // over calling malloc and free.
99 //
100 // The caller must set the Tensor values by writing them to the pointer returned
101 // by TF_TensorData with length TF_TensorByteSize.
102 TF_CAPI_EXPORT extern TF_Tensor* TF_AllocateTensor(TF_DataType,
103                                                    const int64_t* dims,
104                                                    int num_dims, size_t len);
105 
106 // Deletes `tensor` and returns a new TF_Tensor with the same content if
107 // possible. Returns nullptr and leaves `tensor` untouched if not.
108 TF_CAPI_EXPORT extern TF_Tensor* TF_TensorMaybeMove(TF_Tensor* tensor);
109 
110 // Destroy a tensor.
111 TF_CAPI_EXPORT extern void TF_DeleteTensor(TF_Tensor*);
112 
113 // Return the type of a tensor element.
114 TF_CAPI_EXPORT extern TF_DataType TF_TensorType(const TF_Tensor*);
115 
116 // Set a new shape for the Tensor.
117 TF_CAPI_EXPORT extern void TF_SetShape(TF_Tensor* tensor, const int64_t* dims,
118                                        int num_dims);
119 
120 // Return the number of dimensions that the tensor has.
121 TF_CAPI_EXPORT extern int TF_NumDims(const TF_Tensor*);
122 
123 // Return the length of the tensor in the "dim_index" dimension.
124 // REQUIRES: 0 <= dim_index < TF_NumDims(tensor)
125 TF_CAPI_EXPORT extern int64_t TF_Dim(const TF_Tensor* tensor, int dim_index);
126 
127 // Return the size of the underlying data in bytes.
128 TF_CAPI_EXPORT extern size_t TF_TensorByteSize(const TF_Tensor*);
129 
130 // Return a pointer to the underlying data buffer.
131 TF_CAPI_EXPORT extern void* TF_TensorData(const TF_Tensor*);
132 
133 // Returns the number of elements in the tensor.
134 TF_CAPI_EXPORT extern int64_t TF_TensorElementCount(const TF_Tensor* tensor);
135 
136 // Copy the internal data representation of `from` to `to`. `new_dims` and
137 // `num_new_dims` specify the new shape of the `to` tensor, `type` specifies its
138 // data type. On success, *status is set to TF_OK and the two tensors share the
139 // same data buffer.
140 //
141 // This call requires that the `from` tensor and the given type and shape (dims
142 // and num_dims) are "compatible" (i.e. they occupy the same number of bytes).
143 // Specifically, given from_type_size = TF_DataTypeSize(TF_TensorType(from)):
144 //
145 // ShapeElementCount(dims, num_dims) * TF_DataTypeSize(type)
146 //
147 // must equal
148 //
149 // TF_TensorElementCount(from) * from_type_size
150 //
151 // where TF_ShapeElementCount would be the number of elements in a tensor with
152 // the given shape.
153 //
154 // In addition, this function requires:
155 //   * TF_DataTypeSize(TF_TensorType(from)) != 0
156 //   * TF_DataTypeSize(type) != 0
157 //
158 // If any of the requirements are not met, *status is set to
159 // TF_INVALID_ARGUMENT.
160 TF_CAPI_EXPORT extern void TF_TensorBitcastFrom(const TF_Tensor* from,
161                                                 TF_DataType type, TF_Tensor* to,
162                                                 const int64_t* new_dims,
163                                                 int num_new_dims,
164                                                 TF_Status* status);
165 
166 // Returns bool iff this tensor is aligned.
167 TF_CAPI_EXPORT extern bool TF_TensorIsAligned(const TF_Tensor*);
168 
169 #ifdef __cplusplus
170 } /* end extern "C" */
171 #endif
172 
173 #endif  // TENSORFLOW_C_TF_TENSOR_H_
174