bmv2
Designing your own switch target with bmv2
tables.h
1 /* Copyright 2013-present Barefoot Networks, Inc.
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 /*
17  * Antonin Bas (antonin@barefootnetworks.com)
18  *
19  */
20 
21 #ifndef BM_BM_SIM_TABLES_H_
22 #define BM_BM_SIM_TABLES_H_
23 
24 #include <memory>
25 #include <string>
26 #include <utility>
27 
28 #include "control_flow.h"
29 #include "match_tables.h"
30 
31 namespace bm {
32 
33 // from http://stackoverflow.com/questions/87372/check-if-a-class-has-a-member-function-of-a-given-signature
34 
35 template<typename T>
36 struct HasFactoryMethod {
37  using Signature = std::unique_ptr<T> (*)(
38  const std::string &, const std::string &,
39  p4object_id_t, size_t, const MatchKeyBuilder &,
40  LookupStructureFactory *,
41  bool, bool);
42 
43  template <typename U, Signature> struct SFINAE {};
44  template<typename U> static char Test(SFINAE<U, U::create>*);
45  template<typename U> static int Test(...);
46  static const bool value = sizeof(Test<T>(nullptr)) == sizeof(char);
47 };
48 
49 class MatchActionTable : public ControlFlowNode {
50  public:
51  MatchActionTable(const std::string &name, p4object_id_t id,
52  std::unique_ptr<MatchTableAbstract> match_table);
53 
54  const ControlFlowNode *operator()(Packet *pkt) const override;
55 
56  MatchTableAbstract *get_match_table() { return match_table.get(); }
57 
58  public:
59  template <typename MT>
60  static std::unique_ptr<MatchActionTable> create_match_action_table(
61  const std::string &match_type,
62  const std::string &name, p4object_id_t id,
63  size_t size, const MatchKeyBuilder &match_key_builder,
64  bool with_counters, bool with_ageing,
65  LookupStructureFactory *lookup_factory) {
66  static_assert(
67  std::is_base_of<MatchTableAbstract, MT>::value,
68  "incorrect template, needs to be a subclass of MatchTableAbstract");
69 
70  static_assert(
71  HasFactoryMethod<MT>::value,
72  "template class needs to have a create() static factory method");
73 
74  std::unique_ptr<MT> match_table = MT::create(
75  match_type, name, id, size, match_key_builder,
76  lookup_factory, with_counters, with_ageing);
77 
78  return std::unique_ptr<MatchActionTable>(
79  new MatchActionTable(name, id, std::move(match_table)));
80  }
81 
82  private:
83  std::unique_ptr<MatchTableAbstract> match_table;
84 };
85 
86 } // namespace bm
87 
88 #endif // BM_BM_SIM_TABLES_H_