linux shell请参考pure bash bible
SHELL命令
read
pear
diff
trap
ldconfig
which
printf
tr
time
mktemp
readlink
ulimit
注意事项:
- 获取当前路径:
cur_path=$(cd "$(dirname "$0")"; pwd)
$(basename $0)
值显示当前脚本名,$0
显示会包括当前脚本路径;- 获取系统类型:
SYSTEM=$(uname -s)
echo -n
不换行输出;echo -e
输出特殊字符(\t
,\n
,\r
);nohup <command> &
后台运行命令或脚本;nohup
不挂断地运行命令;&
:在后台运行;
变量定义:
REPO_ROOT=$(pwd)
LOCAL_DIR=$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)
ROOT_DIR=$(cd "$LOCAL_DIR"/../.. && pwd)
gtest_reports_dir="${TEST_DIR}/cpp"
junit_reports_dir="${TEST_DIR}/junit_reports"
mkdir -p "$gtest_reports_dir" "$junit_reports_dir"
LTARGS=" --copy --force"
${OUTPUT_DIR}
${ARTIFACTS_OUT}
mkdir -p artifacts/
# Script directory
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
source "${SCRIPT_DIR}/builds_common.sh"
INSTALL_PREFIX="/usr/local/caffe2"
readonly PROTOBUF_INSTALL_PREFIX="$(mktemp -d)"
flags="-max_total_time=$runtime -artifact_prefix=fuzzer_output/ -max_len=2048 -timeout=120"
flags="$flags -dict=test/core/end2end/fuzzers/api_fuzzer.dictionary"
export PYTHON_BIN_PATH=`which python3`
yes "" | $PYTHON_BIN_PATH configure.py
python ${SCRIPT_DIR}/grpc_tensorflow_server.py $@ 2>&1 | tee "${LOG_FILE}"
if [[ -x ./cudnn_test ]]; then
./cudnn_test
fi
for dir in "${DIRS[@]}"; do
...
done
示例-1: 生成文件:
cat << EOF > src/butil/config.h
// This file is auto-generated by $(basename "$0"). DON'T edit it!
#ifndef BUTIL_CONFIG_H
#define BUTIL_CONFIG_H
#ifdef BRPC_WITH_GLOG
#undef BRPC_WITH_GLOG
#endif
#define BRPC_WITH_GLOG $WITH_GLOG
#endif // BUTIL_CONFIG_H
EOF
function add_to_manifest() {
local artifact_type=$1
local artifact_file=$2
local artifact_prefix=$3
local artifact_name
artifact_name=$(basename "$artifact_file")
local artifact_size
artifact_size=$(stat -c%s "$artifact_file")
local artifact_sha256
artifact_sha256=$(openssl sha256 -r "$artifact_file" | cut -d " " -f 1)
local artifact_target=$LOCAL_BUILD_ROOT/$artifact_type/$artifact_prefix
mkdir -p "$artifact_target"
cp "$artifact_file" "$artifact_target"
cat <<EOF
<artifact name='$artifact_name'
type='$artifact_type'
path='$artifact_type/$artifact_prefix$artifact_name'
size='$artifact_size'
sha256='$artifact_sha256' />
EOF
}
cat <<EOF > ${OUTPUT_FILENAME}
#include <string>
const char* tf_git_version() {return "${GIT_VERSION}";}
const char* tf_compiler_version() {
#ifdef _MSC_VER
#define STRINGIFY(x) #x
#define TOSTRING(x) STRINGIFY(x)
return "MSVC " TOSTRING(_MSC_FULL_VER);
#else
return __VERSION__;
#endif
}
const int tf_cxx11_abi_flag() {
#ifdef _GLIBCXX_USE_CXX11_ABI
return _GLIBCXX_USE_CXX11_ABI;
#else
return 0;
#endif
}
const int tf_monolithic_build() {
#ifdef TENSORFLOW_MONOLITHIC_BUILD
return 1;
#else
return 0;
#endif
}
EOF
mkdir -p ci_scripts/
cat >ci_scripts/upload_image.py << EOL
import os
import sys
import boto3
IMAGE_COMMIT_TAG = os.getenv('IMAGE_COMMIT_TAG')
session = boto3.session.Session()
s3 = session.resource('s3')
data = open(sys.argv[1], 'rb')
s3.Bucket('ossci-windows-build').put_object(Key='pytorch/'+IMAGE_COMMIT_TAG+'.7z', Body=data)
object_acl = s3.ObjectAcl('ossci-windows-build','pytorch/'+IMAGE_COMMIT_TAG+'.7z')
response = object_acl.put(ACL='public-read')
EOL
示例-2: 输出帮助
PROG=`basename $0`
usage() {
cat <<EOF
Usage: ${PROG} [OPTION]...
Find out the highest cpu consumed threads of java, and print the stack of these threads.
Example: ${PROG} -c 10
Options:
-p, --pid find out the highest cpu consumed threads from the specifed java process,
default from all java process.
-c, --count set the thread count to show, default is 5
-h, --help display this help and exit
EOF
exit $1
}
usage() {
echo "Usage: $(basename "$0") OPTIONS"
echo -e "-p, --prefix\tset installation prefix (default: /usr/local)"
echo -e "-l, --libdir\tset lib directory (default: lib)"
echo -e "-v, --version\tset TensorFlow version"
echo -e "-h, --help\tdisplay this message"
}
OUTPUT_FILENAME=$1
if [[ -z "${OUTPUT_FILENAME}" ]]; then
echo "Usage: $(basename "$0") <filename>"
exit 1
fi
echo "TIME: $(date)"
示例-3: 解析命令行参数(getopt/getopts)
TEMP=`getopt -o v: --long headers:,libs:,cc:,cxx:,with-glog,with-thrift,nodebugsymbols -n 'config_brpc' -- "$@"`
WITH_GLOG=0
WITH_THRIFT=0
DEBUGSYMBOLS=-g
if [ $? != 0 ] ; then >&2 $ECHO "Terminating..."; exit 1 ; fi
# Note the quotes around `$TEMP': they are essential!
eval set -- "$TEMP"
# Convert to abspath always so that generated mk is include-able from everywhere
while true; do
case "$1" in
--headers ) HDRS_IN="$(${REALPATH} $2)"; shift 2 ;;
--libs ) LIBS_IN="$(${REALPATH} $2)"; shift 2 ;;
--cc ) CC=$2; shift 2 ;;
--cxx ) CXX=$2; shift 2 ;;
--with-glog ) WITH_GLOG=1; shift 1 ;;
--with-thrift) WITH_THRIFT=1; shift 1 ;;
--nodebugsymbols ) DEBUGSYMBOLS=; shift 1 ;;
-- ) shift; break ;;
* ) break ;;
esac
done
# read the options
ARGS=$(getopt -o p:l:v:h --long prefix:,libdir:,version:,help -n $0 -- "$@")
eval set -- "$ARGS"
# extract options and their arguments into variables.
while true ; do
case "$1" in
-h|--help) usage ; exit ;;
-p|--prefix)
case "$2" in
"") shift 2 ;;
*) TF_PREFIX=$2 ; shift 2 ;;
esac ;;
-l|--libdir)
case "$2" in
"") shift 2 ;;
*) LIBDIR=$2 ; shift 2 ;;
esac ;;
-v|--version)
case "$2" in
"") shift 2 ;;
*) TF_VERSION=$2 ; shift 2 ;;
esac ;;
--) shift ; break ;;
*) echo "Internal error! Try '$0 --help' for more information." ; exit 1 ;;
esac
done
SCRIPT_DIR=$(dirname $0)
ARCHITECTURE=armeabi-v7a
# debug options
while getopts "a:c" opt_name; do
case "$opt_name" in
a) ARCHITECTURE=$OPTARG;;
c) clean=true;;
*) usage;;
esac
done
shift $((OPTIND - 1))
# Process input arguments
IS_VIRTUALENV=0
IS_GPU=0
while true; do
if [[ "$1" == "--virtualenv" ]]; then
IS_VIRTUALENV=1
elif [[ "$1" == "--gpu" ]]; then
IS_GPU=1
fi
shift
if [[ -z "$1" ]]; then
break
fi
done
TMP_DIR=$(mktemp -d)
mkdir -p "${TMP_DIR}"
示例-4: 获取当前系统CPU个数
# Determine the number of cores, for parallel make.
N_JOBS=$(grep -c ^processor /proc/cpuinfo)
if [[ -z ${N_JOBS} ]]; then
# The Linux way didn't work. Try the Mac way.
N_JOBS=$(sysctl -n hw.ncpu)
fi
CPUS=`python -c 'import multiprocessing; print multiprocessing.cpu_count()'`
make CONFIG=opt memory_usage_test memory_usage_client memory_usage_server -j $CPUS
示例-5: BASH设置CMAKE参数
###############################################################################
# Set cmake args
###############################################################################
CMAKE_ARGS=()
CMAKE_ARGS+=("-DBUILD_BINARY=ON")
CMAKE_ARGS+=("-DBUILD_TEST=ON")
CMAKE_ARGS+=("-DINSTALL_TEST=ON")
CMAKE_ARGS+=("-DUSE_OBSERVERS=ON")
CMAKE_ARGS+=("-DUSE_ZSTD=ON")
CMAKE_ARGS+=("-DCMAKE_INSTALL_PREFIX=${INSTALL_PREFIX}")
if [[ $BUILD_ENVIRONMENT == *mkl* ]]; then
CMAKE_ARGS+=("-DBLAS=MKL")
fi
if [[ $BUILD_ENVIRONMENT == *cuda* ]]; then
CMAKE_ARGS+=("-DUSE_CUDA=ON")
CMAKE_ARGS+=("-DCUDA_ARCH_NAME=Maxwell")
CMAKE_ARGS+=("-DUSE_NNPACK=OFF")
# Explicitly set path to NVCC such that the symlink to ccache or sccache is used
CMAKE_ARGS+=("-DCUDA_NVCC_EXECUTABLE=${CACHE_WRAPPER_DIR}/nvcc")
# Ensure FindCUDA.cmake can infer the right path to the CUDA toolkit.
# Setting PATH to resolve to the right nvcc alone isn't enough.
# See /usr/share/cmake-3.5/Modules/FindCUDA.cmake, block at line 589.
export CUDA_PATH="/usr/local/cuda"
# Ensure the ccache symlink can still find the real nvcc binary.
export PATH="/usr/local/cuda/bin:$PATH"
fi
if [[ $BUILD_ENVIRONMENT == *rocm* ]]; then
# This is needed to enable ImageInput operator in resnet50_trainer
CMAKE_ARGS+=("-USE_OPENCV=ON")
# This is needed to read datasets from https://download.caffe2.ai/databases/resnet_trainer.zip
CMAKE_ARGS+=("-USE_LMDB=ON")
########## HIPIFY Caffe2 operators
${PYTHON} "${ROOT_DIR}/tools/amd_build/build_pytorch_amd.py"
${PYTHON} "${ROOT_DIR}/tools/amd_build/build_caffe2_amd.py"
fi
# Try to include Redis support for Linux builds
if [ "$(uname)" == "Linux" ]; then
CMAKE_ARGS+=("-DUSE_REDIS=ON")
fi
# Currently, on Jenkins mac os, we will use custom protobuf. Mac OS
# contbuild at the moment is minimal dependency - it doesn't use glog
# or gflags either.
if [ "$(uname)" == "Darwin" ]; then
CMAKE_ARGS+=("-DBUILD_CUSTOM_PROTOBUF=ON")
fi
# Use a speciallized onnx namespace in CI to catch hardcoded onnx namespace
CMAKE_ARGS+=("-DONNX_NAMESPACE=ONNX_NAMESPACE_FOR_C2_CI")
# We test the presence of cmake3 (for platforms like Centos and Ubuntu 14.04)
# and use that if so.
if [[ -x "$(command -v cmake3)" ]]; then
CMAKE_BINARY=cmake3
else
CMAKE_BINARY=cmake
fi
示例-6: cppcheck
检测Wireshark
源代码
#!/bin/bash
#
# cppcheck.sh
# Script to run CppCheck Static Analyzer.
# http://cppcheck.sourceforge.net/
#
# Wireshark - Network traffic analyzer
# By Gerald Combs <gerald@wireshark.org>
# Copyright 2012 Gerald Combs
#
# SPDX-License-Identifier: GPL-2.0-or-later
#
CPPCHECK=`which cppcheck`
CPPCHECK_DIR=`dirname $0`
THREADS=4
QUIET="--quiet"
SUPPRESSIONS="--suppressions-list=$CPPCHECK_DIR/suppressions"
INCLUDES="--includes-file=$CPPCHECK_DIR/includes"
MODE="gcc"
while getopts "ahj:v" OPTCHAR ; do
case $OPTCHAR in
a) SUPPRESSIONS=" " ;;
h) MODE="html" ;;
j) THREADS="$OPTARG" ;;
v) QUIET=" " ;;
esac
done
shift $(($OPTIND-1))
if [ "$MODE" = "gcc" ]; then
TEMPLATE="gcc"
elif [ "$MODE" = "html" ]; then
echo "<html><body><table border=1>"
echo "<tr><th>File</th><th>Line</th><th>Severity</th>"
echo "<th>Message</th><th>ID</th></tr>"
TEMPLATE="<tr><td>{file}</td><td>{line}</td><td>{severity}</td><td>{message}</td><td>{id}</td></tr>"
fi
if [ $# -eq 0 ]; then
TARGET="."
else
TARGET=$@
fi
# Use a little-documented feature of the shell to pass SIGINTs only to the
# child process (cppcheck in this case). That way the final 'echo' still
# runs and we aren't left with broken HTML.
trap : INT
$CPPCHECK --force --enable=style $QUIET \
$SUPPRESSIONS $INCLUDES \
--std=c89 --template=$TEMPLATE \
-j $THREADS $TARGET 2>&1
if [ "$MODE" = "html" ]; then
echo "</table></body></html>"
fi
参考资料
[1] shell script编程小结——附带实例
[2] shell的set命令
[3] Shell 风格指南 - 内容目录
[4] Linux命令大全
[5] brpc
[6] shell getopt
[7] 使用getopt命令解析shell脚本的命令行选项
[8] nohup和&后台运行,进程查看及终止