pinocchio  2.4.4
A fast and flexible implementation of Rigid Body Dynamics algorithms and their analytical derivatives
code-generator-base.hpp
1 //
2 // Copyright (c) 2018 CNRS
3 //
4 
5 #ifndef __pinocchio_utils_code_generator_base_hpp__
6 #define __pinocchio_utils_code_generator_base_hpp__
7 
8 #include "pinocchio/codegen/cppadcg.hpp"
9 
10 #include "pinocchio/multibody/model.hpp"
11 #include "pinocchio/multibody/data.hpp"
12 
13 #ifdef PINOCCHIO_WITH_CPPADCG_SUPPORT
14 
15 namespace pinocchio
16 {
17 
18  template<typename _Scalar>
19  struct CodeGenBase
20  {
21  typedef _Scalar Scalar;
22  typedef CppAD::cg::CG<Scalar> CGScalar;
23  typedef CppAD::AD<CGScalar> ADScalar;
24 
25  enum { Options = 0 };
26 
33 
34  typedef Eigen::Matrix<Scalar,Eigen::Dynamic,Eigen::Dynamic,Options> MatrixXs;
35  typedef Eigen::Matrix<Scalar,Eigen::Dynamic,1,Options> VectorXs;
36  typedef Eigen::Matrix<Scalar,Eigen::Dynamic,Eigen::Dynamic,Options|Eigen::RowMajor> RowMatrixXs;
37  typedef Eigen::Matrix<ADScalar,Eigen::Dynamic,1,Options> ADVectorXs;
38  typedef Eigen::Matrix<ADScalar,Eigen::Dynamic,Eigen::Dynamic,Options> ADMatrixXs;
39 
40  typedef typename Model::ConfigVectorType ConfigVectorType;
41  typedef typename Model::TangentVectorType TangentVectorType;
42 
43  typedef typename ADModel::ConfigVectorType ADConfigVectorType;
44  typedef typename ADModel::TangentVectorType ADTangentVectorType;
45 
46  typedef CppAD::ADFun<CGScalar> ADFun;
47 
48  CodeGenBase(const Model & model,
49  const Eigen::DenseIndex dim_input,
50  const Eigen::DenseIndex dim_output,
51  const std::string & function_name,
52  const std::string & library_name)
53  : ad_model(model.template cast<ADScalar>())
54  , ad_data(ad_model)
55  , function_name(function_name)
56  , library_name(library_name + "_" + model.name)
57  , build_forward(true)
58  , build_jacobian(true)
59  {
60  ad_X = ADVectorXs(dim_input);
61  ad_Y = ADVectorXs(dim_output);
62 
63  y = VectorXs(ad_Y.size());
64 
65  jac = RowMatrixXs(ad_Y.size(),ad_X.size());
66  }
67 
69  virtual void buildMap() = 0;
70 
71  void initLib()
72  {
73  buildMap();
74 
75  // generates source code
76  cgen_ptr = std::unique_ptr<CppAD::cg::ModelCSourceGen<Scalar> >(new CppAD::cg::ModelCSourceGen<Scalar>(ad_fun, function_name));
77  cgen_ptr->setCreateForwardZero(build_forward);
78  cgen_ptr->setCreateJacobian(build_jacobian);
79  libcgen_ptr = std::unique_ptr<CppAD::cg::ModelLibraryCSourceGen<Scalar> >(new CppAD::cg::ModelLibraryCSourceGen<Scalar>(*cgen_ptr));
80 
81  dynamicLibManager_ptr
82  = std::unique_ptr<CppAD::cg::DynamicModelLibraryProcessor<Scalar> >(new CppAD::cg::DynamicModelLibraryProcessor<Scalar>(*libcgen_ptr,library_name));
83  }
84 
85  CppAD::cg::ModelCSourceGen<Scalar> & codeGenerator()
86  { return *cgen_ptr; }
87 
88  void compileLib()
89  {
90  CppAD::cg::GccCompiler<Scalar> compiler;
91  std::vector<std::string> compile_options = compiler.getCompileFlags();
92  compile_options[0] = "-Ofast";
93  compiler.setCompileFlags(compile_options);
94  dynamicLibManager_ptr->createDynamicLibrary(compiler,false);
95  }
96 
97  bool existLib() const
98  {
99  const std::string filename = dynamicLibManager_ptr->getLibraryName() + CppAD::cg::system::SystemInfo<>::DYNAMIC_LIB_EXTENSION;
100  std::ifstream file(filename.c_str());
101  return file.good();
102  }
103 
104  void loadLib(const bool generate_if_not_exist = true)
105  {
106  if(not existLib() && generate_if_not_exist)
107  compileLib();
108 
109  const auto it = dynamicLibManager_ptr->getOptions().find("dlOpenMode");
110  if (it == dynamicLibManager_ptr->getOptions().end())
111  {
112  dynamicLib_ptr.reset(new CppAD::cg::LinuxDynamicLib<Scalar>(dynamicLibManager_ptr->getLibraryName() + CppAD::cg::system::SystemInfo<>::DYNAMIC_LIB_EXTENSION));
113  }
114  else
115  {
116  int dlOpenMode = std::stoi(it->second);
117  dynamicLib_ptr.reset(new CppAD::cg::LinuxDynamicLib<Scalar>(dynamicLibManager_ptr->getLibraryName() + CppAD::cg::system::SystemInfo<>::DYNAMIC_LIB_EXTENSION, dlOpenMode));
118  }
119 
120  generatedFun_ptr = dynamicLib_ptr->model(function_name.c_str());
121  }
122 
123  template<typename Vector>
124  void evalFunction(const Eigen::MatrixBase<Vector> & x)
125  {
126  assert(build_forward);
127 
128  generatedFun_ptr->ForwardZero(PINOCCHIO_EIGEN_CONST_CAST(Vector,x),y);
129  }
130 
131  template<typename Vector>
132  void evalJacobian(const Eigen::MatrixBase<Vector> & x)
133  {
134  assert(build_jacobian);
135 
136  CppAD::cg::ArrayView<const Scalar> x_(PINOCCHIO_EIGEN_CONST_CAST(Vector,x).data(),(size_t)x.size());
137  CppAD::cg::ArrayView<Scalar> jac_(jac.data(),(size_t)jac.size());
138  generatedFun_ptr->Jacobian(x_,jac_);
139  }
140 
142  Eigen::DenseIndex getInputDimension() const { return ad_X.size(); }
144  Eigen::DenseIndex getOutputDimension() const { return ad_Y.size(); }
145 
146  protected:
147 
148  ADModel ad_model;
149  ADData ad_data;
150 
152  const std::string function_name;
154  const std::string library_name;
155 
158 
161 
162  ADVectorXs ad_X, ad_Y;
163  ADFun ad_fun;
164 
165  ADConfigVectorType ad_q, ad_q_plus;
166  ADTangentVectorType ad_dq, ad_v, ad_a;
167 
168  VectorXs y;
169  RowMatrixXs jac;
170 
171  std::unique_ptr<CppAD::cg::ModelCSourceGen<Scalar> > cgen_ptr;
172  std::unique_ptr<CppAD::cg::ModelLibraryCSourceGen<Scalar> > libcgen_ptr;
173  std::unique_ptr<CppAD::cg::DynamicModelLibraryProcessor<Scalar> > dynamicLibManager_ptr;
174  std::unique_ptr<CppAD::cg::DynamicLib<Scalar> > dynamicLib_ptr;
175  std::unique_ptr<CppAD::cg::GenericModel<Scalar> > generatedFun_ptr;
176 
177  }; // struct CodeGenBase
178 
179 } // namespace pinocchio
180 
181 #endif // PINOCCHIO_WITH_CPPADCG_SUPPORT
182 
183 #endif // ifndef __pinocchio_utils_code_generator_base_hpp__
bool build_forward
Options to generate or not the source code for the evaluation function.
Eigen::DenseIndex getOutputDimension() const
Dimension of the output vector.
const std::string function_name
Name of the function.
Eigen::DenseIndex getInputDimension() const
Dimension of the input vector.
VectorXs ConfigVectorType
Dense vectorized version of a joint configuration vector.
Definition: model.hpp:66
const std::string library_name
Name of the library.
bool build_jacobian
Options to build or not the Jacobian of he function.
virtual void buildMap()=0
build the mapping Y = f(X)
Main pinocchio namespace.
Definition: treeview.dox:24
std::string name
Model name;.
Definition: model.hpp:157
VectorXs TangentVectorType
Dense vectorized version of a joint tangent vector (e.g. velocity, acceleration, etc). It also handles the notion of co-tangent vector (e.g. torque, etc).
Definition: model.hpp:72