// // RoutingTableNewRequest.cpp //Copyright (c) 2015 Antillia.com TOSHIYUKI ARAI. ALL RIGHTS RESERVED. #include <oz++/CommonObject.h> #include <oz++/Locale.h> #include <oz++/Exception.h> #include <oz++/netlink/SocketNetlink.h> #include <oz++/netlink/RoutingTableMsg.h> #include <oz++/netlink/NetlinkRouteAttributeRequest.h> #include <oz++/netlink/NetlinkReply.h> #include <oz++/netlink/NetlinkMsgError.h> //Simple program to register a new route through Netlink++ with RTM_NEWROUTE message. //This program should be run as the root user. namespace OZ { class RoutingTableNewRequest :public CommonObject { private: NetlinkRouteAttributeRequest<rtmsg> request; SocketNetlink socketNetlink; NetlinkReply<rtmsg> reply; public: RoutingTableNewRequest(unsigned char family, __u32 dest, __u32 gateway) { NetlinkMsgHeader header(request.head()); header.type(RTM_NEWROUTE); header.flags(NLM_F_CREATE|NLM_F_REQUEST| NLM_F_ACK); header.seq(100); header.pid(0); RoutingTableMsg body(request.body()); header.length( NLMSG_LENGTH(body.size()) ); body.family(family); body.table(RT_TABLE_UNSPEC); body.dstlen(32); //Specifiy 32 bits for IPv4. body.srclen(32); body.scope(RT_SCOPE_UNIVERSE); body.type(RTN_UNICAST); body.protocol(RTPROT_UNSPEC); body.flags(RTM_F_NOTIFY); request.addAttribute(RTA_DST, &dest, 4); request.addAttribute(RTA_GATEWAY, &gateway, 4); } int send() { RouteAttributeRequest<rtmsg>& req = request.request(); size_t length = request.length(); return socketNetlink.send((const char*)&req, length, 0); } void recv() { while (true) { bzero(&reply, sizeof(reply)); int n = socketNetlink.recv((char*)&reply, sizeof(reply), 0); if (n < 0){ break;; } NetlinkMsgHeader replyHeader(&reply.head); if (replyHeader.isError() ) { //You should check the reply from the kernel, it may return success or error. NetlinkMsgError error(replyHeader.errorMsg()); error.display(); break; } fflush(stdout); } //while } }; } // int main(int argc, char* argv[]) { if (argc != 3) { printf("Usage: %s destIP gatewayIP\n", argv[0]); return 0; } try { __u32 dest = 0; __u32 gateway = 0; unsigned char family = AF_INET; if (inet_pton(family, argv[1], (struct in_addr*)&dest) <= 0) { throw IException("Invalid destIP %s", argv[1]); } if (inet_pton(family, argv[2], (struct in_addr*)&gateway) <= 0) { throw IException("Invalid gatewayIP %s", argv[2]); } RoutingTableNewRequest request(family, dest, gateway); request.send(); request.recv(); } catch (Exception& ex) { caught(ex); } return 0; } |