Browse Source

uniform interface, add vector and string self-defined

pull/13610/head
yangjie159 4 years ago
parent
commit
48d7330a55
17 changed files with 753 additions and 159 deletions
  1. +5
    -3
      mindspore/lite/include/context.h
  2. +2
    -3
      mindspore/lite/include/errorcode.h
  3. +11
    -10
      mindspore/lite/include/lite_session.h
  4. +363
    -10
      mindspore/lite/include/lite_utils.h
  5. +3
    -3
      mindspore/lite/include/model.h
  6. +6
    -31
      mindspore/lite/include/ms_tensor.h
  7. +5
    -5
      mindspore/lite/include/version.h
  8. +1
    -0
      mindspore/lite/micro/cmake/package_wrapper.cmake
  9. +2
    -1
      mindspore/lite/micro/coder/generator/component/cmake_component.cc
  10. +16
    -7
      mindspore/lite/micro/coder/generator/component/common_component.cc
  11. +1
    -12
      mindspore/lite/micro/coder/generator/component/const_blocks/benchmark.cc
  12. +4
    -0
      mindspore/lite/micro/coder/generator/component/const_blocks/cmake_lists.cc
  13. +22
    -49
      mindspore/lite/micro/coder/generator/component/const_blocks/msession.cc
  14. +10
    -25
      mindspore/lite/micro/coder/generator/component/const_blocks/mtensor.cc
  15. +1
    -0
      mindspore/lite/micro/coder/generator/generator.cc
  16. +1
    -0
      mindspore/lite/micro/coder/operator_library/CMakeLists.txt
  17. +300
    -0
      mindspore/lite/src/common/string.cc

+ 5
- 3
mindspore/lite/include/context.h View File

@@ -17,8 +17,6 @@
#ifndef MINDSPORE_LITE_INCLUDE_CONTEXT_H_ #ifndef MINDSPORE_LITE_INCLUDE_CONTEXT_H_
#define MINDSPORE_LITE_INCLUDE_CONTEXT_H_ #define MINDSPORE_LITE_INCLUDE_CONTEXT_H_


#include <string>
#include <memory>
#include "include/ms_tensor.h" #include "include/ms_tensor.h"
#include "include/lite_utils.h" #include "include/lite_utils.h"
#include "include/lite_types.h" #include "include/lite_types.h"
@@ -55,10 +53,14 @@ struct DeviceContext {


/// \brief Context defined for holding environment variables during runtime. /// \brief Context defined for holding environment variables during runtime.
struct Context { struct Context {
std::string vendor_name_;
String vendor_name_;
int thread_num_ = 2; /**< thread number config for thread pool */ int thread_num_ = 2; /**< thread number config for thread pool */
AllocatorPtr allocator = nullptr; AllocatorPtr allocator = nullptr;
#ifndef NOT_USE_STL
DeviceContextVector device_list_ = {{DT_CPU, {false, MID_CPU}}}; DeviceContextVector device_list_ = {{DT_CPU, {false, MID_CPU}}};
#else
DeviceContextVector device_list_;
#endif // NOT_USE_STL
}; };
} // namespace mindspore::lite } // namespace mindspore::lite
#endif // MINDSPORE_LITE_INCLUDE_CONTEXT_H_ #endif // MINDSPORE_LITE_INCLUDE_CONTEXT_H_

+ 2
- 3
mindspore/lite/include/errorcode.h View File

@@ -17,8 +17,7 @@
#ifndef MINDSPORE_LITE_INCLUDE_ERRORCODE_H_ #ifndef MINDSPORE_LITE_INCLUDE_ERRORCODE_H_
#define MINDSPORE_LITE_INCLUDE_ERRORCODE_H_ #define MINDSPORE_LITE_INCLUDE_ERRORCODE_H_


#include <string>
#include <map>
#include "include/lite_utils.h"


namespace mindspore { namespace mindspore {
namespace lite { namespace lite {
@@ -67,7 +66,7 @@ constexpr int RET_INPUT_PARAM_INVALID = -600; /**< Invalid input param by user.
/// \param[in] error_code define return status of procedure. /// \param[in] error_code define return status of procedure.
/// ///
/// \return String of errorcode info. /// \return String of errorcode info.
std::string GetErrorInfo(STATUS error_code);
String GetErrorInfo(STATUS error_code);


} // namespace lite } // namespace lite
} // namespace mindspore } // namespace mindspore


+ 11
- 10
mindspore/lite/include/lite_session.h View File

@@ -17,10 +17,9 @@
#ifndef MINDSPORE_LITE_INCLUDE_LITE_SESSION_H #ifndef MINDSPORE_LITE_INCLUDE_LITE_SESSION_H
#define MINDSPORE_LITE_INCLUDE_LITE_SESSION_H #define MINDSPORE_LITE_INCLUDE_LITE_SESSION_H


#include <memory>
#include <vector>
#include <string>
#ifndef NOT_USE_STL
#include <unordered_map> #include <unordered_map>
#endif // NOT_USE_STL
#include "include/ms_tensor.h" #include "include/ms_tensor.h"
#include "include/model.h" #include "include/model.h"
#include "include/context.h" #include "include/context.h"
@@ -66,14 +65,14 @@ class MS_API LiteSession {
/// \brief Get input MindSpore Lite MSTensors of model. /// \brief Get input MindSpore Lite MSTensors of model.
/// ///
/// \return The vector of MindSpore Lite MSTensor. /// \return The vector of MindSpore Lite MSTensor.
virtual std::vector<tensor::MSTensor *> GetInputs() const = 0;
virtual Vector<tensor::MSTensor *> GetInputs() const = 0;


/// \brief Get input MindSpore Lite MSTensors of model by tensor name. /// \brief Get input MindSpore Lite MSTensors of model by tensor name.
/// ///
/// \param[in] node_name Define tensor name. /// \param[in] node_name Define tensor name.
/// ///
/// \return The vector of MindSpore Lite MSTensor. /// \return The vector of MindSpore Lite MSTensor.
virtual mindspore::tensor::MSTensor *GetInputsByTensorName(const std::string &tensor_name) const = 0;
virtual mindspore::tensor::MSTensor *GetInputsByTensorName(const String &tensor_name) const = 0;


/// \brief Run session with callback. /// \brief Run session with callback.
/// ///
@@ -92,24 +91,26 @@ class MS_API LiteSession {
/// \note Deprecated, replace with GetOutputByTensorName /// \note Deprecated, replace with GetOutputByTensorName
/// ///
/// \return The vector of MindSpore Lite MSTensor. /// \return The vector of MindSpore Lite MSTensor.
virtual std::vector<tensor::MSTensor *> GetOutputsByNodeName(const std::string &node_name) const = 0;
virtual Vector<tensor::MSTensor *> GetOutputsByNodeName(const String &node_name) const = 0;


#ifndef NOT_USE_STL
/// \brief Get output MindSpore Lite MSTensors of model mapped by tensor name. /// \brief Get output MindSpore Lite MSTensors of model mapped by tensor name.
/// ///
/// \return The map of output tensor name and MindSpore Lite MSTensor. /// \return The map of output tensor name and MindSpore Lite MSTensor.
virtual std::unordered_map<std::string, mindspore::tensor::MSTensor *> GetOutputs() const = 0;
virtual std::unordered_map<String, mindspore::tensor::MSTensor *> GetOutputs() const = 0;
#endif


/// \brief Get name of output tensors of model compiled by this session. /// \brief Get name of output tensors of model compiled by this session.
/// ///
/// \return The vector of string as output tensor names in order. /// \return The vector of string as output tensor names in order.
virtual std::vector<std::string> GetOutputTensorNames() const = 0;
virtual Vector<String> GetOutputTensorNames() const = 0;


/// \brief Get output MindSpore Lite MSTensors of model by tensor name. /// \brief Get output MindSpore Lite MSTensors of model by tensor name.
/// ///
/// \param[in] tensor_name Define tensor name. /// \param[in] tensor_name Define tensor name.
/// ///
/// \return Pointer of MindSpore Lite MSTensor. /// \return Pointer of MindSpore Lite MSTensor.
virtual mindspore::tensor::MSTensor *GetOutputByTensorName(const std::string &tensor_name) const = 0;
virtual mindspore::tensor::MSTensor *GetOutputByTensorName(const String &tensor_name) const = 0;


/// \brief Resize inputs shape. /// \brief Resize inputs shape.
/// ///
@@ -117,7 +118,7 @@ class MS_API LiteSession {
/// \param[in] dims Define the inputs new shape. /// \param[in] dims Define the inputs new shape.
/// ///
/// \return STATUS as an error code of resize inputs, STATUS is defined in errorcode.h. /// \return STATUS as an error code of resize inputs, STATUS is defined in errorcode.h.
virtual int Resize(const std::vector<tensor::MSTensor *> &inputs, const std::vector<std::vector<int>> &dims) = 0;
virtual int Resize(const Vector<tensor::MSTensor *> &inputs, const Vector<Vector<int>> &dims) = 0;
}; };
} // namespace session } // namespace session
} // namespace mindspore } // namespace mindspore


+ 363
- 10
mindspore/lite/include/lite_utils.h View File

@@ -16,31 +16,383 @@


#ifndef MINDSPORE_LITE_INCLUDE_LITE_UTILS_H_ #ifndef MINDSPORE_LITE_INCLUDE_LITE_UTILS_H_
#define MINDSPORE_LITE_INCLUDE_LITE_UTILS_H_ #define MINDSPORE_LITE_INCLUDE_LITE_UTILS_H_

#ifndef NOT_USE_STL
#include <vector> #include <vector>
#include <string> #include <string>
#include <memory> #include <memory>
#include "include/ms_tensor.h"
#include <functional>
#else
#include <stdint.h>
#include <stdlib.h>
#include <string.h>
#include <stddef.h>
#endif // NOT_USE_STL


namespace mindspore {
class Allocator;
#ifndef MS_API
#ifdef _WIN32
#define MS_API __declspec(dllexport)
#else
#define MS_API __attribute__((visibility("default")))
#endif
#endif


namespace mindspore {
namespace schema { namespace schema {
struct Tensor; struct Tensor;
} // namespace schema } // namespace schema


namespace tensor {
class MSTensor;
} // namespace tensor

namespace lite { namespace lite {
struct DeviceContext;
} // namespace lite

#ifdef NOT_USE_STL
class String {
public:
String();
String(size_t count, char ch);
String(const char *s, size_t count);
explicit String(const char *s);
String(const String &other);
String(const String &other, size_t pos, size_t count = npos);

~String();

String &operator=(const String &str);
String &operator=(const char *str);

char &at(size_t pos);
const char &at(size_t pos) const;
inline char &operator[](size_t pos);
inline const char &operator[](size_t pos) const;
char *data() noexcept;
const char *data() const noexcept;
const char *c_str() const noexcept;

// capacity
bool empty() const noexcept;
size_t size() const noexcept;
size_t length() const noexcept;

// operations
void clear() noexcept;
String &append(size_t count, const char ch);
String &append(const String &str);
String &append(const char *s);
String &operator+(const String &str);
String &operator+=(const String &str);
String &operator+=(const char *str);
String &operator+=(const char ch);
int compare(const String &str) const;
int compare(const char *str) const;

String substr(size_t pos = 0, size_t count = npos) const;

static const size_t npos = -1;

private:
size_t size_;
char *buffer_;
};

String operator+(const String &str1, const char *str2);
String operator+(const char *str1, const String &str2);

String to_string(int32_t value);
String to_string(float value);

#define DEFAULT_CAPACITY 4
#define MS_C_EXCEPTION(...) exit(1)
#define MIN(x, y) ((x < y) ? (x) : (y))
template <typename T>
class Vector {
public:
Vector() {
size_ = 0;
capacity_ = DEFAULT_CAPACITY;
elem_size_ = sizeof(T);
data_ = nullptr;
}

explicit Vector(size_t size) {
size_ = size;
elem_size_ = sizeof(T);
capacity_ = (size == 0 ? DEFAULT_CAPACITY : size);
data_ = reinterpret_cast<T *>(malloc(capacity_ * elem_size_));
if (data_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
memset(data_, 0, capacity_ * elem_size_);
}

Vector(size_t size, const T &value) {
size_ = size;
elem_size_ = sizeof(T);
capacity_ = (size == 0 ? DEFAULT_CAPACITY : size);
data_ = reinterpret_cast<T *>(malloc(capacity_ * elem_size_));
if (data_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
for (int i = 0; i < size; ++i) {
data_[i] = value;
}
}

Vector(const Vector<T> &vec) {
size_ = vec.size_;
elem_size_ = sizeof(T);
capacity_ = vec.capacity_;
data_ = reinterpret_cast<T *>(malloc(capacity_ * elem_size_));
if (data_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
memcpy(data_, vec.data_, size_ * elem_size_);
}

~Vector() {
if (data_ != nullptr) {
free(data_);
}
}

void clear() {
size_ = 0;
if (data_ != nullptr) {
free(data_);
data_ = nullptr;
}
}

void push_back(const T &elem) {
if (data_ == nullptr) {
data_ = reinterpret_cast<T *>(malloc(capacity_ * elem_size_));
if (data_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
} else if (size_ == capacity_) {
resize(size_ + 1);
--size_;
}
data_[size_] = elem;
++size_;
}

void push_back(T &&elem) {
if (data_ == nullptr) {
data_ = reinterpret_cast<T *>(malloc(capacity_ * elem_size_));
if (data_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
} else if (size_ == capacity_) {
resize(size_ + 1);
--size_;
}
data_[size_] = elem;
++size_;
}

void pop_back() {
if (size_ > 0) {
--size_;
} else {
MS_C_EXCEPTION("Index is out of range!");
}
}

void insert(const T &elem, size_t index) {
if (index <= size_) {
++size_;
if (size_ > capacity_) {
resize(size_);
}
if (index == size_ - 1) {
push_back(elem);
} else {
memmove(data_ + index + 1, data_ + index, (size_ - index - 1) * elem_size_);
data_[index] = elem;
}
} else {
MS_C_EXCEPTION("Input index is out of range!");
}
}

T *begin() { return data_; }

const T *begin() const { return data_; }

T *end() { return data_ + size_; }

const T *end() const { return data_ + size_; }

T &front() {
if (size_ > 0) {
return data_[0];
}
MS_C_EXCEPTION("Index is out of range!");
}

const T &front() const {
if (size_ > 0) {
return data_[0];
}
MS_C_EXCEPTION("Index is out of range!");
}

T &back() {
if (size_ > 0) {
return data_[size_ - 1];
}
MS_C_EXCEPTION("Index is out of range!");
}

const T &back() const {
if (size_ > 0) {
return data_[size_ - 1];
}
MS_C_EXCEPTION("Index is out of range!");
}

T &at(size_t index) {
if (index < size_) {
return data_[index];
}
MS_C_EXCEPTION("Input index is out of range!");
}

const T &at(size_t index) const {
if (index < size_) {
return data_[index];
}
MS_C_EXCEPTION("Input index is out of range!");
}

T &operator[](size_t index) {
if (index < size_) {
return data_[index];
}
MS_C_EXCEPTION("Input index is out of range!");
}

const T &operator[](size_t index) const {
if (index < size_) {
return data_[index];
}
MS_C_EXCEPTION("Input index is out of range!");
}

T *data() { return data_; }

const T *data() const { return data_; }

size_t size() const { return size_; }

size_t capacity() const { return capacity_; }

bool empty() const { return size_ == 0; }

void erase(size_t index) {
if (index == size_ - 1) {
--size_;
} else if (index < size_) {
memmove(data_ + index, data_ + index + 1, (size_ - index - 1) * elem_size_);
--size_;
} else {
MS_C_EXCEPTION("Input index is out of range!");
}
}

void resize(size_t size) {
while (size > capacity_) {
capacity_ *= 2;
}
T *tmp = data_;
data_ = reinterpret_cast<T *>(malloc(capacity_ * elem_size_));
if (data_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
memcpy(data_, tmp, MIN(size, size_) * elem_size_);
size_ = size;
free(tmp);
}

void reserve(size_t capacity) {
if (capacity > capacity_) {
capacity_ = capacity;
}
}

Vector<T> &operator=(const Vector<T> &vec) {
if (this == &vec) {
return *this;
}
size_ = vec.size_;
elem_size_ = sizeof(T);
capacity_ = vec.capacity_;
data_ = reinterpret_cast<T *>(malloc(capacity_ * elem_size_));
if (data_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
memcpy(data_, vec.data_, size_ * elem_size_);
return *this;
}

private:
size_t size_;
size_t elem_size_;
size_t capacity_;
T *data_;
};
using TensorPtrVector = Vector<mindspore::schema::Tensor *>;
using Uint32Vector = Vector<uint32_t>;
using AllocatorPtr = void *;
using DeviceContextVector = Vector<lite::DeviceContext>;
using KernelCallBack = void (*)(void *, void *);
#else
/// \brief Allocator defined a memory pool for malloc memory and free memory dynamically. /// \brief Allocator defined a memory pool for malloc memory and free memory dynamically.
/// ///
/// \note List public class and interface for reference. /// \note List public class and interface for reference.

/// \brief DeviceContext defined a device context.
struct DeviceContext;
class Allocator;
using AllocatorPtr = std::shared_ptr<Allocator>;


using TensorPtrVector = std::vector<mindspore::schema::Tensor *>; using TensorPtrVector = std::vector<mindspore::schema::Tensor *>;
using DeviceContextVector = std::vector<DeviceContext>;
using Uint32Vector = std::vector<uint32_t>; using Uint32Vector = std::vector<uint32_t>;
template <typename T>
using Vector = std::vector<T>;

template <typename T>
inline std::string to_string(T t) {
return std::to_string(t);
}

namespace tensor {
using String = std::string; using String = std::string;
using AllocatorPtr = std::shared_ptr<Allocator>;
} // namespace tensor

namespace session {
using String = std::string;
} // namespace session

/// \brief CallBackParam defined input arguments for callBack function.
struct CallBackParam {
session::String node_name; /**< node name argument */
session::String node_type; /**< node type argument */
};

struct GPUCallBackParam : CallBackParam {
double execute_time{-1.f};
};

/// \brief KernelCallBack defined the function pointer for callBack.
using KernelCallBack = std::function<bool(Vector<tensor::MSTensor *> inputs, Vector<tensor::MSTensor *> outputs,
const CallBackParam &opInfo)>;

namespace lite {
using String = std::string;
using DeviceContextVector = std::vector<DeviceContext>;


/// \brief Set data of MSTensor from string vector. /// \brief Set data of MSTensor from string vector.
/// ///
@@ -48,12 +400,13 @@ using AllocatorPtr = std::shared_ptr<Allocator>;
/// \param[out] MSTensor. /// \param[out] MSTensor.
/// ///
/// \return STATUS as an error code of this interface, STATUS is defined in errorcode.h. /// \return STATUS as an error code of this interface, STATUS is defined in errorcode.h.
int MS_API StringsToMSTensor(const std::vector<std::string> &inputs, tensor::MSTensor *tensor);
int MS_API StringsToMSTensor(const Vector<String> &inputs, tensor::MSTensor *tensor);


/// \brief Get string vector from MSTensor. /// \brief Get string vector from MSTensor.
/// \param[in] MSTensor. /// \param[in] MSTensor.
/// \return string vector. /// \return string vector.
std::vector<std::string> MS_API MSTensorToStrings(const tensor::MSTensor *tensor);
Vector<String> MS_API MSTensorToStrings(const tensor::MSTensor *tensor);
} // namespace lite } // namespace lite
#endif // NOT_USE_STL
} // namespace mindspore } // namespace mindspore
#endif // MINDSPORE_LITE_INCLUDE_LITE_UTILS_H_ #endif // MINDSPORE_LITE_INCLUDE_LITE_UTILS_H_

+ 3
- 3
mindspore/lite/include/model.h View File

@@ -15,7 +15,7 @@
*/ */
#ifndef MINDSPORE_LITE_INCLUDE_MODEL_H_ #ifndef MINDSPORE_LITE_INCLUDE_MODEL_H_
#define MINDSPORE_LITE_INCLUDE_MODEL_H_ #define MINDSPORE_LITE_INCLUDE_MODEL_H_
#include <vector>
#include "include/lite_utils.h" #include "include/lite_utils.h"


namespace mindspore::lite { namespace mindspore::lite {
@@ -28,7 +28,7 @@ struct MS_API Model {
Uint32Vector output_indices_; Uint32Vector output_indices_;
int quant_type_; int quant_type_;
}; };
using NodePtrVector = std::vector<Node *>;
using NodePtrVector = Vector<Node *>;
struct SubGraph { struct SubGraph {
String name_; String name_;
Uint32Vector input_indices_; Uint32Vector input_indices_;
@@ -36,7 +36,7 @@ struct MS_API Model {
Uint32Vector node_indices_; Uint32Vector node_indices_;
Uint32Vector tensor_indices_; Uint32Vector tensor_indices_;
}; };
using SubGraphPtrVector = std::vector<SubGraph *>;
using SubGraphPtrVector = Vector<SubGraph *>;
String name_; String name_;
String version_; String version_;
TensorPtrVector all_tensors_; TensorPtrVector all_tensors_;


+ 6
- 31
mindspore/lite/include/ms_tensor.h View File

@@ -17,21 +17,9 @@
#ifndef MINDSPORE_LITE_INCLUDE_MS_TENSOR_H_ #ifndef MINDSPORE_LITE_INCLUDE_MS_TENSOR_H_
#define MINDSPORE_LITE_INCLUDE_MS_TENSOR_H_ #define MINDSPORE_LITE_INCLUDE_MS_TENSOR_H_


#include <functional>
#include <memory>
#include <string>
#include <utility>
#include <vector>
#include "include/lite_utils.h"
#include "ir/dtype/type_id.h" #include "ir/dtype/type_id.h"


#ifndef MS_API
#ifdef _WIN32
#define MS_API __declspec(dllexport)
#else
#define MS_API __attribute__((visibility("default")))
#endif
#endif

namespace mindspore { namespace mindspore {
namespace tensor { namespace tensor {
/// \brief MSTensor defined tensor in MindSpore Lite. /// \brief MSTensor defined tensor in MindSpore Lite.
@@ -48,7 +36,7 @@ class MS_API MSTensor {
/// \brief Create a MSTensor. /// \brief Create a MSTensor.
/// ///
/// \return Pointer to an instance of MindSpore Lite MSTensor. /// \return Pointer to an instance of MindSpore Lite MSTensor.
static MSTensor *CreateTensor(const std::string &name, TypeId type, const std::vector<int> &shape, const void *data,
static MSTensor *CreateTensor(const String &name, TypeId type, const Vector<int> &shape, const void *data,
size_t data_len); size_t data_len);


/// \brief Get data type of the MindSpore Lite MSTensor. /// \brief Get data type of the MindSpore Lite MSTensor.
@@ -62,10 +50,10 @@ class MS_API MSTensor {
/// \brief Get shape of the MindSpore Lite MSTensor. /// \brief Get shape of the MindSpore Lite MSTensor.
/// ///
/// \return A vector of int as the shape of the MindSpore Lite MSTensor. /// \return A vector of int as the shape of the MindSpore Lite MSTensor.
virtual std::vector<int> shape() const = 0;
virtual Vector<int> shape() const = 0;


/// \brief Set the shape of MSTensor. /// \brief Set the shape of MSTensor.
virtual void set_shape(const std::vector<int> &name) = 0;
virtual void set_shape(const Vector<int> &name) = 0;


/// \brief Get number of element in MSTensor. /// \brief Get number of element in MSTensor.
/// ///
@@ -80,10 +68,10 @@ class MS_API MSTensor {
/// \brief Get the name of MSTensor. /// \brief Get the name of MSTensor.
/// ///
/// \return the name of MSTensor. /// \return the name of MSTensor.
virtual std::string tensor_name() const = 0;
virtual String tensor_name() const = 0;


/// \brief Set the name of MSTensor. /// \brief Set the name of MSTensor.
virtual void set_tensor_name(const std::string name) = 0;
virtual void set_tensor_name(const String name) = 0;


/// \brief Get the pointer of data in MSTensor. /// \brief Get the pointer of data in MSTensor.
/// ///
@@ -105,18 +93,5 @@ class MS_API MSTensor {
virtual void set_data(void *data) = 0; virtual void set_data(void *data) = 0;
}; };
} // namespace tensor } // namespace tensor
/// \brief CallBackParam defined input arguments for callBack function.
struct CallBackParam {
std::string node_name; /**< node name argument */
std::string node_type; /**< node type argument */
};

struct GPUCallBackParam : CallBackParam {
double execute_time{-1.f};
};

/// \brief KernelCallBack defined the function pointer for callBack.
using KernelCallBack = std::function<bool(std::vector<tensor::MSTensor *> inputs,
std::vector<tensor::MSTensor *> outputs, const CallBackParam &opInfo)>;
} // namespace mindspore } // namespace mindspore
#endif // MINDSPORE_LITE_INCLUDE_MS_TENSOR_H_ #endif // MINDSPORE_LITE_INCLUDE_MS_TENSOR_H_

+ 5
- 5
mindspore/lite/include/version.h View File

@@ -17,7 +17,7 @@
#ifndef MINDSPORE_LITE_INCLUDE_VERSION_H_ #ifndef MINDSPORE_LITE_INCLUDE_VERSION_H_
#define MINDSPORE_LITE_INCLUDE_VERSION_H_ #define MINDSPORE_LITE_INCLUDE_VERSION_H_


#include <string>
#include "include/lite_utils.h"


namespace mindspore { namespace mindspore {
namespace lite { namespace lite {
@@ -28,11 +28,11 @@ const int ms_version_revision = 0;
/// \brief Global method to get a version string. /// \brief Global method to get a version string.
/// ///
/// \return The version string of MindSpore Lite. /// \return The version string of MindSpore Lite.
inline std::string Version() {
return "MindSpore Lite " + std::to_string(ms_version_major) + "." + std::to_string(ms_version_minor) + "." +
std::to_string(ms_version_revision);
inline String Version() {
return "MindSpore Lite " + to_string(ms_version_major) + "." + to_string(ms_version_minor) + "." +
to_string(ms_version_revision);
} }
} // namespace lite } // namespace lite
} // namespace mindspore } // namespace mindspore


#endif // LITE_VERSION_H
#endif // MINDSPORE_LITE_INCLUDE_VERSION_H_

+ 1
- 0
mindspore/lite/micro/cmake/package_wrapper.cmake View File

@@ -22,6 +22,7 @@ set(WRAPPER_SRC
${WRAPPER_DIR}/int8/resize_int8_wrapper.c ${WRAPPER_DIR}/int8/resize_int8_wrapper.c
${WRAPPER_DIR}/int8/slice_int8_wrapper.c ${WRAPPER_DIR}/int8/slice_int8_wrapper.c
${WRAPPER_DIR}/int8/batchnorm_int8_wrapper.c ${WRAPPER_DIR}/int8/batchnorm_int8_wrapper.c
${LITE_DIR}/src/common/string.cc
) )


list(APPEND FILE_SET ${WRAPPER_SRC} ${RUNTIME_SRC}) list(APPEND FILE_SET ${WRAPPER_SRC} ${RUNTIME_SRC})

+ 2
- 1
mindspore/lite/micro/coder/generator/component/cmake_component.cc View File

@@ -34,7 +34,8 @@ void CodeCMakeNetLibrary(std::ofstream &ofs, const std::unique_ptr<CoderContext>
ofs << " weight.c.o\n" ofs << " weight.c.o\n"
<< " net.c.o\n" << " net.c.o\n"
<< " session.cc.o\n" << " session.cc.o\n"
<< " tensor.cc.o\n";
<< " tensor.cc.o\n"
<< " string.cc.o\n";
if (config->debug_mode()) { if (config->debug_mode()) {
ofs << " debug_utils.c.o\n"; ofs << " debug_utils.c.o\n";
} }


+ 16
- 7
mindspore/lite/micro/coder/generator/component/common_component.cc View File

@@ -26,6 +26,14 @@


namespace mindspore::lite::micro { namespace mindspore::lite::micro {
void CodeSessionCompileGraph(std::ofstream &ofs, const std::unique_ptr<CoderContext> &ctx) { void CodeSessionCompileGraph(std::ofstream &ofs, const std::unique_ptr<CoderContext> &ctx) {
auto array_tostring = [&ofs](const std::vector<int> &array, const std::string &name) {
size_t num = array.size();
ofs << " Vector<int> " << name << ";\n";
ofs << " " << name << ".resize(" << num << ");\n";
for (size_t i = 0; i < num; ++i) {
ofs << " " << name << "[" << i << "] = " << array[i] << ";\n";
}
};
std::vector<Tensor *> inputs = ctx->graph_inputs(); std::vector<Tensor *> inputs = ctx->graph_inputs();
std::vector<Tensor *> outputs = ctx->graph_outputs(); std::vector<Tensor *> outputs = ctx->graph_outputs();
size_t inputs_size = inputs.size(); size_t inputs_size = inputs.size();
@@ -36,20 +44,21 @@ void CodeSessionCompileGraph(std::ofstream &ofs, const std::unique_ptr<CoderCont
ofs << " inputs_.resize(" << inputs_size << ");\n"; ofs << " inputs_.resize(" << inputs_size << ");\n";
for (size_t i = 0; i < inputs_size; ++i) { for (size_t i = 0; i < inputs_size; ++i) {
Tensor *input = inputs[i]; Tensor *input = inputs[i];
ofs << " inputs_[" << i << "] = new (std::nothrow) MTensor(\"" << input->tensor_name() << "\", "
<< EnumNameDataType(input->data_type()) << ", " << ArrayToString(input->shape()) << ");\n";
std::string shape_i = "in_shape_" + std::to_string(i);
array_tostring(input->shape(), shape_i);
ofs << " inputs_[" << i << "] = new (std::nothrow) MTensor(String(\"" << input->tensor_name() << "\"), "
<< EnumNameDataType(input->data_type()) << ", " << shape_i << ");\n";
ofs << " MS_ERROR_IF_NULL(inputs_[" << i << "]);\n"; ofs << " MS_ERROR_IF_NULL(inputs_[" << i << "]);\n";
} }
ofs << " outputs_.resize(" << outputs_size << ");\n"; ofs << " outputs_.resize(" << outputs_size << ");\n";
for (size_t i = 0; i < outputs_size; ++i) { for (size_t i = 0; i < outputs_size; ++i) {
Tensor *output = outputs[i]; Tensor *output = outputs[i];
ofs << " outputs_[" << i << "] = new (std::nothrow) MTensor(\"" << output->tensor_name() << "\", "
<< EnumNameDataType(output->data_type()) << ", " << ArrayToString(output->shape()) << ");\n";
std::string shape_i = "out_shape_" + std::to_string(i);
array_tostring(output->shape(), shape_i);
ofs << " outputs_[" << i << "] = new (std::nothrow) MTensor(String(\"" << output->tensor_name() << "\"), "
<< EnumNameDataType(output->data_type()) << ", " << shape_i << ");\n";
ofs << " MS_ERROR_IF_NULL(outputs_[" << i << "]);\n"; ofs << " MS_ERROR_IF_NULL(outputs_[" << i << "]);\n";
} }
ofs << " for (const auto &output: outputs_) {\n"
" output_tensor_map_[output->tensor_name()] = output;\n"
" }\n";
ofs << " return RET_OK;\n"; ofs << " return RET_OK;\n";
ofs << "}\n\n"; ofs << "}\n\n";
} }


+ 1
- 12
mindspore/lite/micro/coder/generator/component/const_blocks/benchmark.cc View File

@@ -72,10 +72,6 @@ void PrintData(void *data, size_t data_number) {
} }


void TensorToString(tensor::MSTensor *tensor) { void TensorToString(tensor::MSTensor *tensor) {
uint8_t i = 0;
std::cout << "uint8: " << i << std::endl;

std::cout << "Name: " << tensor->tensor_name();
std::cout << ", DataType: " << tensor->data_type(); std::cout << ", DataType: " << tensor->data_type();
std::cout << ", Size: " << tensor->Size(); std::cout << ", Size: " << tensor->Size();
std::cout << ", Shape:"; std::cout << ", Shape:";
@@ -129,7 +125,7 @@ int main(int argc, const char **argv) {
} }


// set model inputs tensor data // set model inputs tensor data
std::vector<tensor::MSTensor *> inputs = session->GetInputs();
Vector<tensor::MSTensor *> inputs = session->GetInputs();
size_t inputs_num = inputs.size(); size_t inputs_num = inputs.size();
void *inputs_binbuf[inputs_num]; void *inputs_binbuf[inputs_num];
int inputs_size[inputs_num]; int inputs_size[inputs_num];
@@ -150,13 +146,6 @@ int main(int argc, const char **argv) {
return lite::RET_ERROR; return lite::RET_ERROR;
} }


auto outputs = session->GetOutputs();
std::cout << "output size: " << outputs.size() << std::endl;
for (const auto &item : outputs) {
auto output = item.second;
TensorToString(output);
}

std::cout << "run benchmark success" << std::endl; std::cout << "run benchmark success" << std::endl;
delete session; delete session;
for (size_t i = 0; i < inputs_num; ++i) { for (size_t i = 0; i < inputs_num; ++i) {


+ 4
- 0
mindspore/lite/micro/coder/generator/component/const_blocks/cmake_lists.cc View File

@@ -34,6 +34,8 @@ set(HEADER_PATH ${PKG_PATH}/inference)
option(MICRO_BUILD_ARM64 "build android arm64" OFF) option(MICRO_BUILD_ARM64 "build android arm64" OFF)
option(MICRO_BUILD_ARM32A "build android arm32" OFF) option(MICRO_BUILD_ARM32A "build android arm32" OFF)


add_compile_definitions(NOT_USE_STL)

if(MICRO_BUILD_ARM64 OR MICRO_BUILD_ARM32A) if(MICRO_BUILD_ARM64 OR MICRO_BUILD_ARM32A)
add_compile_definitions(ENABLE_NEON) add_compile_definitions(ENABLE_NEON)
add_compile_definitions(ENABLE_ARM) add_compile_definitions(ENABLE_ARM)
@@ -95,6 +97,8 @@ set(HEADER_PATH ${PKG_PATH}/inference)
message("operator lib path: ${OP_LIB}") message("operator lib path: ${OP_LIB}")
message("operator header path: ${OP_HEADER_PATH}") message("operator header path: ${OP_HEADER_PATH}")


add_compile_definitions(NOT_USE_STL)

include_directories(${CMAKE_CURRENT_SOURCE_DIR}/../include) include_directories(${CMAKE_CURRENT_SOURCE_DIR}/../include)
include_directories(${OP_HEADER_PATH}) include_directories(${OP_HEADER_PATH})
include_directories(${HEADER_PATH}) include_directories(${HEADER_PATH})


+ 22
- 49
mindspore/lite/micro/coder/generator/component/const_blocks/msession.cc View File

@@ -63,31 +63,25 @@ class LiteSession : public session::LiteSession {


int CompileGraph(lite::Model *model) override; int CompileGraph(lite::Model *model) override;


std::vector<tensor::MSTensor *> GetInputs() const override;
Vector<tensor::MSTensor *> GetInputs() const override;


mindspore::tensor::MSTensor *GetInputsByTensorName(const std::string &tensor_name) const override { return nullptr; }
mindspore::tensor::MSTensor *GetInputsByTensorName(const String &tensor_name) const override { return nullptr; }


int RunGraph(const KernelCallBack &before = nullptr, const KernelCallBack &after = nullptr) override; int RunGraph(const KernelCallBack &before = nullptr, const KernelCallBack &after = nullptr) override;


std::vector<tensor::MSTensor *> GetOutputsByNodeName(const std::string &node_name) const override;
Vector<tensor::MSTensor *> GetOutputsByNodeName(const String &node_name) const override;


std::unordered_map<std::string, mindspore::tensor::MSTensor *> GetOutputs() const override;
Vector<String> GetOutputTensorNames() const override;


std::vector<std::string> GetOutputTensorNames() const override;
mindspore::tensor::MSTensor *GetOutputByTensorName(const String &tensor_name) const override;


mindspore::tensor::MSTensor *GetOutputByTensorName(const std::string &tensor_name) const override;

int Resize(const std::vector<tensor::MSTensor *> &inputs, const std::vector<std::vector<int>> &dims) override;
int Resize(const Vector<tensor::MSTensor *> &inputs, const Vector<Vector<int>> &dims) override { return RET_ERROR; }


int InitRuntimeBuffer(); int InitRuntimeBuffer();


private: private:
int SetInputsData(const std::vector<MTensor *> &inputs) const;
std::vector<MTensor *> inputs_;
std::vector<MTensor *> outputs_;
std::unordered_map<std::string, mindspore::tensor::MSTensor *> output_tensor_map_;
std::unordered_map<std::string, std::vector<mindspore::tensor::MSTensor *>> output_node_map_;

Vector<MTensor *> inputs_;
Vector<MTensor *> outputs_;
void *runtime_buffer_; void *runtime_buffer_;
}; };


@@ -95,7 +89,6 @@ class LiteSession : public session::LiteSession {
} // namespace mindspore } // namespace mindspore


#endif // MINDSPORE_LITE_MICRO_LIBRARY_SOURCE_SESSION_H_ #endif // MINDSPORE_LITE_MICRO_LIBRARY_SOURCE_SESSION_H_

)RAW"; )RAW";


const char *session_source = R"RAW( const char *session_source = R"RAW(
@@ -130,8 +123,7 @@ LiteSession::~LiteSession() {
delete input; delete input;
input = nullptr; input = nullptr;
} }
for (auto &item : output_tensor_map_) {
auto output = item.second;
for (auto &output : outputs_) {
if (output == nullptr) { if (output == nullptr) {
continue; continue;
} }
@@ -153,46 +145,28 @@ int LiteSession::InitRuntimeBuffer() {
return RET_OK; return RET_OK;
} }


std::vector<tensor::MSTensor *> LiteSession::GetInputs() const {
std::vector<tensor::MSTensor *> inputs;
inputs.insert(inputs.begin(), inputs_.begin(), inputs_.end());
return inputs;
}

std::vector<tensor::MSTensor *> LiteSession::GetOutputsByNodeName(const std::string &node_name) const {
auto iter = output_node_map_.find(node_name);
if (iter == output_node_map_.end()) {
std::vector<tensor::MSTensor *> empty;
return empty;
Vector<tensor::MSTensor *> LiteSession::GetInputs() const {
Vector<tensor::MSTensor *> inputs;
for (const auto &input : inputs_) {
inputs.push_back(input);
} }
return iter->second;
return inputs;
} }


std::unordered_map<std::string, mindspore::tensor::MSTensor *> LiteSession::GetOutputs() const {
return output_tensor_map_;
Vector<tensor::MSTensor *> LiteSession::GetOutputsByNodeName(const String &node_name) const {
Vector<tensor::MSTensor *> outputs;
return outputs;
} }


std::vector<std::string> LiteSession::GetOutputTensorNames() const {
std::vector<std::string> output_names;
for (const auto &item : output_node_map_) {
for (const auto &output : item.second) {
output_names.emplace_back(output->tensor_name());
}
Vector<String> LiteSession::GetOutputTensorNames() const {
Vector<String> output_names;
for (const auto &output : outputs_) {
output_names.push_back(output->tensor_name());
} }
return output_names; return output_names;
} }


mindspore::tensor::MSTensor *LiteSession::GetOutputByTensorName(const std::string &tensor_name) const {
auto item = output_tensor_map_.find(tensor_name);
if (item == output_tensor_map_.end()) {
return nullptr;
}
return item->second;
}

int LiteSession::Resize(const std::vector<tensor::MSTensor *> &inputs, const std::vector<std::vector<int>> &dims) {
return RET_OK;
}
mindspore::tensor::MSTensor *LiteSession::GetOutputByTensorName(const String &tensor_name) const { return nullptr; }


} // namespace lite } // namespace lite


@@ -219,7 +193,6 @@ session::LiteSession *session::LiteSession::CreateSession(const char *net_buf, s
return session; return session;
} }
} // namespace mindspore } // namespace mindspore

)RAW"; )RAW";


} // namespace mindspore::lite::micro } // namespace mindspore::lite::micro

+ 10
- 25
mindspore/lite/micro/coder/generator/component/const_blocks/mtensor.cc View File

@@ -19,7 +19,6 @@
namespace mindspore::lite::micro { namespace mindspore::lite::micro {


const char *tensor_header = R"RAW( const char *tensor_header = R"RAW(

/** /**
* Copyright 2021 Huawei Technologies Co., Ltd * Copyright 2021 Huawei Technologies Co., Ltd
* *
@@ -40,8 +39,6 @@ const char *tensor_header = R"RAW(
#define MINDSPORE_LITE_MICRO_LIBRARY_SOURCE_TENSOR_H_ #define MINDSPORE_LITE_MICRO_LIBRARY_SOURCE_TENSOR_H_


#include "include/ms_tensor.h" #include "include/ms_tensor.h"
#include <utility>
#include <vector>


namespace mindspore { namespace mindspore {
namespace lite { namespace lite {
@@ -51,7 +48,7 @@ struct QuantArg {
float var_corr{1}; float var_corr{1};
float mean_corr{0}; float mean_corr{0};
bool inited; bool inited;
std::vector<float> clusters{};
Vector<float> clusters{};
int bitNum; int bitNum;
int roundType; int roundType;
int multiplier; int multiplier;
@@ -61,38 +58,35 @@ struct QuantArg {
class MTensor : public mindspore::tensor::MSTensor { class MTensor : public mindspore::tensor::MSTensor {
public: public:
MTensor() = default; MTensor() = default;
MTensor(std::string name, enum TypeId type, std::vector<int32_t> shape)
: tensor_name_(std::move(name)), data_type_(type), shape_(std::move(shape)) {}
MTensor(String name, TypeId type, Vector<int32_t> shape) : tensor_name_(name), data_type_(type), shape_(shape) {}
~MTensor() override; ~MTensor() override;


TypeId data_type() const override { return data_type_; } TypeId data_type() const override { return data_type_; }
std::vector<int> shape() const override { return shape_; }
int DimensionSize(size_t index) const override;
Vector<int> shape() const override { return shape_; }
void set_shape(const Vector<int> &shape) override { shape_ = shape; }
int ElementsNum() const override; int ElementsNum() const override;
size_t Size() const override; size_t Size() const override;
String tensor_name() const override { return tensor_name_; }
void set_tensor_name(const String name) override { tensor_name_ = name; }
void *MutableData() override; void *MutableData() override;
std::string tensor_name() const override { return tensor_name_; }
void set_tensor_name(const std::string name) override { tensor_name_ = name; }
void *data() override { return data_; }
void set_data(void *data) override { data_ = data; } void set_data(void *data) override { data_ = data; }


private: private:
std::string tensor_name_;
String tensor_name_;
TypeId data_type_; TypeId data_type_;
std::vector<int> shape_;
Vector<int> shape_;
void *data_ = nullptr; void *data_ = nullptr;
std::vector<QuantArg> quant_params_;
Vector<QuantArg> quant_params_;
}; };


} // namespace lite } // namespace lite
} // namespace mindspore } // namespace mindspore


#endif // MINDSPORE_LITE_MICRO_LIBRARY_SOURCE_TENSOR_H_ #endif // MINDSPORE_LITE_MICRO_LIBRARY_SOURCE_TENSOR_H_


)RAW"; )RAW";


const char *tensor_source = R"RAW( const char *tensor_source = R"RAW(

/** /**
* Copyright 2021 Huawei Technologies Co., Ltd * Copyright 2021 Huawei Technologies Co., Ltd
* *
@@ -154,14 +148,6 @@ MTensor::~MTensor() {
} }
} }


int MTensor::DimensionSize(const size_t index) const {
int dim_size = -1;
if (index < shape_.size()) {
dim_size = shape_[index];
}
return dim_size;
}

int MTensor::ElementsNum() const { int MTensor::ElementsNum() const {
int elements = 1; int elements = 1;
for (int i : shape_) { for (int i : shape_) {
@@ -183,7 +169,6 @@ void *MTensor::MutableData() {
} }
} // namespace lite } // namespace lite
} // namespace mindspore } // namespace mindspore

)RAW"; )RAW";


} // namespace mindspore::lite::micro } // namespace mindspore::lite::micro

+ 1
- 0
mindspore/lite/micro/coder/generator/generator.cc View File

@@ -111,6 +111,7 @@ int Generator::CodeSessionImplement() {
ofs << g_hwLicense; ofs << g_hwLicense;
ofs << "#include \"session.h\"\n"; ofs << "#include \"session.h\"\n";
ofs << "#include \"net.h\"\n\n"; ofs << "#include \"net.h\"\n\n";
ofs << "#include <new>\n\n";
CodeSessionCompileGraph(ofs, ctx_); CodeSessionCompileGraph(ofs, ctx_);
ofs << session_source; ofs << session_source;
return RET_OK; return RET_OK;


+ 1
- 0
mindspore/lite/micro/coder/operator_library/CMakeLists.txt View File

@@ -60,4 +60,5 @@ endif()


# generate static library # generate static library
add_library(ops STATIC ${OP_FILES}) add_library(ops STATIC ${OP_FILES})
target_compile_definitions(ops PRIVATE NOT_USE_STL)
install(TARGETS ops ARCHIVE DESTINATION ${LIB_PATH}) install(TARGETS ops ARCHIVE DESTINATION ${LIB_PATH})

+ 300
- 0
mindspore/lite/src/common/string.cc View File

@@ -0,0 +1,300 @@
/**
* Copyright 2021 Huawei Technologies Co., Ltd
*
* 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.
*/

#ifdef NOT_USE_STL
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <float.h>
#include <stdint.h>
#include "include/lite_utils.h"

namespace mindspore {
String::String() {
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
buffer_[0] = '\0';
size_ = 0;
}

String::String(size_t count, char ch) {
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (count + 1)));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
memset(buffer_, ch, count);
buffer_[count] = '\0';
size_ = count;
}
String::String(const char *s, size_t count) {
if (s == nullptr) {
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
buffer_[0] = '\0';
size_ = 0;
return;
}
size_t size_s = strlen(s);
if (size_s <= count) {
size_ = size_s;
} else {
size_ = count;
}
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (size_ + 1)));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
strncpy(buffer_, s, size_);
buffer_[size_] = '\0';
}

String::String(const char *s) {
if (s == nullptr) {
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
buffer_[0] = '\0';
size_ = 0;
return;
}
size_ = strlen(s);
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (size_ + 1)));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
memcpy(buffer_, s, size_ + 1);
}

String::String(const String &other) {
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (other.size_ + 1)));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
size_ = other.size_;
memcpy(buffer_, other.buffer_, size_ + 1);
}

String::String(const String &other, size_t pos, size_t count) {
if (pos >= other.size_) {
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
buffer_[0] = '\0';
size_ = 0;
} else {
if (count == npos) {
count = other.size_ - pos;
}
if (pos + count > other.size_) {
size_ = other.size_ - pos;
} else {
size_ = count;
}
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (size_ + 1)));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
strncpy(buffer_, other.buffer_ + pos, size_);
buffer_[size_] = '\0';
}
}

String::~String() { free(buffer_); }

String &String::operator=(const String &str) {
if (this == &str) {
return *this;
}
free(buffer_);
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (str.size_ + 1)));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
size_ = str.size_;
memcpy(buffer_, str.buffer_, size_ + 1);
return *this;
}

String &String::operator=(const char *str) {
free(buffer_);
if (str == nullptr) {
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
buffer_[0] = '\0';
size_ = 0;
return *this;
}
size_t size_s = strlen(str);
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (size_s + 1)));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
size_ = size_s;
memcpy(buffer_, str, size_ + 1);
return *this;
}

char &String::at(size_t pos) {
if (pos >= size_) {
MS_C_EXCEPTION("pos out of range");
}
return buffer_[pos];
}
const char &String::at(size_t pos) const {
if (pos >= size_) {
MS_C_EXCEPTION("pos out of range");
}
return buffer_[pos];
}
char &String::operator[](size_t pos) {
if (pos >= size_) {
MS_C_EXCEPTION("pos out of range");
}
return this->at(pos);
}
const char &String::operator[](size_t pos) const {
if (pos >= size_) {
MS_C_EXCEPTION("pos out of range");
}
return this->at(pos);
}
char *String::data() noexcept { return buffer_; };
const char *String::data() const noexcept { return buffer_; }
const char *String::c_str() const noexcept { return buffer_; }

// capacity
bool String::empty() const noexcept { return size_ == 0; }
size_t String::size() const noexcept { return size_; }
size_t String::length() const noexcept { return size_; }

// operations
void String::clear() noexcept {
free(buffer_);
buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
if (buffer_ == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
buffer_[0] = '\0';
size_ = 0;
}

String &String::operator+(const String &str) {
(*this) += str;
return *this;
}

String &String::operator+=(const String &str) {
size_t new_size = size_ + str.size_;
char *tmp = reinterpret_cast<char *>(malloc(sizeof(char) * (new_size + 1)));
if (tmp == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
memcpy(tmp, this->buffer_, size_ + 1);
strncat(tmp, str.buffer_, str.size_);
tmp[new_size] = '\0';
free(buffer_);
buffer_ = tmp;
size_ = new_size;
return *this;
}

String &String::operator+=(const char *str) {
if (str == nullptr) {
return *this;
}
size_t str_size = strlen(str);
size_t new_size = size_ + str_size;
char *tmp = reinterpret_cast<char *>(malloc(sizeof(char) * (new_size + 1)));
if (tmp == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
memcpy(tmp, this->buffer_, size_ + 1);
strncat(tmp, str, str_size);
tmp[new_size] = '\0';
free(buffer_);
buffer_ = tmp;
size_ = new_size;
return *this;
}

String &String::operator+=(const char ch) {
char *tmp = reinterpret_cast<char *>(malloc(sizeof(char) * (size_ + 2)));
if (tmp == nullptr) {
MS_C_EXCEPTION("malloc data failed");
}
memcpy(tmp, this->buffer_, size_ + 1);
tmp[size_] = ch;
tmp[size_ + 1] = '\0';
free(buffer_);
buffer_ = tmp;
size_ += 1;
return *this;
}

String &String::append(size_t count, const char ch) {
(*this) += ch;
return *this;
}
String &String::append(const String &str) {
(*this) += str;
return *this;
}
String &String::append(const char *str) {
if (str == nullptr) {
return *this;
}
(*this) += str;
return *this;
}

int String::compare(const String &str) const { return strcmp(buffer_, str.buffer_); }
int String::compare(const char *str) const { return strcmp(buffer_, str); }

String String::substr(size_t pos, size_t count) const { return String(*this, pos, count); }

String operator+(const String &str1, const char *str2) {
String str = str1;
str += str2;
return str;
}

String operator+(const char *str1, const String &str2) {
String str = str2;
str += str1;
return str;
}

String to_String(int32_t value) {
char tmp[sizeof(int32_t) * 4];
snprintf(tmp, sizeof(int32_t) * 4, "%d", value);
return String(tmp, strlen(tmp));
}

String to_String(float value) {
char tmp[FLT_MAX_10_EXP + 20];
snprintf(tmp, FLT_MAX_10_EXP + 20, "%f", value);
return String(tmp, strlen(tmp));
}
} // namespace mindspore
#endif // NOT_USE_STL

Loading…
Cancel
Save