| /*** |
| * Copyright 2020 HAProxy Technologies |
| * |
| * This file is part of the HAProxy OpenTracing filter. |
| * |
| * This program is free software; you can redistribute it and/or |
| * modify it under the terms of the GNU General Public License |
| * as published by the Free Software Foundation; either version 2 |
| * of the License, or (at your option) any later version. |
| * |
| * This program is distributed in the hope that it will be useful, |
| * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| * GNU General Public License for more details. |
| * |
| * You should have received a copy of the GNU General Public License |
| * along with this program; if not, write to the Free Software |
| * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. |
| */ |
| #include "include.h" |
| |
| |
| /*** |
| * NAME |
| * flt_ot_cli_set_msg - |
| * |
| * ARGUMENTS |
| * appctx - |
| * err - |
| * msg - |
| * cli_state - |
| * |
| * DESCRIPTION |
| * - |
| * |
| * RETURN VALUE |
| * This function does not return a value. |
| */ |
| static void cmn_cli_set_msg(struct appctx *appctx, char *err, char *msg, int cli_state) |
| { |
| FLT_OT_FUNC("%p, %p, %p, %d", appctx, err, msg, cli_state); |
| |
| if ((appctx == NULL) || ((err == NULL) && (msg == NULL))) |
| FLT_OT_RETURN(); |
| |
| appctx->ctx.cli.err = (err == NULL) ? msg : err; |
| appctx->st0 = (appctx->ctx.cli.err == NULL) ? CLI_ST_PROMPT : cli_state; |
| |
| FLT_OT_DBG(1, "err(%d): \"%s\"", appctx->st0, appctx->ctx.cli.err); |
| |
| FLT_OT_RETURN(); |
| } |
| |
| |
| #ifdef DEBUG_OT |
| |
| /*** |
| * NAME |
| * flt_ot_cli_parse_debug - |
| * |
| * ARGUMENTS |
| * args - |
| * payload - |
| * appctx - |
| * private - |
| * |
| * DESCRIPTION |
| * - |
| * |
| * RETURN VALUE |
| * - |
| */ |
| static int flt_ot_cli_parse_debug(char **args, char *payload, struct appctx *appctx, void *private) |
| { |
| char *err = NULL, *msg = NULL; |
| uint8_t value; |
| int retval = 0; |
| |
| FLT_OT_FUNC("%p, \"%s\", %p, %p", args, payload, appctx, private); |
| |
| FLT_OT_ARGS_DUMP(); |
| |
| if (FLT_OT_ARG_ISVALID(2)) { |
| value = flt_ot_strtoll(args[2], 0, 255, &err); |
| if (err == NULL) { |
| _HA_ATOMIC_STORE(&(flt_ot_debug.level), value); |
| |
| (void)memprintf(&msg, FLT_OT_CLI_CMD " : debug level set to %hhu", value); |
| } else { |
| retval = 1; |
| } |
| } else { |
| value = _HA_ATOMIC_LOAD(&(flt_ot_debug.level)); |
| |
| (void)memprintf(&msg, FLT_OT_CLI_CMD " : current debug level is %hhu", value); |
| } |
| |
| cmn_cli_set_msg(appctx, err, msg, CLI_ST_PRINT_FREE); |
| |
| FLT_OT_RETURN_INT(retval); |
| } |
| |
| #endif /* DEBUG_OT */ |
| |
| |
| /*** |
| * NAME |
| * flt_ot_cli_parse_disabled - |
| * |
| * ARGUMENTS |
| * args - |
| * payload - |
| * appctx - |
| * private - |
| * |
| * DESCRIPTION |
| * - |
| * |
| * RETURN VALUE |
| * - |
| */ |
| static int flt_ot_cli_parse_disabled(char **args, char *payload, struct appctx *appctx, void *private) |
| { |
| char *msg = NULL; |
| bool value = (uintptr_t)private; |
| int retval = 0; |
| |
| FLT_OT_FUNC("%p, \"%s\", %p, %p", args, payload, appctx, private); |
| |
| FLT_OT_ARGS_DUMP(); |
| |
| FLT_OT_PROXIES_LIST_START() { |
| _HA_ATOMIC_STORE(&(conf->tracer->flag_disabled), value); |
| |
| (void)memprintf(&msg, "%s%s" FLT_OT_CLI_CMD " : filter %sabled", FLT_OT_CLI_MSG_CAT(msg), value ? "dis" : "en"); |
| } FLT_OT_PROXIES_LIST_END(); |
| |
| cmn_cli_set_msg(appctx, NULL, msg, CLI_ST_PRINT_FREE); |
| |
| FLT_OT_RETURN_INT(retval); |
| } |
| |
| |
| /*** |
| * NAME |
| * flt_ot_cli_parse_option - |
| * |
| * ARGUMENTS |
| * args - |
| * payload - |
| * appctx - |
| * private - |
| * |
| * DESCRIPTION |
| * - |
| * |
| * RETURN VALUE |
| * - |
| */ |
| static int flt_ot_cli_parse_option(char **args, char *payload, struct appctx *appctx, void *private) |
| { |
| char *msg = NULL; |
| bool value = (uintptr_t)private; |
| int retval = 0; |
| |
| FLT_OT_FUNC("%p, \"%s\", %p, %p", args, payload, appctx, private); |
| |
| FLT_OT_ARGS_DUMP(); |
| |
| FLT_OT_PROXIES_LIST_START() { |
| _HA_ATOMIC_STORE(&(conf->tracer->flag_harderr), value); |
| |
| (void)memprintf(&msg, "%s%s" FLT_OT_CLI_CMD " : filter set %s-errors", FLT_OT_CLI_MSG_CAT(msg), value ? "hard" : "soft"); |
| } FLT_OT_PROXIES_LIST_END(); |
| |
| cmn_cli_set_msg(appctx, NULL, msg, CLI_ST_PRINT_FREE); |
| |
| FLT_OT_RETURN_INT(retval); |
| } |
| |
| |
| /*** |
| * NAME |
| * flt_ot_cli_parse_logging - |
| * |
| * ARGUMENTS |
| * args - |
| * payload - |
| * appctx - |
| * private - |
| * |
| * DESCRIPTION |
| * - |
| * |
| * RETURN VALUE |
| * - |
| */ |
| static int flt_ot_cli_parse_logging(char **args, char *payload, struct appctx *appctx, void *private) |
| { |
| char *err = NULL, *msg = NULL; |
| uint8_t value; |
| int retval = 0; |
| |
| FLT_OT_FUNC("%p, \"%s\", %p, %p", args, payload, appctx, private); |
| |
| FLT_OT_ARGS_DUMP(); |
| |
| if (FLT_OT_ARG_ISVALID(2)) { |
| if (strcasecmp(args[2], FLT_OT_CLI_LOGGING_OFF) == 0) { |
| value = FLT_OT_LOGGING_OFF; |
| } |
| else if (strcasecmp(args[2], FLT_OT_CLI_LOGGING_ON) == 0) { |
| value = FLT_OT_LOGGING_ON; |
| } |
| else if (strcasecmp(args[2], FLT_OT_CLI_LOGGING_NOLOGNORM) == 0) { |
| value = FLT_OT_LOGGING_ON | FLT_OT_LOGGING_NOLOGNORM; |
| } |
| else { |
| (void)memprintf(&err, "'%s' : invalid value, use <" FLT_OT_CLI_LOGGING_OFF " | " FLT_OT_CLI_LOGGING_ON " | " FLT_OT_CLI_LOGGING_NOLOGNORM ">", args[2]); |
| |
| retval = 1; |
| } |
| |
| if (retval == 0) { |
| FLT_OT_PROXIES_LIST_START() { |
| _HA_ATOMIC_STORE(&(conf->tracer->logging), value); |
| |
| (void)memprintf(&msg, "%s%s" FLT_OT_CLI_CMD " : logging is %s", FLT_OT_CLI_MSG_CAT(msg), FLT_OT_CLI_LOGGING_STATE(value)); |
| } FLT_OT_PROXIES_LIST_END(); |
| } |
| } else { |
| FLT_OT_PROXIES_LIST_START() { |
| value = _HA_ATOMIC_LOAD(&(conf->tracer->logging)); |
| |
| (void)memprintf(&msg, "%s%s" FLT_OT_CLI_CMD " : logging is currently %s", FLT_OT_CLI_MSG_CAT(msg), FLT_OT_CLI_LOGGING_STATE(value)); |
| } FLT_OT_PROXIES_LIST_END(); |
| } |
| |
| cmn_cli_set_msg(appctx, err, msg, CLI_ST_PRINT_FREE); |
| |
| FLT_OT_RETURN_INT(retval); |
| } |
| |
| |
| /*** |
| * NAME |
| * flt_ot_cli_parse_rate - |
| * |
| * ARGUMENTS |
| * args - |
| * payload - |
| * appctx - |
| * private - |
| * |
| * DESCRIPTION |
| * - |
| * |
| * RETURN VALUE |
| * - |
| */ |
| static int flt_ot_cli_parse_rate(char **args, char *payload, struct appctx *appctx, void *private) |
| { |
| char *err = NULL, *msg = NULL; |
| uint32_t value; |
| int retval = 0; |
| |
| FLT_OT_FUNC("%p, \"%s\", %p, %p", args, payload, appctx, private); |
| |
| FLT_OT_ARGS_DUMP(); |
| |
| if (FLT_OT_ARG_ISVALID(2)) { |
| value = FLT_OT_FLOAT_U32(flt_ot_strtod(args[2], 0.0, FLT_OT_RATE_LIMIT_MAX, &err), FLT_OT_RATE_LIMIT_MAX); |
| if (err == NULL) { |
| FLT_OT_PROXIES_LIST_START() { |
| _HA_ATOMIC_STORE(&(conf->tracer->rate_limit), value); |
| |
| (void)memprintf(&msg, "%s%s" FLT_OT_CLI_CMD " : rate limit set to %.2f", FLT_OT_CLI_MSG_CAT(msg), FLT_OT_U32_FLOAT(value, FLT_OT_RATE_LIMIT_MAX)); |
| } FLT_OT_PROXIES_LIST_END(); |
| } else { |
| retval = 1; |
| } |
| } else { |
| FLT_OT_PROXIES_LIST_START() { |
| value = _HA_ATOMIC_LOAD(&(conf->tracer->rate_limit)); |
| |
| (void)memprintf(&msg, "%s%s" FLT_OT_CLI_CMD " : current rate limit is %.2f", FLT_OT_CLI_MSG_CAT(msg), FLT_OT_U32_FLOAT(value, FLT_OT_RATE_LIMIT_MAX)); |
| } FLT_OT_PROXIES_LIST_END(); |
| } |
| |
| cmn_cli_set_msg(appctx, err, msg, CLI_ST_PRINT_FREE); |
| |
| FLT_OT_RETURN_INT(retval); |
| } |
| |
| |
| /*** |
| * NAME |
| * flt_ot_cli_parse_status - |
| * |
| * ARGUMENTS |
| * args - |
| * payload - |
| * appctx - |
| * private - |
| * |
| * DESCRIPTION |
| * - |
| * |
| * RETURN VALUE |
| * - |
| */ |
| static int flt_ot_cli_parse_status(char **args, char *payload, struct appctx *appctx, void *private) |
| { |
| const char *nl = ""; |
| char *msg = NULL; |
| int retval = 0; |
| |
| FLT_OT_FUNC("%p, \"%s\", %p, %p", args, payload, appctx, private); |
| |
| FLT_OT_ARGS_DUMP(); |
| flt_ot_filters_dump(); |
| |
| (void)memprintf(&msg, " " FLT_OT_OPT_NAME " filter status\n" FLT_OT_STR_DASH_78); |
| #ifdef DEBUG_OT |
| (void)memprintf(&msg, "%s\n debug level: 0x%02hhx\n", msg, flt_ot_debug.level); |
| #endif |
| |
| FLT_OT_PROXIES_LIST_START() { |
| (void)memprintf(&msg, "%s\n%s filter %s\n", msg, nl, conf->id); |
| (void)memprintf(&msg, "%s configuration: %s\n", msg, conf->cfg_file); |
| (void)memprintf(&msg, "%s disable count: %" PRIu64 " %" PRIu64 "\n\n", msg, conf->cnt.disabled[0], conf->cnt.disabled[1]); |
| (void)memprintf(&msg, "%s tracer %s\n", msg, conf->tracer->id); |
| (void)memprintf(&msg, "%s configuration: %s\n", msg, conf->tracer->config); |
| (void)memprintf(&msg, "%s plugin: %s\n", msg, conf->tracer->plugin); |
| (void)memprintf(&msg, "%s rate limit: %.2f %%\n", msg, FLT_OT_U32_FLOAT(conf->tracer->rate_limit, FLT_OT_RATE_LIMIT_MAX)); |
| (void)memprintf(&msg, "%s hard errors: %s\n", msg, FLT_OT_STR_FLAG_YN(conf->tracer->flag_harderr)); |
| (void)memprintf(&msg, "%s disabled: %s\n", msg, FLT_OT_STR_FLAG_YN(conf->tracer->flag_disabled)); |
| (void)memprintf(&msg, "%s logging: %s\n", msg, FLT_OT_CLI_LOGGING_STATE(conf->tracer->logging)); |
| (void)memprintf(&msg, "%s analyzers: %08x", msg, conf->tracer->analyzers); |
| |
| nl = "\n"; |
| } FLT_OT_PROXIES_LIST_END(); |
| |
| cmn_cli_set_msg(appctx, NULL, msg, CLI_ST_PRINT_FREE); |
| |
| FLT_OT_RETURN_INT(retval); |
| } |
| |
| |
| static struct cli_kw_list cli_kws = { { }, { |
| #ifdef DEBUG_OT |
| { { FLT_OT_CLI_CMD, "debug", NULL }, FLT_OT_CLI_CMD " debug [level] : set the OT filter debug level (default: get current debug level)", flt_ot_cli_parse_debug, NULL, NULL, NULL, 0 }, |
| #endif |
| { { FLT_OT_CLI_CMD, "disable", NULL }, FLT_OT_CLI_CMD " disable : disable the OT filter", flt_ot_cli_parse_disabled, NULL, NULL, (void *)1, 0 }, |
| { { FLT_OT_CLI_CMD, "enable", NULL }, FLT_OT_CLI_CMD " enable : enable the OT filter", flt_ot_cli_parse_disabled, NULL, NULL, (void *)0, 0 }, |
| { { FLT_OT_CLI_CMD, "soft-errors", NULL }, FLT_OT_CLI_CMD " soft-errors : turning off hard-errors mode", flt_ot_cli_parse_option, NULL, NULL, (void *)0, 0 }, |
| { { FLT_OT_CLI_CMD, "hard-errors", NULL }, FLT_OT_CLI_CMD " hard-errors : enabling hard-errors mode", flt_ot_cli_parse_option, NULL, NULL, (void *)1, 0 }, |
| { { FLT_OT_CLI_CMD, "logging", NULL }, FLT_OT_CLI_CMD " logging [state] : set logging state (default: get current logging state)", flt_ot_cli_parse_logging, NULL, NULL, NULL, 0 }, |
| { { FLT_OT_CLI_CMD, "rate", NULL }, FLT_OT_CLI_CMD " rate [value] : set the rate limit (default: get current rate value)", flt_ot_cli_parse_rate, NULL, NULL, NULL, 0 }, |
| { { FLT_OT_CLI_CMD, "status", NULL }, FLT_OT_CLI_CMD " status : show the OT filter status", flt_ot_cli_parse_status, NULL, NULL, NULL, 0 }, |
| { /* END */ } |
| }}; |
| |
| |
| /*** |
| * NAME |
| * flt_ot_cli_init - |
| * |
| * ARGUMENTS |
| * This function takes no arguments. |
| * |
| * DESCRIPTION |
| * - |
| * |
| * RETURN VALUE |
| * This function does not return a value. |
| */ |
| void flt_ot_cli_init(void) |
| { |
| FLT_OT_FUNC(""); |
| |
| /* Register CLI keywords. */ |
| cli_register_kw(&cli_kws); |
| |
| FLT_OT_RETURN(); |
| } |
| |
| /* |
| * Local variables: |
| * c-indent-level: 8 |
| * c-basic-offset: 8 |
| * End: |
| * |
| * vi: noexpandtab shiftwidth=8 tabstop=8 |
| */ |