With this patch, batctl is able to: * list supported routing algorithms * list batX interfaces with their configured routing algorithm * view and alter the selected routing algorithm
Signed-off-by: Marek Lindner mareklindner@neomailbox.ch --- debug.c | 14 ++++++++++ debug.h | 2 ++ main.c | 5 ++++ sys.c | 91 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ sys.h | 3 +++ 5 files changed, 115 insertions(+)
diff --git a/debug.c b/debug.c index a050345..c3959db 100644 --- a/debug.c +++ b/debug.c @@ -219,6 +219,20 @@ int handle_debug_table(char *mesh_iface, int debug_table, int argc, char **argv) batctl_debug_tables[debug_table].header_lines); }
+int print_routing_algos(void) { + char full_path[MAX_PATH+1]; + char *debugfs_mnt; + + debugfs_mnt = debugfs_mount(NULL); + if (!debugfs_mnt) { + fprintf(stderr, "Error - can't mount or find debugfs\n"); + return -1; + } + + debugfs_make_path(DEBUG_BATIF_PATH_FMT, "", full_path, sizeof(full_path)); + return read_file(full_path, DEBUG_ROUTING_ALGOS, 0, 0, 0, 0); +} + int print_vis_info(char *mesh_iface) { char full_path[MAX_PATH+1]; diff --git a/debug.h b/debug.h index 2bc0ff9..8287b54 100644 --- a/debug.h +++ b/debug.h @@ -28,6 +28,7 @@ #define DEBUG_BATIF_PATH_FMT "%s/batman_adv/%s" #define DEBUG_TRANSTABLE_GLOBAL "transtable_global" #define DEBUG_LOG "log" +#define DEBUG_ROUTING_ALGOS "routing_algos"
enum batctl_debug_tables { BATCTL_TABLE_ORIGINATORS, @@ -52,6 +53,7 @@ extern const struct debug_table_data batctl_debug_tables[BATCTL_TABLE_NUM];
int handle_debug_table(char *mesh_iface, int debug_table, int argc, char **argv); int log_print(char *mesh_iface, int argc, char **argv); +int print_routing_algos(void); int print_vis_info(char *mesh_iface);
#endif diff --git a/main.c b/main.c index d127cdc..96aea4d 100644 --- a/main.c +++ b/main.c @@ -70,6 +70,7 @@ static void print_usage(void) fprintf(stderr, " \tloglevel|ll [level] \tdisplay or modify the log level\n"); fprintf(stderr, " \tlog|l \tread the log produced by the kernel module\n"); fprintf(stderr, " \tgw_mode|gw [mode] \tdisplay or modify the gateway mode\n"); + fprintf(stderr, " \trouting_algo|ra [mode] \tdisplay or modify the routing algorithm\n"); fprintf(stderr, "\n");
fprintf(stderr, "debug tables: \tdisplay the corresponding debug table\n"); @@ -150,6 +151,10 @@ int main(int argc, char **argv)
ret = bisect_iv(argc - 1, argv + 1); #endif + } else if ((strcmp(argv[1], "routing_algo") == 0) || (strcmp(argv[1], "ra") == 0)) { + + ret = handle_ra_setting(argc - 1, argv + 1); + } else if (check_mesh_iface(mesh_iface) < 0) { fprintf(stderr, "Error - interface %s is not present or not a batman-adv interface\n", mesh_iface); exit(EXIT_FAILURE); diff --git a/sys.c b/sys.c index 81b8faf..c04e204 100644 --- a/sys.c +++ b/sys.c @@ -30,6 +30,7 @@ #include "main.h" #include "sys.h" #include "functions.h" +#include "debug.h"
#define PATH_BUFF_LEN 200
@@ -563,6 +564,96 @@ out: return res; }
+static void ra_mode_usage(void) +{ + fprintf(stderr, "Usage: batctl [options] routing_algo [algorithm]\n"); + fprintf(stderr, "options:\n"); + fprintf(stderr, " \t -h print this help\n"); +} + +int handle_ra_setting(int argc, char **argv) +{ + DIR *iface_base_dir; + struct dirent *iface_dir; + int optchar; + char *path_buff; + int res = EXIT_FAILURE; + int first_iface = 1; + + while ((optchar = getopt(argc, argv, "h")) != -1) { + switch (optchar) { + case 'h': + ra_mode_usage(); + return EXIT_SUCCESS; + default: + ra_mode_usage(); + return EXIT_FAILURE; + } + } + + if (argc == 2) { + res = write_file(SYS_SELECTED_RA_PATH, "", argv[1], NULL); + goto out; + } + + path_buff = malloc(PATH_BUFF_LEN); + if (!path_buff) { + fprintf(stderr, "Error - could not allocate path buffer: out of memory ?\n"); + goto out; + } + + iface_base_dir = opendir(SYS_IFACE_PATH); + if (!iface_base_dir) { + fprintf(stderr, "Error - the directory '%s' could not be read: %s\n", + SYS_IFACE_PATH, strerror(errno)); + fprintf(stderr, "Is the batman-adv module loaded and sysfs mounted ?\n"); + goto free_buff; + } + + while ((iface_dir = readdir(iface_base_dir)) != NULL) { + snprintf(path_buff, PATH_BUFF_LEN, SYS_ROUTING_ALGO_FMT, iface_dir->d_name); + res = read_file("", path_buff, USE_READ_BUFF | SILENCE_ERRORS, 0, 0, 0); + if (res != EXIT_SUCCESS) + continue; + + if (line_ptr[strlen(line_ptr) - 1] == '\n') + line_ptr[strlen(line_ptr) - 1] = '\0'; + + if (first_iface) { + first_iface = 0; + printf("Active routing protocol configuration:\n"); + } + + printf(" * %s: %s\n", iface_dir->d_name, line_ptr); + + free(line_ptr); + line_ptr = NULL; + } + + closedir(iface_base_dir); + free(path_buff); + + if (!first_iface) + printf("\n"); + + printf("Selected routing algorithm (used when next batX interface is created):\n"); + res = read_file("", SYS_SELECTED_RA_PATH, USE_READ_BUFF, 0, 0, 0); + if (res != EXIT_SUCCESS) + return EXIT_FAILURE; + + printf(" => %s\n", line_ptr); + free(line_ptr); + line_ptr = NULL; + + print_routing_algos(); + return EXIT_SUCCESS; + +free_buff: + free(path_buff); +out: + return res; +} + int check_mesh_iface(char *mesh_iface) { char *base_dev = NULL; diff --git a/sys.h b/sys.h index 9addd90..13c164e 100644 --- a/sys.h +++ b/sys.h @@ -35,6 +35,8 @@ #define SYS_MESH_IFACE_FMT SYS_IFACE_PATH"/%s/batman_adv/mesh_iface" #define SYS_IFACE_STATUS_FMT SYS_IFACE_PATH"/%s/batman_adv/iface_status" #define SYS_VLAN_PATH SYS_IFACE_PATH"/%s/mesh/vlan%d/" +#define SYS_ROUTING_ALGO_FMT SYS_IFACE_PATH"/%s/mesh/routing_algo" +#define SYS_SELECTED_RA_PATH "/sys/module/batman_adv/parameters/routing_algo" #define VLAN_ID_MAX_LEN 4
enum batctl_settings_list { @@ -72,6 +74,7 @@ int interface(char *mesh_iface, int argc, char **argv); int handle_loglevel(char *mesh_iface, int argc, char **argv); int handle_sys_setting(char *mesh_iface, int setting, int argc, char **argv); int handle_gw_setting(char *mesh_iface, int argc, char **argv); +int handle_ra_setting(int argc, char **argv); int check_mesh_iface(char *mesh_iface); int check_mesh_iface_ownership(char *mesh_iface, char *hard_iface);