Home | History | Annotate | Download | only in public
      1 // Copyright 2015 The Gemmlowp 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 // map.h: a minimalist view-existing-buffer-as-a-matrix class,
     16 // which is how gemmlowp interfaces with external matrix data.
     17 
     18 #ifndef GEMMLOWP_PUBLIC_MAP_H_
     19 #define GEMMLOWP_PUBLIC_MAP_H_
     20 
     21 #include "../internal/common.h"
     22 
     23 namespace gemmlowp {
     24 
     25 // The two storage orders allowed to map buffers as matrices: ColMajor
     26 // means column-major, RowMajor means row-major.
     27 enum class MapOrder { ColMajor, RowMajor };
     28 
     29 // A MatrixMap is a view of an existing buffer as a matrix. It does not own
     30 // the buffer.
     31 template <typename tScalar, MapOrder tOrder>
     32 class MatrixMap {
     33  public:
     34   typedef tScalar Scalar;
     35   static const MapOrder kOrder = tOrder;
     36 
     37  protected:
     38   Scalar* data_;  // not owned.
     39   int rows_, cols_, stride_;
     40 
     41  public:
     42   MatrixMap() : data_(nullptr), rows_(0), cols_(0), stride_(0) {}
     43   MatrixMap(Scalar* data, int rows, int cols)
     44       : data_(data),
     45         rows_(rows),
     46         cols_(cols),
     47         stride_(kOrder == MapOrder::ColMajor ? rows : cols) {}
     48   MatrixMap(Scalar* data, int rows, int cols, int stride)
     49       : data_(data), rows_(rows), cols_(cols), stride_(stride) {}
     50   MatrixMap(const MatrixMap& other)
     51       : data_(other.data_),
     52         rows_(other.rows_),
     53         cols_(other.cols_),
     54         stride_(other.stride_) {}
     55 
     56   int rows() const { return rows_; }
     57   int cols() const { return cols_; }
     58   int stride() const { return stride_; }
     59   int rows_stride() const { return kOrder == MapOrder::ColMajor ? 1 : stride_; }
     60   int cols_stride() const { return kOrder == MapOrder::RowMajor ? 1 : stride_; }
     61   Scalar* data() const { return data_; }
     62   Scalar* data(int row, int col) const {
     63     return data_ + row * rows_stride() + col * cols_stride();
     64   }
     65   Scalar& operator()(int row, int col) const { return *data(row, col); }
     66 
     67   MatrixMap block(int start_row, int start_col, int block_rows,
     68                   int block_cols) const {
     69     assert(start_row >= 0);
     70     assert(start_row + block_rows <= rows_);
     71     assert(start_col >= 0);
     72     assert(start_col + block_cols <= cols_);
     73 
     74     return MatrixMap(data(start_row, start_col), block_rows, block_cols,
     75                      stride_);
     76   }
     77 };
     78 
     79 enum class VectorShape { Col, Row };
     80 
     81 // A VectorMap is a view of an existing buffer as a vector. It does not own
     82 // the buffer.
     83 template <typename tScalar, VectorShape tShape>
     84 class VectorMap {
     85  public:
     86   typedef tScalar Scalar;
     87   static const VectorShape kShape = tShape;
     88 
     89  protected:
     90   Scalar* data_;  // not owned.
     91   int size_;
     92 
     93  public:
     94   VectorMap() : data_(nullptr), size_(0) {}
     95   VectorMap(Scalar* data, int size) : data_(data), size_(size) {}
     96   VectorMap(const VectorMap& other) : data_(other.data_), size_(other.size_) {}
     97 
     98   int size() const { return size_; }
     99   Scalar* data() const { return data_; }
    100   Scalar* data(int index) const { return data_ + index; }
    101   Scalar& operator()(int index) const { return *data(index); }
    102 
    103   VectorMap block(int start, int len) const {
    104     assert(start >= 0);
    105     assert(start + len <= size_);
    106 
    107     return VectorMap(data(start), len);
    108   }
    109 };
    110 
    111 // A VectorDup is a (duplicated value) vector where all components are the same.
    112 template <typename tScalar, VectorShape tShape>
    113 class VectorDup {
    114  public:
    115   typedef tScalar Scalar;
    116   static const VectorShape kShape = tShape;
    117 
    118  protected:
    119   Scalar data_;
    120   int size_;
    121 
    122  public:
    123   VectorDup() : data_(0), size_(0) {}
    124   VectorDup(Scalar data, int size) : data_(data), size_(size) {}
    125   VectorDup(const VectorDup& other) : data_(other.data_), size_(other.size_) {}
    126 
    127   int size() const { return size_; }
    128   Scalar& operator()(int) const { return data_; }
    129 
    130   VectorDup block(int start, int len) const {
    131     assert(start >= 0);
    132     assert(start + len <= size_);
    133 
    134     return VectorDup(data_, len);
    135   }
    136 };
    137 
    138 }  // namespace gemmlowp
    139 
    140 #endif  // GEMMLOWP_PUBLIC_MAP_H_
    141