+++ /dev/null
-#!/usr/bin/sh
-
-# Use dtrace to trace the following syscalls of all "dt" processes:
-# open*, close, mkdir, [f]chmod, dup, [l|f]stat[64]
-
-
-dtrace='
-#pragma D option quiet
-
-dtrace:::BEGIN
-{
-}
-
-/******************************************************************************
- * open stuff
- */
-
-syscall::open*:entry
-/execname == "dt" && arg1 == 770/
-/* arg2 770 = O_RDWR|O_CREAT|O_TRUNC */
-{
- printf("%Y\t%d:\t%s(\"%s\", 0x%x(O_RDWR|O_CREAT|O_TRUNC), %04o)", walltimestamp, pid, probefunc, copyinstr(arg0), arg1, arg2);
-}
-
-syscall::open*:entry
-/execname == "dt" && arg1 != 770/
-{
- printf("%Y\t%d:\t%s(\"%s\", 0x%x, %04o)", walltimestamp, pid, probefunc, copyinstr(arg0), arg1, arg2);
-}
-
-syscall::open*:return
-/execname == "dt"/
-{
- printf("\t-> fd:%d\n", arg0);
-}
-
-/******************************************************************************
- * close stuff
- */
-
-syscall::close:entry
-/execname == "dt"/
-{
- printf("%Y\t%d:\t%s(fd:%d)", walltimestamp, pid, probefunc, arg0);
-}
-
-syscall::close:return
-/execname == "dt"/
-{
- printf("\t-> returned: %d\n", arg0);
-}
-
-/******************************************************************************
- * mkdir
- */
-
-syscall::mkdir:entry
-/execname == "dt"/
-{
- printf("%Y\t%d:\t%s(\"%s\", %04o)", walltimestamp, pid, probefunc, copyinstr(arg0), arg1);
-}
-
-syscall::mkdir:return
-/execname == "dt"/
-{
- printf("\t-> returned: %d\n", arg0);
-}
-
-
-/******************************************************************************
- * *chmod stuff
- */
-
-syscall::chmod:entry
-/execname == "dt"/
-{
- printf("%Y\t%d:\t%s(\"%s\", %04o)", walltimestamp, pid, probefunc, copyinstr(arg0), arg1);
-}
-
-syscall::chmod:return
-/execname == "dt"/
-{
- printf("\treturned: %d\n", arg0);
-}
-
-
-syscall::fchmod:entry
-/execname == "dt"/
-{
- printf("%Y\t%d:\t%s(fd: %d, %04o)", walltimestamp, pid, probefunc, arg0, arg1);
-}
-
-syscall::fchmod:return
-/execname == "dt"/
-{
- printf("\treturned: %d\n", arg0);
-}
-
-
-/******************************************************************************
- * *stat stuff
- */
-
-syscall::stat*:entry
-/execname == "dt"/
-{
- self->pathp = copyinstr(arg0);
- self->statptr = arg1;
- printf("%Y\t%d:\t%s(\"%s\")", walltimestamp, pid, probefunc, self->pathp);
-}
-
-syscall::lstat*:entry
-/execname == "dt"/
-{
- self->pathp = copyinstr(arg0);
- self->statptr = arg1;
- printf("%Y\t%d:\t%s(\"%s\")", walltimestamp, pid, probefunc, self->pathp);
-}
-
-syscall::fstat*:entry
-/execname == "dt"/
-{
- self->statptr = arg1;
- printf("%Y\t%d:\t%s(fd:%d)", walltimestamp, pid, probefunc, arg0);
-}
-
-
-/*** stat returns with ERROR ***/
-
-syscall::*stat:return
-/execname == "dt" && arg0 != 0/
-{
- printf("\t -> returned: %d, errno: %d\n", arg0, errno);
-}
-
-syscall::*stat64:return
-/execname == "dt" && arg0 != 0/
-{
- printf("\t -> returned: %d, errno: %d\n", arg0, errno);
-}
-
-/*** "*stat*" returns OK ***/
-
-syscall::*stat:return
-/execname == "dt" && arg0 == 0 && self->statptr != NULL && curpsinfo->pr_dmodel == PR_MODEL_ILP32/
-{
- self->stat32 = (struct stat32 *)copyin(self->statptr, sizeof(struct stat32));
- printf("\t-> size:%lld, mode:%04o\n", (long long)self->stat32->st_size, self->stat32->st_mode);
-}
-
-syscall::*stat:return
-/execname == "dt" && arg0 == 0 && self->statptr != NULL && curpsinfo->pr_dmodel == PR_MODEL_LP64/
-{
- self->stat64 = (struct stat *)copyin(self->statptr, sizeof(struct stat));
- printf("\t-> size:%lld, mode:%04o\n", (long long)self->stat64->st_size, self->stat64->st_mode);
-}
-
-syscall::*stat64:return
-/execname == "dt" && arg0 == 0 && self->statptr != NULL && curpsinfo->pr_dmodel == PR_MODEL_ILP32/
-{
- self->stat64_32 = (struct stat64_32 *)copyin(self->statptr, sizeof(struct stat64_32));
- printf("\t-> size:%lld, mode:%04o\n", (long long)self->stat64_32->st_size, self->stat64_32->st_mode);
-}
-
-syscall::*stat64:return
-/execname == "dt" && arg0 == 0 && self->statptr != NULL && curpsinfo->pr_dmodel == PR_MODEL_LP64/
-{
- self->stat64_64 = (struct stat64 *)copyin(self->statptr, sizeof(struct stat64));
- printf("\t-> size:%lld, mode:%04o\n", (long long)self->stat64_64->st_size, self->stat64_64->st_mode);
-}
-
-/******************************************************************************
- * MISC
- */
-
-syscall::dup:entry
-/execname == "dt"/
-{
- printf("%Y\t%d:\t%s(fd:%d)", walltimestamp, pid, probefunc, arg0);
-}
-
-syscall::dup:return
-/execname == "dt"/
-{
- printf("\t-> returned: %d\n", arg0);
-}
-
-
-/****************** END ****************/
-
-dtrace:::END
-{
-}
-'
-
-/usr/sbin/dtrace -x dynvarsize=4m -n "$dtrace" >&2
\ No newline at end of file
--- /dev/null
+#!/bin/bash
+#
+# slow
+#
+# Simulates a low bandwidth, high-latency network connection
+#
+# Requires a Linux operating system with the 'tc' traffic control tool
+#
+# Author: Richard Bullington-McGuire <richard@moduscreate.com>
+# Author: Mike Schwartz <mike@moduscreate.com>
+#
+# Copyright 2012 Modus Create, Inc.
+#
+# Permission is hereby granted, free of charge, to any person obtaining
+# a copy of this software and associated documentation files (the
+# "Software"), to deal in the Software without restriction, including
+# without limitation the rights to use, copy, modify, merge, publish,
+# distribute, sublicense, and/or sell copies of the Software, and to
+# permit persons to whom the Software is furnished to do so, subject
+# to the following conditions:
+#
+# The above copyright notice and this permission notice shall be included
+# in all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+# OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+# IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+# CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+# TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+# SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+VERSION=0.1
+device=eth0
+bandwidth=100kbps
+latency=350ms
+packetloss=
+command=slow
+retcode=0
+PATH=/sbin:/bin:/usr/sbin:/usr/bin
+
+if ! which tc > /dev/null; then
+ echo "Aborting: No 'tc' iptables firewall traffic conditioner found" 1>&2
+ echo "This requires the Linux iptables firewall." 1>&2
+ exit 1
+fi
+
+if [ $EUID -ne 0 ]; then
+ echo "Aborting: you must run this as root."
+ exit 2
+fi
+
+
+# Option processing courtesy of Stack Overflow question
+# http://stackoverflow.com/questions/402377/using-getopts-in-bash-shell-script-to-get-long-and-short-command-line-options/7680682#7680682
+# Questioner: gagneet http://stackoverflow.com/users/35416/gagneet
+# Answer: http://stackoverflow.com/a/9899366
+# Answerer: http://stackoverflow.com/users/375889/jakesandlund
+
+
+while test $# -gt 0
+do
+ case $1 in
+
+ # Normal option processing
+ -h | --help)
+ # usage and help
+ command=help
+ break
+ ;;
+ -v | --version)
+ command=version
+ break
+ ;;
+ -d | --device)
+ shift
+ device=$1
+ echo using device $device
+ ;;
+ -b | --bandwidth)
+ shift
+ bandwidth=$1
+ ;;
+ -l | --latency)
+ shift
+ latency=$1
+ ;;
+ -p | --packetloss)
+ shift
+ packetloss=$1
+ ;;
+ # ...
+
+ # Special cases
+ --)
+ break
+ ;;
+ --*)
+ # error unknown (long) option $1
+ ;;
+ -?)
+ # error unknown (short) option $1
+ ;;
+ #
+ # Shortcuts
+ AMPS)
+ command=slow
+ bandwidth=14kbps
+ latency=250ms
+ ;;
+ EDGE|2.5G|GPRS)
+ command=slow
+ bandwidth=50kbps
+ latency=200ms
+ ;;
+ 3G)
+ command=slow
+ bandwidth=1000kbps
+ latency=200ms
+ ;;
+ 4G)
+ command=slow
+ bandwidth=10000kbps
+ latency=100ms
+ ;;
+ modem-0.1k|modem-110)
+ command=slow
+ bandwidth=110bps
+ latency=350ms
+ ;;
+ modem-0.3k|modem-300)
+ command=slow
+ bandwidth=300bps
+ latency=300ms
+ ;;
+ modem-1.2k|modem-1200)
+ command=slow
+ bandwidth=1200bps
+ latency=280ms
+ ;;
+ modem-2.4k|modem-2400)
+ command=slow
+ bandwidth=2400bps
+ latency=250ms
+ ;;
+ modem-9.6k|modem-9600)
+ command=slow
+ bandwidth=9600bps
+ latency=200ms
+ ;;
+ modem-14.4k|modem-14400)
+ command=slow
+ bandwidth=14400bps
+ latency=150ms
+ ;;
+ modem-28.8k|modem-28800)
+ command=slow
+ bandwidth=28800bps
+ latency=150ms
+ ;;
+ modem-56k|modem-56000)
+ command=slow
+ bandwidth=56kbps
+ latency=120ms
+ ;;
+ 56k)
+ command=slow
+ bandwidth=56kbps
+ latency=40ms
+ ;;
+ T1|t1)
+ command=slow
+ bandwidth=1500kbps
+ latency=20ms
+ ;;
+ T3|t3)
+ command=slow
+ bandwidth=45mbps
+ latency=10ms
+ ;;
+ DSL|dsl)
+ command=slow
+ bandwidth=2mbps
+ latency=40ms
+ ;;
+ cablemodem)
+ command=slow
+ bandwidth=10mbps
+ latency=20ms
+ ;;
+ wifi-a|wifi-g)
+ command=slow
+ bandwidth=54mbps
+ latency=5ms
+ ;;
+ wifi-b)
+ command=slow
+ bandwidth=11mbps
+ latency=10ms
+ ;;
+ wifi-n)
+ command=slow
+ bandwidth=110mbps
+ latency=2ms
+ ;;
+ vsat)
+ command=slow
+ bandwidth=5mbps
+ latency=500ms
+ ;;
+ clear|reset)
+ command=clear
+ ;;
+ status)
+ command=status
+ break
+ ;;
+
+
+ # FUN STUFF HERE:
+ # Split apart combined short options
+ -*)
+ split=$1
+ shift
+ set -- $(echo "$split" | cut -c 2- | sed 's/./-& /g') "$@"
+ continue
+ ;;
+
+ # Done with options
+ *)
+ break
+ ;;
+ esac
+
+ # for testing purposes:
+ echo "param $1"
+
+ shift
+done
+
+echo "command=$command"
+echo "bandwidth=$bandwidth"
+echo "latency=$latency"
+
+case $command in
+ help)
+ echo $0
+ echo 'Usage: slow <network-type> [-d device] [-b bandwidth] [-l latency] [-p drop]'
+ echo ' slow reset'
+ echo ' slow status'
+ echo
+ echo '"network-type" type can be:'
+ echo ' GPRS'
+ echo ' GSM'
+ echo ' EDGE'
+ echo ' 2.5G'
+ echo ' GPRS'
+ echo ' 3G'
+ echo ' 4G'
+ echo ' modem-2.4k'
+ echo ' modem-9.6k'
+ echo ' modem-14.4k'
+ echo ' modem-28.8k'
+ echo ' modem-56k'
+ echo ' 56k'
+ echo ' T1'
+ echo ' T3'
+ echo ' DSL'
+ echo ' cablemodem'
+ echo ' wifi-a'
+ echo ' wifi-b'
+ echo ' wifi-g'
+ echo ' wifi-n'
+ echo ' eth-10'
+ echo ' eth-100'
+ echo ' eth-1000'
+ echo ' vsat'
+ echo ' vsat-busy'
+ ;;
+ version)
+ # version info
+ echo "slow version $VERSION"
+ echo "Copyright (c) 2012 Modus Create"
+ ;;
+ slow)
+ # Credit to Superuser for the basic commands that run this
+ # Question: http://superuser.com/questions/147156/simulating-a-low-bandwidth-high-latency-network-connection-on-linux
+ # Author: Justin L. http://superuser.com/users/38740/justin-l
+ # Answer: http://superuser.com/a/147434/159810
+ if tc qdisc show dev $device | grep "qdisc htb 1: root" >/dev/null; then
+ verb=change
+ echo "Changing existing queuing discipline"
+ else
+ verb=add
+ echo "Adding new queuing discipline"
+ tc qdisc $verb dev $device root handle 1: htb default 12
+ fi
+ tc class $verb dev $device parent 1:1 classid 1:12 htb rate $bandwidth ceil $bandwidth &&
+ tc qdisc $verb dev $device parent 1:12 netem delay $latency
+ retcode=$?
+ ;;
+ clear)
+ echo resetting queueing discipline
+ tc qdisc del dev $device root
+ retcode=$?
+ ;;
+ status)
+ tc qdisc
+ retcode=$?
+ ;;
+esac
+
+exit $retcode