• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /**
2  * Copyright 2020 Huawei Technologies Co., Ltd
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef MINDSPORE_LITE_INCLUDE_LITE_UTILS_H_
18 #define MINDSPORE_LITE_INCLUDE_LITE_UTILS_H_
19 
20 #ifndef NOT_USE_STL
21 #include <vector>
22 #include <string>
23 #include <memory>
24 #include <functional>
25 #else
26 #include <stdint.h>
27 #include <stdlib.h>
28 #include <string.h>
29 #include <stddef.h>
30 #include <stdio.h>
31 #include <float.h>
32 #include <new>
33 #endif  // NOT_USE_STL
34 
35 #ifndef MS_API
36 #ifdef _WIN32
37 #define MS_API __declspec(dllexport)
38 #else
39 #define MS_API __attribute__((visibility("default")))
40 #endif
41 #endif
42 
43 namespace mindspore {
44 namespace schema {
45 struct Tensor;
46 }  // namespace schema
47 
48 namespace tensor {
49 class MSTensor;
50 }  // namespace tensor
51 
52 namespace lite {
53 struct DeviceContext;
54 struct LiteQuantParam;
55 }  // namespace lite
56 
57 #ifdef NOT_USE_STL
58 #define MS_C_EXCEPTION(...) exit(1)
59 
60 class String {
61  public:
String()62   String() {
63     buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
64     if (buffer_ == nullptr) {
65       MS_C_EXCEPTION("malloc data failed");
66     }
67     buffer_[0] = '\0';
68     size_ = 0;
69   }
70 
String(size_t count,char ch)71   String(size_t count, char ch) {
72     buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (count + 1)));
73     if (buffer_ == nullptr) {
74       MS_C_EXCEPTION("malloc data failed");
75     }
76     memset(buffer_, ch, count);
77     buffer_[count] = '\0';
78     size_ = count;
79   }
80 
String(const char * s,size_t count)81   String(const char *s, size_t count) {
82     if (s == nullptr) {
83       buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
84       if (buffer_ == nullptr) {
85         MS_C_EXCEPTION("malloc data failed");
86       }
87       buffer_[0] = '\0';
88       size_ = 0;
89       return;
90     }
91     size_t size_s = strlen(s);
92     if (size_s <= count) {
93       size_ = size_s;
94     } else {
95       size_ = count;
96     }
97     buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (size_ + 1)));
98     if (buffer_ == nullptr) {
99       MS_C_EXCEPTION("malloc data failed");
100     }
101     strncpy(buffer_, s, size_);
102     buffer_[size_] = '\0';
103   }
104 
String(const char * s)105   explicit String(const char *s) {
106     if (s == nullptr) {
107       buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
108       if (buffer_ == nullptr) {
109         MS_C_EXCEPTION("malloc data failed");
110       }
111       buffer_[0] = '\0';
112       size_ = 0;
113       return;
114     }
115     size_ = strlen(s);
116     buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (size_ + 1)));
117     if (buffer_ == nullptr) {
118       MS_C_EXCEPTION("malloc data failed");
119     }
120     memcpy(buffer_, s, size_ + 1);
121   }
122 
String(const String & other)123   String(const String &other) {
124     buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (other.size_ + 1)));
125     if (buffer_ == nullptr) {
126       MS_C_EXCEPTION("malloc data failed");
127     }
128     size_ = other.size_;
129     memcpy(buffer_, other.buffer_, size_ + 1);
130   }
131 
132   String(const String &other, size_t pos, size_t count = npos) {
133     if (pos >= other.size_) {
134       buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
135       if (buffer_ == nullptr) {
136         MS_C_EXCEPTION("malloc data failed");
137       }
138       buffer_[0] = '\0';
139       size_ = 0;
140     } else {
141       if (count == npos) {
142         count = other.size_ - pos;
143       }
144       if (pos + count > other.size_) {
145         size_ = other.size_ - pos;
146       } else {
147         size_ = count;
148       }
149       buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (size_ + 1)));
150       if (buffer_ == nullptr) {
151         MS_C_EXCEPTION("malloc data failed");
152       }
153       strncpy(buffer_, other.buffer_ + pos, size_);
154       buffer_[size_] = '\0';
155     }
156   }
157 
~String()158   ~String() { free(buffer_); }
159 
160   String &operator=(const String &str) {
161     if (this == &str) {
162       return *this;
163     }
164     free(buffer_);
165     buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (str.size_ + 1)));
166     if (buffer_ == nullptr) {
167       MS_C_EXCEPTION("malloc data failed");
168     }
169     size_ = str.size_;
170     memcpy(buffer_, str.buffer_, size_ + 1);
171     return *this;
172   }
173 
174   String &operator=(const char *str) {
175     free(buffer_);
176     if (str == nullptr) {
177       buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
178       if (buffer_ == nullptr) {
179         MS_C_EXCEPTION("malloc data failed");
180       }
181       buffer_[0] = '\0';
182       size_ = 0;
183       return *this;
184     }
185     size_t size_s = strlen(str);
186     buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * (size_s + 1)));
187     if (buffer_ == nullptr) {
188       MS_C_EXCEPTION("malloc data failed");
189     }
190     size_ = size_s;
191     memcpy(buffer_, str, size_ + 1);
192     return *this;
193   }
194 
at(size_t pos)195   char &at(size_t pos) {
196     if (pos >= size_) {
197       MS_C_EXCEPTION("pos out of range");
198     }
199     return buffer_[pos];
200   }
201 
at(size_t pos)202   const char &at(size_t pos) const {
203     if (pos >= size_) {
204       MS_C_EXCEPTION("pos out of range");
205     }
206     return buffer_[pos];
207   }
208 
209   inline char &operator[](size_t pos) {
210     if (pos >= size_) {
211       MS_C_EXCEPTION("pos out of range");
212     }
213     return this->at(pos);
214   }
215 
216   inline const char &operator[](size_t pos) const {
217     if (pos >= size_) {
218       MS_C_EXCEPTION("pos out of range");
219     }
220     return this->at(pos);
221   }
222 
data()223   char *data() noexcept { return buffer_; }
data()224   const char *data() const noexcept { return buffer_; }
c_str()225   const char *c_str() const noexcept { return buffer_; }
226 
227   // capacity
empty()228   bool empty() const noexcept { return size_ == 0; }
size()229   size_t size() const noexcept { return size_; }
length()230   size_t length() const noexcept { return size_; }
231 
232   // operations
clear()233   void clear() noexcept {
234     free(buffer_);
235     buffer_ = reinterpret_cast<char *>(malloc(sizeof(char) * 1));
236     if (buffer_ == nullptr) {
237       MS_C_EXCEPTION("malloc data failed");
238     }
239     buffer_[0] = '\0';
240     size_ = 0;
241   }
242 
append(size_t count,const char ch)243   String &append(size_t count, const char ch) {
244     (*this) += ch;
245     return *this;
246   }
247 
append(const String & str)248   String &append(const String &str) {
249     (*this) += str;
250     return *this;
251   }
252 
append(const char * str)253   String &append(const char *str) {
254     if (str == nullptr) {
255       return *this;
256     }
257     (*this) += str;
258     return *this;
259   }
260 
261   String &operator+(const String &str) {
262     (*this) += str;
263     return *this;
264   }
265 
266   String &operator+=(const String &str) {
267     size_t new_size = size_ + str.size_;
268     char *tmp = reinterpret_cast<char *>(malloc(sizeof(char) * (new_size + 1)));
269     if (tmp == nullptr) {
270       MS_C_EXCEPTION("malloc data failed");
271     }
272     memcpy(tmp, this->buffer_, size_ + 1);
273     strncat(tmp, str.buffer_, str.size_);
274     tmp[new_size] = '\0';
275     free(buffer_);
276     buffer_ = tmp;
277     size_ = new_size;
278     return *this;
279   }
280 
281   String &operator+=(const char *str) {
282     if (str == nullptr) {
283       return *this;
284     }
285     size_t str_size = strlen(str);
286     size_t new_size = size_ + str_size;
287     char *tmp = reinterpret_cast<char *>(malloc(sizeof(char) * (new_size + 1)));
288     if (tmp == nullptr) {
289       MS_C_EXCEPTION("malloc data failed");
290     }
291     memcpy(tmp, this->buffer_, size_ + 1);
292     strncat(tmp, str, str_size);
293     tmp[new_size] = '\0';
294     free(buffer_);
295     buffer_ = tmp;
296     size_ = new_size;
297     return *this;
298   }
299 
300   String &operator+=(const char ch) {
301     char *tmp = reinterpret_cast<char *>(malloc(sizeof(char) * (size_ + 2)));
302     if (tmp == nullptr) {
303       MS_C_EXCEPTION("malloc data failed");
304     }
305     memcpy(tmp, this->buffer_, size_ + 1);
306     tmp[size_] = ch;
307     tmp[size_ + 1] = '\0';
308     free(buffer_);
309     buffer_ = tmp;
310     size_ += 1;
311     return *this;
312   }
313 
compare(const String & str)314   int compare(const String &str) const { return strcmp(buffer_, str.buffer_); }
compare(const char * str)315   int compare(const char *str) const { return strcmp(buffer_, str); }
316 
317   String substr(size_t pos = 0, size_t count = npos) const { return String(*this, pos, count); }
318 
319   static const size_t npos = -1;
320 
321  private:
322   size_t size_;
323   char *buffer_;
324 };
325 
326 inline String operator+(const String &lhs, const char *rhs) {
327   String str = lhs;
328   str += rhs;
329   return str;
330 }
331 
332 inline String operator+(const char *lhs, const String &rhs) {
333   String str = rhs;
334   str += lhs;
335   return str;
336 }
337 
338 inline bool operator!=(const String &lhs, const String &rhs) { return lhs.compare(rhs) != 0; }
339 inline bool operator==(const String &lhs, const String &rhs) { return lhs.compare(rhs) == 0; }
340 inline bool operator==(const String &lhs, const char *rhs) { return lhs.compare(rhs) == 0; }
341 inline bool operator==(const char *lhs, const String &rhs) { return rhs.compare(lhs) == 0; }
342 
to_String(int32_t value)343 inline String to_String(int32_t value) {
344   char tmp[sizeof(int32_t) * 4];
345   snprintf(tmp, sizeof(int32_t) * 4, "%d", value);
346   return String(tmp, strlen(tmp));
347 }
348 
to_String(float value)349 inline String to_String(float value) {
350   char tmp[FLT_MAX_10_EXP + 20];
351   snprintf(tmp, FLT_MAX_10_EXP + 20, "%f", value);
352   return String(tmp, strlen(tmp));
353 }
354 
355 #define DEFAULT_CAPACITY 4
356 #define MIN(x, y) ((x < y) ? (x) : (y))
357 template <typename T>
358 class Vector {
359  public:
Vector()360   Vector() {
361     size_ = 0;
362     capacity_ = DEFAULT_CAPACITY;
363     elem_size_ = sizeof(T);
364     data_ = nullptr;
365   }
366 
Vector(size_t size)367   explicit Vector(size_t size) {
368     size_ = size;
369     elem_size_ = sizeof(T);
370     capacity_ = (size == 0 ? DEFAULT_CAPACITY : size);
371     data_ = new (std::nothrow) T[capacity_];
372     if (data_ == nullptr) {
373       MS_C_EXCEPTION("malloc data failed");
374     }
375   }
376 
Vector(size_t size,const T & value)377   Vector(size_t size, const T &value) {
378     size_ = size;
379     elem_size_ = sizeof(T);
380     capacity_ = (size == 0 ? DEFAULT_CAPACITY : size);
381     data_ = new (std::nothrow) T[capacity_];
382     if (data_ == nullptr) {
383       MS_C_EXCEPTION("malloc data failed");
384     }
385     for (int i = 0; i < static_cast<int>(size_); ++i) {
386       data_[i] = value;
387     }
388   }
389 
Vector(const Vector<T> & vec)390   Vector(const Vector<T> &vec) {
391     size_ = vec.size_;
392     elem_size_ = sizeof(T);
393     capacity_ = vec.capacity_;
394     data_ = new (std::nothrow) T[capacity_];
395     if (data_ == nullptr) {
396       MS_C_EXCEPTION("malloc data failed");
397     }
398     for (int i = 0; i < static_cast<int>(size_); ++i) {
399       data_[i] = vec.data_[i];
400     }
401   }
402 
~Vector()403   ~Vector() {
404     if (data_ != nullptr) {
405       delete[] data_;
406     }
407   }
408 
clear()409   void clear() {
410     size_ = 0;
411     if (data_ != nullptr) {
412       delete[] data_;
413       data_ = nullptr;
414     }
415   }
416 
push_back(const T & elem)417   void push_back(const T &elem) {
418     if (data_ == nullptr) {
419       data_ = new (std::nothrow) T[capacity_];
420       if (data_ == nullptr) {
421         MS_C_EXCEPTION("malloc data failed");
422       }
423     } else if (size_ == capacity_) {
424       resize(size_ + 1);
425       --size_;
426     }
427     data_[size_] = elem;
428     ++size_;
429   }
430 
push_back(T && elem)431   void push_back(T &&elem) {
432     if (data_ == nullptr) {
433       data_ = new (std::nothrow) T[capacity_];
434       if (data_ == nullptr) {
435         MS_C_EXCEPTION("malloc data failed");
436       }
437     } else if (size_ == capacity_) {
438       resize(size_ + 1);
439       --size_;
440     }
441     data_[size_] = elem;
442     ++size_;
443   }
444 
pop_back()445   void pop_back() {
446     if (size_ > 0) {
447       --size_;
448     } else {
449       MS_C_EXCEPTION("Index is out of range!");
450     }
451   }
452 
insert(const T & elem,size_t index)453   void insert(const T &elem, size_t index) {
454     if (index <= size_) {
455       ++size_;
456       if (size_ > capacity_) {
457         resize(size_);
458       }
459       if (index == size_ - 1) {
460         push_back(elem);
461       } else {
462         for (int i = static_cast<int>(size_) - 1; i > static_cast<int>(index); --i) {
463           data_[i + 1] = data_[i];
464         }
465         data_[index] = elem;
466       }
467     } else {
468       MS_C_EXCEPTION("Input index is out of range!");
469     }
470   }
471 
begin()472   T *begin() { return data_; }
473 
begin()474   const T *begin() const { return data_; }
475 
end()476   T *end() { return data_ + size_; }
477 
end()478   const T *end() const { return data_ + size_; }
479 
front()480   T &front() {
481     if (size_ > 0) {
482       return data_[0];
483     }
484     MS_C_EXCEPTION("Index is out of range!");
485   }
486 
front()487   const T &front() const {
488     if (size_ > 0) {
489       return data_[0];
490     }
491     MS_C_EXCEPTION("Index is out of range!");
492   }
493 
back()494   T &back() {
495     if (size_ > 0) {
496       return data_[size_ - 1];
497     }
498     MS_C_EXCEPTION("Index is out of range!");
499   }
500 
back()501   const T &back() const {
502     if (size_ > 0) {
503       return data_[size_ - 1];
504     }
505     MS_C_EXCEPTION("Index is out of range!");
506   }
507 
at(size_t index)508   T &at(size_t index) {
509     if (index < size_) {
510       return data_[index];
511     }
512     MS_C_EXCEPTION("Input index is out of range!");
513   }
514 
at(size_t index)515   const T &at(size_t index) const {
516     if (index < size_) {
517       return data_[index];
518     }
519     MS_C_EXCEPTION("Input index is out of range!");
520   }
521 
522   T &operator[](size_t index) {
523     if (index < size_) {
524       return data_[index];
525     }
526     MS_C_EXCEPTION("Input index is out of range!");
527   }
528 
529   const T &operator[](size_t index) const {
530     if (index < size_) {
531       return data_[index];
532     }
533     MS_C_EXCEPTION("Input index is out of range!");
534   }
535 
data()536   T *data() { return data_; }
537 
data()538   const T *data() const { return data_; }
539 
size()540   size_t size() const { return size_; }
541 
capacity()542   size_t capacity() const { return capacity_; }
543 
empty()544   bool empty() const { return size_ == 0; }
545 
erase(size_t index)546   void erase(size_t index) {
547     if (index == size_ - 1) {
548       --size_;
549     } else if (index < size_) {
550       for (int i = index; i < static_cast<int>(size_); ++i) {
551         data_[i] = data_[i + 1];
552       }
553       --size_;
554     } else {
555       MS_C_EXCEPTION("Input index is out of range!");
556     }
557   }
558 
resize(size_t size)559   void resize(size_t size) {
560     while (size > capacity_) {
561       capacity_ *= 2;
562     }
563     T *tmp = data_;
564     data_ = new (std::nothrow) T[capacity_];
565     if (data_ == nullptr) {
566       MS_C_EXCEPTION("malloc data failed");
567     }
568     for (int i = 0; i < MIN(static_cast<int>(size), static_cast<int>(size_)); ++i) {
569       data_[i] = tmp[i];
570     }
571     size_ = size;
572     delete[] tmp;
573   }
574 
reserve(size_t capacity)575   void reserve(size_t capacity) {
576     if (capacity > capacity_) {
577       capacity_ = capacity;
578     }
579   }
580 
581   Vector<T> &operator=(const Vector<T> &vec) {
582     if (this == &vec) {
583       return *this;
584     }
585     size_ = vec.size_;
586     elem_size_ = sizeof(T);
587     capacity_ = vec.capacity_;
588     data_ = new (std::nothrow) T[capacity_];
589     if (data_ == nullptr) {
590       MS_C_EXCEPTION("malloc data failed");
591     }
592     for (int i = 0; i < static_cast<int>(size_); ++i) {
593       data_[i] = vec.data_[i];
594     }
595     return *this;
596   }
597 
598  private:
599   size_t size_;
600   size_t elem_size_;
601   size_t capacity_;
602   T *data_;
603 };
604 using TensorPtrVector = Vector<mindspore::schema::Tensor *>;
605 using Uint32Vector = Vector<uint32_t>;
606 class Allocator;
607 using AllocatorPtr = void *;
608 class Delegate;
609 using DelegatePtr = void *;
610 using DeviceContextVector = Vector<lite::DeviceContext>;
611 using KernelCallBack = void (*)(void *, void *);
612 #else
613 /// \brief Allocator defined a memory pool for malloc memory and free memory dynamically.
614 ///
615 /// \note List public class and interface for reference.
616 class Allocator;
617 using AllocatorPtr = std::shared_ptr<Allocator>;
618 
619 class Delegate;
620 using DelegatePtr = std::shared_ptr<Delegate>;
621 
622 using TensorPtrVector = std::vector<void *>;
623 using Uint32Vector = std::vector<uint32_t>;
624 template <typename T>
625 using Vector = std::vector<T>;
626 
627 template <typename T>
to_string(T t)628 inline std::string to_string(T t) {
629   return std::to_string(t);
630 }
631 
632 namespace tensor {
633 using String = std::string;
634 }  // namespace tensor
635 
636 namespace session {
637 using String = std::string;
638 }  // namespace session
639 
640 /// \brief CallBackParam defined input arguments for callBack function.
641 struct CallBackParam {
642   session::String node_name; /**< node name argument */
643   session::String node_type; /**< node type argument */
644 };
645 
646 struct GPUCallBackParam : CallBackParam {
647   double execute_time{-1.f};
648 };
649 
650 /// \brief KernelCallBack defined the function pointer for callBack.
651 using KernelCallBack = std::function<bool(Vector<tensor::MSTensor *> inputs, Vector<tensor::MSTensor *> outputs,
652                                           const CallBackParam &opInfo)>;
653 
654 namespace lite {
655 using String = std::string;
656 using DeviceContextVector = std::vector<DeviceContext>;
657 
658 /// \brief Set data of MSTensor from string vector.
659 ///
660 /// \param[in] input string vector.
661 /// \param[out] MSTensor.
662 ///
663 /// \return STATUS as an error code of this interface, STATUS is defined in errorcode.h.
664 int MS_API StringsToMSTensor(const Vector<String> &inputs, tensor::MSTensor *tensor);
665 
666 /// \brief Get string vector from MSTensor.
667 /// \param[in] MSTensor.
668 /// \return string vector.
669 Vector<String> MS_API MSTensorToStrings(const tensor::MSTensor *tensor);
670 }  // namespace lite
671 #endif  // NOT_USE_STL
672 }  // namespace mindspore
673 #endif  // MINDSPORE_LITE_INCLUDE_LITE_UTILS_H_
674