OpenSDN source code
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
t_scope.h
Go to the documentation of this file.
1 /*
2  * Licensed to the Apache Software Foundation (ASF) under one
3  * or more contributor license agreements. See the NOTICE file
4  * distributed with this work for additional information
5  * regarding copyright ownership. The ASF licenses this file
6  * to you under the Apache License, Version 2.0 (the
7  * "License"); you may not use this file except in compliance
8  * with the License. You may obtain a copy of the License at
9  *
10  * http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing,
13  * software distributed under the License is distributed on an
14  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15  * KIND, either express or implied. See the License for the
16  * specific language governing permissions and limitations
17  * under the License.
18  *
19  * Copyright 2006-2017 The Apache Software Foundation.
20  * https://github.com/apache/thrift
21  */
22 
23 #ifndef T_SCOPE_H
24 #define T_SCOPE_H
25 
26 #include <map>
27 #include <string>
28 #include <sstream>
29 
30 #include "t_type.h"
31 #include "t_service.h"
32 #include "t_const.h"
33 #include "t_const_value.h"
34 #include "t_base_type.h"
35 #include "t_map.h"
36 #include "t_list.h"
37 #ifdef SANDESH
38 #include "t_sandesh.h"
39 #endif
40 
48 class t_scope {
49  public:
50  t_scope() {}
51 
52  void add_type(std::string name, t_type* type) {
53  types_[name] = type;
54  }
55 
56  t_type* get_type(std::string name) {
57  return types_[name];
58  }
59 
60  void add_service(std::string name, t_service* service) {
61  services_[name] = service;
62  }
63 
64  t_service* get_service(std::string name) {
65  return services_[name];
66  }
67 
68 #ifdef SANDESH
69  void add_sandesh(std::string name, t_sandesh* sandesh) {
70  sandeshs_[name] = sandesh;
71  }
72 
73  t_sandesh* get_sandesh(std::string name) {
74  return sandeshs_[name];
75  }
76 #endif
77 
78  void add_constant(std::string name, t_const* constant) {
79  if (constants_.find(name) != constants_.end()) {
80  throw "Enum " + name + " is already defined!";
81  } else {
82  constants_[name] = constant;
83  }
84  }
85 
86  t_const* get_constant(std::string name) {
87  return constants_[name];
88  }
89 
90  void print() {
91  std::map<std::string, t_type*>::iterator iter;
92  for (iter = types_.begin(); iter != types_.end(); ++iter) {
93  printf("%s => %s\n",
94  iter->first.c_str(),
95  iter->second->get_name().c_str());
96  }
97  }
98 
99  void resolve_const_value(t_const_value* const_val, t_type* ttype) {
100  if (ttype->is_map()) {
101  const std::map<t_const_value*, t_const_value*>& map = const_val->get_map();
102  std::map<t_const_value*, t_const_value*>::const_iterator v_iter;
103  for (v_iter = map.begin(); v_iter != map.end(); ++v_iter) {
104  resolve_const_value(v_iter->first, ((t_map*)ttype)->get_key_type());
105  resolve_const_value(v_iter->second, ((t_map*)ttype)->get_val_type());
106  }
107  } else if (ttype->is_list() || ttype->is_set()) {
108  const std::vector<t_const_value*>& val = const_val->get_list();
109  std::vector<t_const_value*>::const_iterator v_iter;
110  for (v_iter = val.begin(); v_iter != val.end(); ++v_iter) {
111  resolve_const_value((*v_iter), ((t_list*)ttype)->get_elem_type());
112  }
113  } else if (ttype->is_struct()) {
114  t_struct* tstruct = (t_struct*)ttype;
115  const std::map<t_const_value*, t_const_value*>& map = const_val->get_map();
116  std::map<t_const_value*, t_const_value*>::const_iterator v_iter;
117  for (v_iter = map.begin(); v_iter != map.end(); ++v_iter) {
118  t_field* field = tstruct->get_field_by_name(v_iter->first->get_string());
119  if (field == NULL) {
120  throw "No field named \"" + v_iter->first->get_string() + "\" was found in struct of type \"" + tstruct->get_name() + "\"";
121  }
122  resolve_const_value(v_iter->second, field->get_type());
123  }
124  } else if (const_val->get_type() == t_const_value::CV_IDENTIFIER) {
125  if (ttype->is_enum()) {
126  const_val->set_enum((t_enum*)ttype);
127  } else {
128  t_const* constant = get_constant(const_val->get_identifier());
129  if (constant == NULL) {
130  throw "No enum value or constant found named \"" + const_val->get_identifier() + "\"!";
131  }
132 
133  // Resolve typedefs to the underlying type
134  t_type* const_type = constant->get_type()->get_true_type();
135 
136  if (const_type->is_base_type()) {
137  switch (((t_base_type*)const_type)->get_base()) {
143  const_val->set_integer(constant->get_value()->get_integer());
144  break;
146  const_val->set_string(constant->get_value()->get_string());
147  break;
149  const_val->set_double(constant->get_value()->get_double());
150  break;
152  throw "Constants cannot be of type VOID";
153 #ifdef SANDESH
154  case t_base_type::TYPE_U16:
155  case t_base_type::TYPE_U32:
156  case t_base_type::TYPE_U64:
157  const_val->set_integer(constant->get_value()->get_integer());
158  break;
159  case t_base_type::TYPE_STATIC_CONST_STRING:
160  case t_base_type::TYPE_XML:
161  const_val->set_string(constant->get_value()->get_string());
162  break;
163  case t_base_type::TYPE_SANDESH_SYSTEM:
164  break;
165  case t_base_type::TYPE_SANDESH_REQUEST:
166  break;
167  case t_base_type::TYPE_SANDESH_RESPONSE:
168  break;
169  case t_base_type::TYPE_SANDESH_TRACE:
170  break;
171  case t_base_type::TYPE_SANDESH_TRACE_OBJECT:
172  break;
173  case t_base_type::TYPE_SANDESH_BUFFER:
174  break;
175  case t_base_type::TYPE_SANDESH_UVE:
176  break;
177  case t_base_type::TYPE_SANDESH_DYNAMIC_UVE:
178  break;
179  case t_base_type::TYPE_SANDESH_OBJECT:
180  break;
181  case t_base_type::TYPE_SANDESH_FLOW:
182  break;
183  case t_base_type::TYPE_SANDESH_SESSION:
184  break;
185 #endif
186  }
187  } else if (const_type->is_map()) {
188  const std::map<t_const_value*, t_const_value*>& map = constant->get_value()->get_map();
189  std::map<t_const_value*, t_const_value*>::const_iterator v_iter;
190 
191  const_val->set_map();
192  for (v_iter = map.begin(); v_iter != map.end(); ++v_iter) {
193  const_val->add_map(v_iter->first, v_iter->second);
194  }
195  } else if (const_type->is_list()) {
196  const std::vector<t_const_value*>& val = constant->get_value()->get_list();
197  std::vector<t_const_value*>::const_iterator v_iter;
198 
199  const_val->set_list();
200  for (v_iter = val.begin(); v_iter != val.end(); ++v_iter) {
201  const_val->add_list(*v_iter);
202  }
203  }
204  }
205  } else if (ttype->is_enum()) {
206  // enum constant with non-identifier value. set the enum and find the
207  // value's name.
208  t_enum* tenum = (t_enum*)ttype;
209  t_enum_value* enum_value = tenum->get_constant_by_value(const_val->get_integer());
210  if (enum_value == NULL) {
211  std::ostringstream valstm;
212  valstm << const_val->get_integer();
213  throw "Couldn't find a named value in enum " + tenum->get_name() + " for value " + valstm.str();
214  }
215  const_val->set_identifier(tenum->get_name() + "." + enum_value->get_name());
216  const_val->set_enum(tenum);
217  }
218  }
219 
220  private:
221 
222  // Map of names to types
223  std::map<std::string, t_type*> types_;
224 
225  // Map of names to constants
226  std::map<std::string, t_const*> constants_;
227 
228  // Map of names to services
229  std::map<std::string, t_service*> services_;
230 
231 #ifdef SANDESH
232  // Map of names to sandeshs
233  std::map<std::string, t_sandesh*> sandeshs_;
234 #endif
235 
236 };
237 
238 #endif
std::map< std::string, t_const * > constants_
Definition: t_scope.h:226
t_service * get_service(std::string name)
Definition: t_scope.h:64
void set_string(std::string val)
Definition: t_const_value.h:58
void add_type(std::string name, t_type *type)
Definition: t_scope.h:52
void set_enum(t_enum *tenum)
Definition: t_enum.h:30
Definition: t_type.h:48
void resolve_const_value(t_const_value *const_val, t_type *ttype)
Definition: t_scope.h:99
virtual bool is_map() const
Definition: t_type.h:78
t_const * get_constant(std::string name)
Definition: t_scope.h:86
t_field * get_field_by_name(std::string field_name)
Definition: t_struct.h:81
virtual bool is_enum() const
Definition: t_type.h:72
t_type * get_type() const
Definition: t_field.h:91
virtual bool is_base_type() const
Definition: t_type.h:61
std::map< std::string, t_type * > types_
Definition: t_scope.h:223
void set_integer(int64_t val)
Definition: t_const_value.h:67
const std::map< t_const_value *, t_const_value * > & get_map() const
const std::string & get_name()
Definition: t_enum_value.h:46
void set_identifier(std::string val)
int64_t get_integer() const
Definition: t_const_value.h:72
t_const_value_type get_type() const
t_type * get_type() const
Definition: t_const.h:40
uint8_t type
Definition: load_balance.h:109
t_type * get_true_type()
Definition: parse.cc:21
virtual bool is_set() const
Definition: t_type.h:77
t_enum_value * get_constant_by_value(int64_t value)
Definition: t_enum.h:58
t_const_value * get_value() const
Definition: t_const.h:48
void set_double(double val)
Definition: t_const_value.h:94
void add_service(std::string name, t_service *service)
Definition: t_scope.h:60
std::string get_identifier() const
virtual const std::string & get_name() const
Definition: t_type.h:56
Definition: t_map.h:30
virtual bool is_list() const
Definition: t_type.h:76
void print()
Definition: t_scope.h:90
std::string get_string() const
Definition: t_const_value.h:63
void add_constant(std::string name, t_const *constant)
Definition: t_scope.h:78
double get_double() const
Definition: t_const_value.h:99
std::map< std::string, t_service * > services_
Definition: t_scope.h:229
virtual bool is_struct() const
Definition: t_type.h:73
Definition: t_list.h:29
void add_list(t_const_value *val)
void add_map(t_const_value *key, t_const_value *val)
t_type * get_type(std::string name)
Definition: t_scope.h:56
t_scope()
Definition: t_scope.h:50
const std::vector< t_const_value * > & get_list() const