CANOpenMaster.cpp
Go to the documentation of this file.
00001 /****************************************************************
00002  *
00003  * Copyright (c) 2012
00004  *
00005  * Fraunhofer Institute for Manufacturing Engineering   
00006  * and Automation (IPA)
00007  *
00008  * +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
00009  *
00010  * Project name: Generic_CANOpen
00011  * ROS stack name: cob_drivers
00012  * ROS package name: cob_generic_can
00013  * Description:
00014  *                                                              
00015  * +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
00016  *                      
00017  * Author: 
00018  * Supervised by:
00019  *
00020  * Date of creation: Jan 2012
00021  *
00022  * +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
00023  *
00024  * Redistribution and use in source and binary forms, with or without
00025  * modification, are permitted provided that the following conditions are met:
00026  *
00027  *     * Redistributions of source code must retain the above copyright
00028  *       notice, this list of conditions and the following disclaimer.
00029  *     * Redistributions in binary form must reproduce the above copyright
00030  *       notice, this list of conditions and the following disclaimer in the
00031  *       documentation and/or other materials provided with the distribution.
00032  *     * Neither the name of the Fraunhofer Institute for Manufacturing 
00033  *       Engineering and Automation (IPA) nor the names of its
00034  *       contributors may be used to endorse or promote products derived from
00035  *       this software without specific prior written permission.
00036  *
00037  * This program is free software: you can redistribute it and/or modify
00038  * it under the terms of the GNU Lesser General Public License LGPL as 
00039  * published by the Free Software Foundation, either version 3 of the 
00040  * License, or (at your option) any later version.
00041  * 
00042  * This program is distributed in the hope that it will be useful,
00043  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00044  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00045  * GNU Lesser General Public License LGPL for more details.
00046  * 
00047  * You should have received a copy of the GNU Lesser General Public 
00048  * License LGPL along with this program. 
00049  * If not, see <http://www.gnu.org/licenses/>.
00050  *
00051  ****************************************************************/
00052 
00053 // includes
00054 #include <CANOpenMaster.h>
00055 
00056 /*---------------------------------------------------------------*/
00057 // starts SYNC Thread
00058 void InitMaster()
00059 {               
00060         // access CAN hardware
00061         // TODO get rid of *.ini
00062         can_itf = new CANPeakSysUSB("/home/tim/git/care-o-bot/schunk_modular_robotics/CANOpen_driver/CanCtrl.ini"); 
00063  
00064         // Init Buffer 
00065         PDO_buffer = new CANOpen_buffer(); 
00066 }
00067 
00068 /*---------------------------------------------------------------*/
00069 // starts SYNC Thread
00070 void StartMasterThread(double SYNC_Freq_HZ)
00071 {                       
00072         // init threads 
00073         pthread_t thread_Master;
00074         int thread_Master_ret; 
00075         
00076         TD_Master.Cycle_Freq_HZ = SYNC_Freq_HZ;
00077 
00078         thread_Master_ret = pthread_create( &thread_Master, NULL, MasterThreadFunc,(void*) &TD_Master);         
00079 }
00080 
00081 /*---------------------------------------------------------------*/
00082 // activate the PDO 
00083 void AcitvatePDO(int CAN_ID, int number, double SYNC_Freq_HZ)
00084 {       
00085         if (PDO_buffer->IsActive(number))
00086         {       PDO_buffer->RegMsg(CAN_ID, number, SYNC_Freq_HZ);       }
00087 }
00088 
00089 /*---------------------------------------------------------------*/
00090 // set new value to PDO
00091 void AssignValue2PDO(int number,char* Msg)
00092 {       
00093         // Msg array has fixed lenght of 8              
00094         PDO_buffer->SetMsg(number, Msg);
00095 }
00096 
00097 /*---------------------------------------------------------------*/
00098 // get Msg buffer
00099 int GetRecievedMsgs(CanMsg* Msgs)
00100 {       
00101         int Msg_Counter = 0; 
00102 
00103         for(int i=0; i<MAX_InBuffer_Lenght; i++) 
00104         {       
00105                 if(!InBuffer.empty())
00106                 {       Msgs[i] = InBuffer.front();
00107                         InBuffer.pop();
00108                         Msg_Counter++; 
00109                 } 
00110         }
00111         return Msg_Counter;     
00112 }
00113 
00114 /*=============================================*/
00115 
00116 /*---------------------------------------------------------------*/
00117 // starts SYNC Thread
00118 void *MasterThreadFunc(void* TD_Master)
00119 {                       
00120         // cast Data struct
00121         Thread_data* m_TD = (Thread_data*) TD_Master; 
00122 
00123         // init threads 
00124         pthread_t thread_WorkBuffer;
00125         int thread_WorkBuffer_ret; 
00126         Mutex* mtx;     
00127 
00128         mtx = new Mutex(); 
00129 
00130         for(;;)
00131         {
00132                 mtx->lock(); 
00133                 // TODO scaduling of the worker 
00134                 thread_WorkBuffer_ret = pthread_create( &thread_WorkBuffer, NULL,EvaluateBuffers,(void*) TD_Master);    
00135         
00136                 mtx->unlock();
00137 
00138                 usleep(1000000/(double)m_TD->Cycle_Freq_HZ);
00139         }
00140         pthread_exit(0);
00141 }
00142 
00143 /*---------------------------------------------------------------*/
00144 // Loop for buffer workout
00145 void *EvaluateBuffers(void* TD)
00146 {       
00147         int Msg_Counter = 0; 
00148         CanMsg cMsg; 
00149 
00150         Thread_data* m_TD = (Thread_data*) TD; 
00151         
00152         
00153         
00154         // 1. send all PDOs on the bus
00155         for (int i=0;i<MAX_PDOS;i++)
00156         {
00157                 if(PDO_buffer->IsActive(i))
00158                 {               
00159                         // send PDO value 
00160                         //WritePDO(PDO_buffer->data[i].CMsg);
00161                 }               
00162         }
00163         
00164         // 2. send SYNC msg and start synchronous motion 
00165         SendSYNC();
00166 
00167         // 3. send 1 SDO form que
00168 
00169         // 4. evaluate recieve buffer
00170         while ((can_itf->receiveMsg(&cMsg)!=0) || (Msg_Counter>=MAX_InBuffer_Lenght))
00171         {       
00172                 InBuffer.push(cMsg);
00173                 Msg_Counter++;
00174         }
00175         //std::cout << "SYNC ID: " << std::hex << CANOpenMasterObj->TxSDO << std::endl;
00176         
00177         // ??? nötig
00178         pthread_exit(0);
00179 } 
00180 
00181 /*---------------------------------------------------------------*/
00182 // send SYNC msg
00183 void SendSYNC()
00184 {       
00185         CanMsg CMsgTr;
00186         
00187         CMsgTr.m_iLen = 0;
00188         CMsgTr.m_iID = CANObj.SYNC;
00189 
00190         can_itf->transmitMsg(CMsgTr);
00191         
00192         //if(can_itf->receiveMsg(&CMsgTr)!=0)
00193         //{CMsgTr.print();}
00194 }
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Friends Defines


CANOpen_driver
Author(s): Tim Fröhlich
autogenerated on Mon Jan 14 2013 16:55:42