Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add utility to configure ECN WRED parameters #153

Merged
merged 3 commits into from
Dec 8, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 23 additions & 0 deletions config/main.py
Original file line number Diff line number Diff line change
Expand Up @@ -331,6 +331,29 @@ def incremental(file_name):
command = "acl-loader update incremental {}".format(file_name)
run_command(command)

#
# 'ecn' command
#
@cli.command()
@click.option('-profile', metavar='<profile_name>', type=str, required=True, help="Profile name")
@click.option('-rmax', metavar='<red threshold max>', type=int, help="Set red max threshold")
@click.option('-rmin', metavar='<red threshold min>', type=int, help="Set red min threshold")
@click.option('-ymax', metavar='<yellow threshold max>', type=int, help="Set yellow max threshold")
@click.option('-ymin', metavar='<yellow threshold min>', type=int, help="Set yellow min threshold")
@click.option('-gmax', metavar='<green threshold max>', type=int, help="Set green max threshold")
@click.option('-gmin', metavar='<green threshold min>', type=int, help="Set green min threshold")
@click.option('-v', '--verbose', is_flag=True, help="Enable verbose output")
def ecn(profile, rmax, rmin, ymax, ymin, gmax, gmin, verbose):
"""ECN-related configuration tasks"""
command = "ecnconfig -p %s" % profile
if rmax is not None: command += " -rmax %d" % rmax
if rmin is not None: command += " -rmin %d" % rmin
if ymax is not None: command += " -ymax %d" % ymax
if ymin is not None: command += " -ymin %d" % ymin
if gmax is not None: command += " -gmax %d" % gmax
if gmin is not None: command += " -gmin %d" % gmin
if verbose: command += " -vv"
run_command(command, display_cmd=verbose)

if __name__ == '__main__':
cli()
121 changes: 121 additions & 0 deletions scripts/ecnconfig
Original file line number Diff line number Diff line change
@@ -0,0 +1,121 @@
#!/usr/bin/python
"""
ecnconfig is the utility to show and change ECN configuration

usage: ecnconfig [-h] [-v] [-l] [-p PROFILE] [-gmin GREEN_MIN]
[-gmax GREEN_MAX] [-ymin YELLOW_MIN] [-ymax YELLOW_MAX]
[-rmin RED_MIN] [-rmax RED_MAX] [-vv]

optional arguments:
-h --help show this help message and exit
-v --version show program's version number and exit
-vv --verbose verbose output
-l --list show ECN WRED configuration
-p' --profile specify WRED profile name
-gmin --green-min set min threshold for packets marked green
-gmax --green-max set max threshold for packets marked green
-ymin --yellow-min set min threshold for packets marked yellow
-ymax --yellow-max set max threshold for packets marked yellow
-rmin --red-min set min threshold for packets marked red
-rmax --red-max set max threshold for packets marked red
"""
from __future__ import print_function

import os
import sys
import json
import argparse
import swsssdk
from tabulate import tabulate

WRED_PROFILE_TABLE_NAME = "WRED_PROFILE"
WRED_CONFIG_FIELDS = {
"gmax": "green_max_threshold",
"gmin": "green_min_threshold",
"ymax": "yellow_max_threshold",
"ymin": "yellow_min_threshold",
"rmax": "red_max_threshold",
"rmin": "red_min_threshold"
}

class EcnConfig(object):
"""
Process aclstat
"""
def __init__(self, verbose):
self.ports = []
self.queues = []
self.verbose = verbose

# Set up db connections
self.db = swsssdk.ConfigDBConnector()
self.db.connect()

def list(self):
wred_tables = self.db.get_table(WRED_PROFILE_TABLE_NAME)
for table in wred_tables:
profile_name = table
profile_data = wred_tables[table]
config = []
print("Profile: " + profile_name)
for field in profile_data:
line = [field, profile_data[field]]
config.append(line)
print(tabulate(config) + "\n")
if self.verbose:
print("Total profiles: %d" % len(wred_tables))

def set_wred_threshold(self, profile, threshold, value):
field = WRED_CONFIG_FIELDS[threshold]
if self.verbose:
print("Setting %s value to %s" % (field, value))
self.db.set_entry(WRED_PROFILE_TABLE_NAME, profile, {field: value})

def main():
parser = argparse.ArgumentParser(description='Show and change ECN WRED configuration',
version='1.0.0',
formatter_class=argparse.RawTextHelpFormatter)
# group = parser.add_mutually_exclusive_group()
parser.add_argument('-l', '--list', action='store_true', help='show ECN WRED configuration')
parser.add_argument('-p', '--profile', type=str, help='specify WRED profile name', default=None)
parser.add_argument('-gmin', '--green-min', type=str, help='set min threshold for packets marked \'green\'', default=None)
parser.add_argument('-gmax', '--green-max', type=str, help='set max threshold for packets marked \'green\'', default=None)
parser.add_argument('-ymin', '--yellow-min', type=str, help='set min threshold for packets marked \'yellow\'', default=None)
parser.add_argument('-ymax', '--yellow-max', type=str, help='set max threshold for packets marked \'yellow\'', default=None)
parser.add_argument('-rmin', '--red-min', type=str, help='set min threshold for packets marked \'red\'', default=None)
parser.add_argument('-rmax', '--red-max', type=str, help='set max threshold for packets marked \'red\'', default=None)
parser.add_argument('-vv', '--verbose', action='store_true', help='Verbose output', default=False)
args = parser.parse_args()

try:
ecn = EcnConfig(args.verbose)
if args.list:
if len(sys.argv) > (3 if args.verbose else 2):
raise Exception("Input arguments error. No set options allowed when -l[ist] specified")
ecn.list()
elif args.profile:
if len(sys.argv) < (5 if args.verbose else 4):
raise Exception("Input arguments error. Specify at least one threshold parameter to set")
# the following parameters can be combined in one run
if args.green_max:
ecn.set_wred_threshold(args.profile, "gmax", args.green_max)
if args.green_min:
ecn.set_wred_threshold(args.profile, "gmin", args.green_min)
if args.yellow_max:
ecn.set_wred_threshold(args.profile, "ymax", args.yellow_max)
if args.yellow_min:
ecn.set_wred_threshold(args.profile, "ymin", args.yellow_min)
if args.red_max:
ecn.set_wred_threshold(args.profile, "rmax", args.red_max)
if args.red_min:
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe deleting comments is not the best thing.

I figured out that args are returning values in strings, so we don't have a risk of ignoring integer value 0 here.

ecn.set_wred_threshold(args.profile, "rmin", args.red_min)
else:
parser.print_help()
sys.exit(1)

except Exception as e:
print(e.message, file=sys.stderr)
sys.exit(1)

if __name__ == "__main__":
main()
1 change: 1 addition & 0 deletions setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ def get_test_suite():
'scripts/coredump-compress',
'scripts/decode-syseeprom',
'scripts/dropcheck',
'scripts/ecnconfig',
'scripts/fast-reboot',
'scripts/fast-reboot-dump.py',
'scripts/fdbshow',
Expand Down
10 changes: 10 additions & 0 deletions show/main.py
Original file line number Diff line number Diff line change
Expand Up @@ -777,5 +777,15 @@ def rule(table_name, rule_id):

run_command("acl-loader show rule {} {}".format(table_name, rule_id))

#
# 'session' command (show ecn)
#
@cli.command('ecn')
def ecn():
"""Show ECN configuration"""
command = "ecnconfig -l"
proc = subprocess.Popen(command, stdout=subprocess.PIPE, shell=True)
click.echo(proc.stdout.read())

if __name__ == '__main__':
cli()