00001 /* 00002 * Copyright (c) 2013, Shadow Robot Company, All rights reserved. 00003 * 00004 * This library is free software; you can redistribute it and/or 00005 * modify it under the terms of the GNU Lesser General Public 00006 * License as published by the Free Software Foundation; either 00007 * version 3.0 of the License, or (at your option) any later version. 00008 * 00009 * This library is distributed in the hope that it will be useful, 00010 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00011 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00012 * Lesser General Public License for more details. 00013 * 00014 * You should have received a copy of the GNU Lesser General Public 00015 * License along with this library. 00016 */ 00017 00024 #ifndef _SPI_BASE_CONTROLLER_H_ 00025 #define _SPI_BASE_CONTROLLER_H_ 00026 00027 #include <ros/node_handle.h> 00028 00029 #include <controller_interface/controller.h> 00030 #include <ros_ethercat_model/robot_state_interface.hpp> 00031 #include <sr_ronex_hardware_interface/spi_hardware_interface.hpp> 00032 #include <realtime_tools/realtime_publisher.h> 00033 #include <sr_ronex_utilities/sr_ronex_utilities.hpp> 00034 #include <queue> 00035 #include <utility> 00036 #include <string> 00037 #include <vector> 00038 #include <boost/circular_buffer.hpp> 00039 00040 #define NUM_BUFFER_ELEMENTS 100 00041 00042 namespace ronex 00043 { 00044 struct SplittedSPICommand 00045 { 00046 SPI_PACKET_OUT packet; 00047 00048 SplittedSPICommand() : packet() 00049 {} 00050 00051 explicit SplittedSPICommand(SplittedSPICommand* copy_me) 00052 { 00053 this->packet = copy_me->packet; 00054 } 00055 }; 00056 00057 struct SPIResponse 00058 { 00059 bool received; 00060 int loop_number; 00061 SPI_PACKET_IN packet; 00062 }; 00063 00064 class SPIBaseController 00065 : public controller_interface::Controller<ros_ethercat_model::RobotStateInterface> 00066 { 00067 public: 00068 SPIBaseController(); 00069 00070 virtual bool init(ros_ethercat_model::RobotStateInterface* robot, ros::NodeHandle &n); 00071 00072 virtual void starting(const ros::Time&); 00073 00077 virtual void update(const ros::Time&, const ros::Duration&); 00078 00079 protected: 00080 ros::NodeHandle node_; 00081 00083 std::string topic_prefix_; 00084 00085 int loop_count_; 00086 00087 ronex::SPI* spi_; 00088 00089 std::vector<std::queue<SplittedSPICommand, boost::circular_buffer<SplittedSPICommand> > > command_queue_; 00090 std::vector<std::queue<std::pair<SplittedSPICommand, SPIResponse>, 00091 boost::circular_buffer<std::pair<SplittedSPICommand, SPIResponse > > > > status_queue_; 00092 00093 uint16_t cmd_pin_output_states_pre_; 00094 uint16_t cmd_pin_output_states_post_; 00095 00096 bool pre_init_(ros_ethercat_model::RobotStateInterface* robot, ros::NodeHandle &n); 00097 00098 void copy_splitted_to_cmd_(uint16_t spi_index); 00099 00100 protected: 00101 // set to true when response have been processed and it is ready to be deleted 00102 std::vector<bool> delete_status_; 00103 }; 00104 } // namespace ronex 00105 00106 /* For the emacs weenies in the crowd. 00107 Local Variables: 00108 c-basic-offset: 2 00109 End: 00110 */ 00111 00112 #endif /* _SPI_BASE_CONTROLLER_H_ */