/** * Asks for the capabilities of all local Link SAPs. * * @param in The input message. * @param out The output message. * @return Always false, because it does not send any response directly. */ bool service_management::link_capability_discover_request(meta_message_ptr &in, meta_message_ptr &out) { // Asks for local Link SAPs capabilities ODTONE_LOG(1, "(mism) gathering information about local Link SAPs capabilities"); *out << mih::request(mih::request::capability_discover); out->tid(in->tid()); out->destination(in->source()); // Check if the Link SAP is still active uint16 fails = _link_abook.fail(out->destination().to_string()); if(fails > kConf_MIHF_Link_Delete_Value) { mih::octet_string dst = out->destination().to_string(); _link_abook.inactive(dst); // Update MIHF capabilities utils::update_local_capabilities(_abook, _link_abook, _user_abook); } else { ODTONE_LOG(1, "(mics) forwarding Link_Capability_Discover.request to ", out->destination().to_string()); utils::forward_request(out, _lpool, _transmit); } return false; }
/** * Send message to a local entity. If the output message destination is a peer * MIHF redirect it to the message_out module. * * @param msg The output message. */ void transmit::operator()(meta_message_ptr& msg) { // TODO: remove try catch try{ // FIXME: Response shouldn't be send to MIH Users if(msg->opcode() != mih::operation::request) { user_entry user = _user_abook.get(msg->destination().to_string()); if(msg->opcode() == mih::operation::response) { msg->opcode(mih::operation::confirm); } utils::udp_send(_io, msg, user.ip.c_str(), user.port, _port); ODTONE_LOG(1, "(transmit) sending local message to: ", msg->destination().to_string(), " : ", user.ip, " : ", user.port); } else { link_entry link = _link_abook.get(msg->destination().to_string()); utils::udp_send(_io, msg, link.ip.c_str(), link.port, _port); ODTONE_LOG(1, "(transmit) sending local message to: ", msg->destination().to_string(), " : ", link.ip, " : ", link.port); } } catch (...) { if(msg->opcode() == mih::operation::confirm) { msg->opcode(mih::operation::response); } ODTONE_LOG(1, "(transmit) forwarding to message_out"); _msg_out(msg); } }
/** * Check if there's a handler for this message and call it, else * discard message. * * @param in The input message. * @param out The output message. */ bool sac_process_message(meta_message_ptr& in, meta_message_ptr& out) { // discard messages that this MIHF broadcasted to itself // discard messages that are not destined to this MIHF or if // multicast messages are not supported if(in->source() == mihfid) { ODTONE_LOG(1, "(sac) Discarding message! Reason: ", "message was broadcasted to itself"); return false; } if(!utils::this_mihf_is_destination(in) && !utils::is_multicast(in)) { ODTONE_LOG(1, "(sac) Discarding message! Reason: ", "this is not the message destination"); return false; } /** __no__ authentication at this point */ uint mid = in->mid(); // // no thread safety because insertion should __only__ be made // on MIHF initialization // std::map<uint, handler_t>::iterator it; it = _callbacks.find(mid); if(it != _callbacks.end()) { handler_t process_message = it->second; bool rsp; try { rsp = process_message(in, out); } catch(mih::bad_tlv) { ODTONE_LOG(1, "Discarding malformed message."); return false; } // set ip and port of response message out->ip(in->ip()); out->scope(in->scope()); out->port(in->port()); // response message must have the same tid out->tid(in->tid()); return rsp; } else { ODTONE_LOG(1, "(sac) (warning) message with mid: ", mid, " unknown, discarding."); } return false; }
/** * Link Get Parameters Confirm message handler. * * @param in input message. * @param out output message. * @return true if the response is sent immediately or false otherwise. */ bool command_service::link_get_parameters_confirm(meta_message_ptr &in, meta_message_ptr &out) { ODTONE_LOG(1, "(mics) received Link_Get_Parameters.confirm from ", in->source().to_string()); _link_abook.reset(in->source().to_string()); if(_lpool.set_user_tid(in)) { mih::status st; boost::optional<mih::link_param_list> lpl; boost::optional<mih::link_states_rsp_list> lsrl; boost::optional<mih::link_desc_rsp_list> ldrl; *in >> mih::confirm(mih::confirm::link_get_parameters) & mih::tlv_status(st) & mih::tlv_link_parameters_status_list(lpl) & mih::tlv_link_states_rsp(lsrl) & mih::tlv_link_descriptor_rsp(ldrl); if(st == mih::status_success) { mih::link_status_rsp link_status; link_status.states_rsp_list = lsrl.get(); link_status.param_list = lpl.get(); link_status.desc_rsp_list = ldrl.get(); _lrpool.add(in->source().to_string(), in->tid(), link_status); } return false; }
/** * Link Get Parameters Response message handler. * * @param in The input message. * @param out The output message. * @return True if the response is sent immediately or false otherwise. */ bool command_service::link_get_parameters_response(meta_message_ptr &in, meta_message_ptr &out) { ODTONE_LOG(1, "(mics) received Link_Get_Parameters.response from ", in->source().to_string()); if(!_lpool.set_user_tid(in)) { ODTONE_LOG(1, "(mics) warning: no local transaction for this msg ", "discarding it"); return false; } ODTONE_LOG(1, "(mics) forwarding Link_Get_Parameters.response to ", in->destination().to_string()); _transmit(in); return false; }
/** * Check if there is a handler for this message and call it, else * discard message. * * @param in The input message. */ void sac_dispatch::operator()(meta_message_ptr& in) { /** __no__ authentication at this point */ uint mid = in->mid(); ODTONE_LOG(1, "(sac) dispatching message with mid: ", mid); // // no thread safety because insertion should __only__ be made // on MIHF initialization // std::map<uint, handler_t>::iterator it; it = _callbacks.find(mid); if(it != _callbacks.end()) { handler_t process_message = it->second; meta_message_ptr out(new meta_message); out->tid(in->tid()); // send response if it was generated try { if (process_message(in, out)) _transmit(out); } catch(mih::bad_tlv) { ODTONE_LOG(1, "Discarding malformed message."); } catch(unknown_link_sap) { ODTONE_LOG(1, "Received message from an unknown Link SAP. Discarding message."); } catch(unknown_mih_user) { ODTONE_LOG(1, "Received message from an unknown MIH-User. Discarding message."); } } else { ODTONE_LOG(1, "(sac) (warning) message with mid: ", mid, " unknown, discarding."); } }
/** * Add a new MIHF entry in the address book. * * @param id MIHF MIH Identifier. * @param entry_info MIHF entry information. */ void address_book::add(const mih::octet_string &id, address_entry entry_info) { boost::mutex::scoped_lock lock(_mutex); std::map<mih::octet_string, address_entry>::iterator it; it = _abook.find(id); if (it != _abook.end()) { entry_info.ip = it->second.ip; entry_info.port = it->second.port; } _abook[id] = entry_info; ODTONE_LOG(4, "(address_book) added: ", id); }
/** * Add a new Link SAP entry in the link book. * * @param id Link SAP MIH Identifier. * @param ip Link SAP IP address. * @param port Link SAP listening port. * @param link_id interfaces that Link SAP manages. */ void link_book::add(const mih::octet_string &id, mih::octet_string& ip, uint16 port, mih::link_id link_id) { boost::mutex::scoped_lock lock(_mutex); // TODO: add thread safety link_entry a; a.ip.assign(ip); a.port = port; a.link_id = link_id; a.fail = 0; a.status = true; _lbook[id] = a; ODTONE_LOG(4, "(link_book) added: ", id, " ", ip, " ", port); }