1ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf/* 2ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf * src/cls-utils.c Classifier Helpers 3ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf * 4ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf * This library is free software; you can redistribute it and/or 5ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf * modify it under the terms of the GNU General Public License as 6ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf * published by the Free Software Foundation version 2 of the License. 7ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf * 8ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf * Copyright (c) 2008-2009 Thomas Graf <tgraf@suug.ch> 9ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf */ 10ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 11ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf#include "utils.h" 12ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 13ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Grafstruct rtnl_cls *nlt_alloc_cls(void) 14ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf{ 15ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf struct rtnl_cls *cls; 16ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 17ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf cls = rtnl_cls_alloc(); 18ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf if (!cls) 19ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf fatal(ENOMEM, "Unable to allocate classifier object"); 20ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 21ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf return cls; 22ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf} 23ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 24ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Grafvoid parse_dev(struct rtnl_cls *cls, struct nl_cache *link_cache, char *arg) 25ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf{ 26ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf int ival; 27ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 28ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf if (!(ival = rtnl_link_name2i(link_cache, arg))) 29ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf fatal(ENOENT, "Link \"%s\" does not exist", arg); 30ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 31ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf rtnl_cls_set_ifindex(cls, ival); 32ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf} 33ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 34ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Grafvoid parse_prio(struct rtnl_cls *cls, char *arg) 35ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf{ 36ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf uint32_t prio = parse_u32(arg); 37ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf rtnl_cls_set_prio(cls, prio); 38ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf} 39ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 40ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Grafvoid parse_parent(struct rtnl_cls *cls, char *arg) 41ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf{ 42ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf uint32_t parent; 43ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf int err; 44ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 45ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf if ((err = rtnl_tc_str2handle(arg, &parent)) < 0) 46ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf fatal(err, "Unable to parse handle \"%s\": %s", 47ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf arg, nl_geterror(err)); 48ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 49ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf rtnl_cls_set_parent(cls, parent); 50ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf} 51ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 52ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Grafvoid parse_handle(struct rtnl_cls *cls, char *arg) 53ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf{ 54ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf uint32_t handle; 55ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf int err; 56ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 57ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf if ((err = rtnl_tc_str2handle(arg, &handle)) < 0) 58ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf fatal(err, "Unable to parse handle \"%s\": %s", 59ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf arg, nl_geterror(err)); 60ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 61ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf rtnl_cls_set_handle(cls, handle); 62ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf} 63ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 64ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Grafvoid parse_proto(struct rtnl_cls *cls, char *arg) 65ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf{ 66ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf int proto = nl_str2ether_proto(arg); 67ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf if (proto < 0) 68ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf fatal(proto, "Unable to parse protocol \"%s\": %s", 69ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf arg, nl_geterror(proto)); 70ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf rtnl_cls_set_protocol(cls, proto); 71ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf} 72ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 73ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Grafstatic NL_LIST_HEAD(cls_modules); 74ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 75ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Grafstruct cls_module *lookup_cls_mod(struct rtnl_cls_ops *ops) 76ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf{ 77ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf struct cls_module *mod; 78ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 79ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf nl_list_for_each_entry(mod, &cls_modules, list) { 80ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf if (mod->ops == ops) 81ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf return mod; 82ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf } 83ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 84ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf return NULL; 85ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf} 86ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 87ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Grafvoid register_cls_module(struct cls_module *mod) 88ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf{ 89ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf struct rtnl_cls_ops *ops; 90ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 91ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf if (!(ops = __rtnl_cls_lookup_ops(mod->name))) 92ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf fatal(ENOENT, "Could not locate classifier module \"%s\"", 93ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf mod->name); 94ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 95ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf if (lookup_cls_mod(ops) != NULL) 96ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf fatal(EEXIST, "Duplicate classifier module registration."); 97ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 98ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf mod->ops = ops; 99ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf nl_list_add_tail(&mod->list, &cls_modules); 100ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf} 101ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf 102ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Grafvoid unregister_cls_module(struct cls_module *mod) 103ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf{ 104ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf nl_list_del(&mod->list); 105ef858fb492dfe98e3ae194264fbc73649cf8493aThomas Graf} 106