CANNL.h
Go to the documentation of this file.00001 /******************************************************************************* 00002 * 00003 * Copyright (c) 2008-2010 Michael Schulze <mschulze@ivs.cs.uni-magdeburg.de> 00004 * All rights reserved. 00005 * 00006 * Redistribution and use in source and binary forms, with or without 00007 * modification, are permitted provided that the following conditions 00008 * are met: 00009 * 00010 * * Redistributions of source code must retain the above copyright 00011 * notice, this list of conditions and the following disclaimer. 00012 * 00013 * * Redistributions in binary form must reproduce the above copyright 00014 * notice, this list of conditions and the following disclaimer in 00015 * the documentation and/or other materials provided with the 00016 * distribution. 00017 * 00018 * * Neither the name of the copyright holders nor the names of 00019 * contributors may be used to endorse or promote products derived 00020 * from this software without specific prior written permission. 00021 * 00022 * 00023 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS 00024 * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 00025 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A 00026 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 00027 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 00028 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 00029 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 00030 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 00031 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 00032 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 00033 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00034 * 00035 * 00036 * $Id$ 00037 * 00038 ******************************************************************************/ 00039 00040 #ifndef __CANNL_h__ 00041 #define __CANNL_h__ 00042 00043 #include "case/Delegate.h" 00044 #include "mw/nl/DistinctNL.h" 00045 #include "mw/nl/Packet.h" 00046 #include "mw/afp/Config.h" 00047 #include "mw/common/NodeID.h" 00048 #include "mw/common/Subject.h" 00049 #include "mw/common/Event.h" 00050 #include "mw/el/EventLayerCallBack.h" 00051 #include "mw/nl/can/canID.h" 00052 #include "debug.h" 00053 #include <stdio.h> 00054 00055 namespace famouso { 00056 namespace mw { 00057 namespace nl { 00058 00067 template< class CAN_Driver, class CCP, class BP > 00068 class CANNL : public DistinctNL { 00069 typedef CANNL type; 00070 uint16_t tx_node; 00071 CAN_Driver driver; 00072 CCP ccp; 00073 BP etagBP; 00074 typename CAN_Driver::MOB mob; 00075 public: 00076 struct info { 00077 enum { 00078 payload = 8 00079 }; 00080 }; 00081 00082 typedef uint16_t SNN; 00083 00084 typedef Packet<SNN> Packet_t; 00085 00087 typedef afp::MultiSubjectConfig<SNN> AFP_Config; 00088 00089 00090 CANNL() : tx_node(0) {} 00091 ~CANNL() {} 00092 00099 void init() { 00100 TRACE_FUNCTION; 00101 driver.init(); 00102 // the CAN Configuration Protocol has to run, before this 00103 // function returns 00104 tx_node = ccp.ccp_configure_tx_node(getNodeID<void>(), driver); 00105 famouso::util::Delegate<> dg; 00106 dg.bind<type, &type::rx_interrupt>(this); 00107 driver.set_rx_Interrupt(dg); 00108 driver.rx_interrupts(true); 00109 } 00110 00116 void bind(const Subject &s, SNN &snn) { 00117 TRACE_FUNCTION; 00118 snn = etagBP.bind_subject(s, tx_node, driver); 00119 } 00120 00125 void deliver(const Packet_t& p) { 00126 // senden des CAN Paketes 00127 TRACE_FUNCTION; 00128 typename CAN_Driver::MOB m; 00129 00130 m.extended(); 00131 m.id().prio(0xfd); 00132 m.id().fragment(p.fragment); 00133 m.id().tx_node(tx_node); 00134 m.id().etag(p.snn); 00135 m.len() = 0; 00136 while (m.len() != p.data_length) { 00137 m.data()[m.len()] = p.data[m.len()]; 00138 ++m.len(); 00139 } 00140 driver.transmit(m); 00141 } 00142 00147 void fetch(Packet_t& p) { 00148 // ist das Auslesen eines einzelnen Paketes 00149 TRACE_FUNCTION; 00150 p.data = mob.data(); 00151 p.data_length = mob.len(); 00152 p.fragment=mob.id().fragment(); 00153 } 00154 00155 00161 void tx_interrupt() { 00162 TRACE_FUNCTION; 00163 } 00164 00179 void rx_interrupt() { 00180 TRACE_FUNCTION; 00181 driver.receive(&mob); 00182 if (ccp.handle_ccp_configure_request(mob, driver)) 00183 return; 00184 if (etagBP.handle_subject_bind_request(mob, driver)) 00185 return; 00186 famouso::mw::el::IncommingEventFromNL(this); 00187 } 00188 00193 SNN lastPacketSNN() { 00194 return mob.id().etag(); 00195 } 00196 00197 }; 00198 } // namespace nl 00199 } // namespace mw 00200 } //namespace famouso 00201 00202 #endif /* __CANNL_h__ */ 00203