Skip to content

Instantly share code, notes, and snippets.

@hypersoft
Last active December 13, 2015 18:18
Show Gist options
  • Select an option

  • Save hypersoft/4953906 to your computer and use it in GitHub Desktop.

Select an option

Save hypersoft/4953906 to your computer and use it in GitHub Desktop.
Automatic I/O loop executive with environment sanitation, predefined macro source expansion, and optional script output to file, for consecutive cached calls / common operations / examination. The generated script, or executed function takes multiple files, or stdin as its arguments.
lib.input.file.forEach ()
{
# BOOT STRAPS
[[ "$1$2$3" == --buildprintfxchar ]] && {
echo "builtin printf -- '\\x`builtin printf '%02X' "'${4}"`';";
return;
}
[[ "$1$2$3" == --buildparservars ]] && {
declare IFS=''
echo "declare FILE=\"\";"
echo "declare RS=\"\$(`$FUNCNAME --build printf xchar ${RS:-$'\n'}`)\"; "
echo "declare -i IRL=0 RL=${RL:-1} RC=0 FNO=0 SPOS=0 FPOS=0 EOF=0 EOS=0; "
echo "declare -a TRAP[0]=\"true\";"
return;
}
[[ $1 == --build ]] && { "$FUNCNAME: $1 $2" || return; }
[[ "$1$2$3" == --listparservars ]] && {
echo FILE RS IRL RL RC FNO SPOS FPOS EOF EOS TRAP\;
return;
}
[[ "$1$2$3" == --listinternalvars ]] && {
echo _RECALL_{LABEL,INIT,SCRIPT,THIS,EXACT,EXPORT,HEAD,RECORD_AS};
return;
}
[[ $1 == --list ]] && { "$FUNCNAME: $1 $2" || return; }
#MACRO SECTION, transforms %identifier to 'var label'
[[ "$1$2" == --parseidentifiers ]] && {
declare -u ID="$3";
IFS= declare SCRIPT="$(< /dev/stdin)"
SCRIPT="${SCRIPT//\%record\.length/IRL}";
SCRIPT="${SCRIPT//\%match/BASH_REMATCH}";
SCRIPT="${SCRIPT//\%record\.number/RC}";
SCRIPT="${SCRIPT//\%record/$ID}";
SCRIPT="${SCRIPT//\%source\.position/FPOS}";
SCRIPT="${SCRIPT//\%source\.end/EOF}"; # boolean 1 true: last record
SCRIPT="${SCRIPT//\%source/FILE}";
SCRIPT="${SCRIPT//\%stream\.number/FNO}";
SCRIPT="${SCRIPT//\%stream\.count/#}";
SCRIPT="${SCRIPT//\%stream\.position/SPOS}";
SCRIPT="${SCRIPT//\%stream\.end/EOS}"; # boolean 1 true: last source file
SCRIPT="${SCRIPT//\%stream/@}";
printf %s "${SCRIPT}";
return;
}
[[ $1 == --parse ]] && { "$FUNCNAME: $1 $2" || return; }
# END BOOT STRAPS
declare -u _RECALL_LABEL=$1 || return; shift;
declare -i _RECALL_EXPORT=0;
declare $_RECALL_LABEL='' _RECALL_INIT='' _RECALL_SCRIPT='' \
_RECALL_EXACT="IFS=''" _RECALL_HEAD='' || return;
declare _RECALL_THIS=$(declare NOW=`date +%s`;
printf %08X $(( SECONDS * RANDOM ))
printf -- .%08X \
$(( ( RANDOM * 314 ) + NOW )) \
$(( SECONDS * RANDOM )) \
$(( ( RANDOM * $$ ) + NOW ));
printf '\n';
);
# These are the types of processing loops that are predefined.
if [[ $_RECALL_LABEL == RECORD ]]; then declare _RECALL_RECORD_AS='-rd"$RS"';
elif [[ $_RECALL_LABEL == LINE ]]; then
declare _RECALL_RECORD_AS='-rd"$RS"';
builtin printf -vRS '\n';
elif [[ $_RECALL_LABEL == CHUNK ]]; then declare _RECALL_RECORD_AS='-rN${RL}';
elif [[ $_RECALL_LABEL == CHAR ]]; then declare _RECALL_RECORD_AS='-rN1';
elif [[ $_RECALL_LABEL == FORMAT ]]; then declare _RECALL_RECORD_AS="$2";
else "$FUNCNAME $_RECALL_LABEL:"; return; fi;
[[ $_RECALL_RECORD_AS == "$1" ]] && shift;
# baked means: read will interpret backslashes
if [[ $1 == baked ]]; then
shift;
_RECALL_RECORD_AS=${_RECALL_RECORD_AS/-r/-};
fi;
# opposite of baked
if [[ $1 == raw ]]; then
shift;
"$FUNCNAME: raw is implied, and cannot be reversed" || return;
fi;
declare FILE="" RS=${RS:-`builtin printf '\n'`};
declare -i IRL=0 RL=${RL:-1} RC=0 FNO=0 SPOS=0 FPOS=0 EOF=0 EOS=0;
declare -a TRAP;
if [[ $_RECALL_LABEL =~ ^(RECORD|CHUNK|FORMAT)$ ]]; then
while [[ $2 == '=' && $# -ge 3 ]]; do
if [[ "$1$2" == 'delimiter=' ]]; then
builtin printf -vRS "%b" "$3" || return;
shift 3;
continue;
fi;
if [[ "$1$2" == 'length=' ]]; then
builtin printf -vRL "%i" "$3" || return;
shift 3;
continue;
fi;
"$FUNCNAME: $_RECALL_LABEL: unknown declaration: $1 $2 $3" || return;
break;
done;
fi;
[[ $1 == -i ]] && {
shift; (( $# )) || "$FUNCNAME: option -i: missing script argument" || return
(( ${#1} )) || "$FUNCNAME: option -i: invalid argument: \`'" || return;
builtin printf -v _RECALL_INIT %s "${1}"; shift;
}
while [[ $# -ne 0 && ${1:0:2} == -a ]]; do
shift; (( $# )) || "$FUNCNAME: option -a: missing script argument" || return;
(( ${#1} )) || "$FUNCNAME: option -a: invalid argument: \`'" || return;
builtin printf -v _RECALL_SCRIPT %s\\n "${_RECALL_SCRIPT}${1}";
shift;
done;
[[ -z "$_RECALL_SCRIPT" ]] && { # don't sleep on me
(( $# )) || "$FUNCNAME: default: missing script argument" || return;
(( ${#1} )) || "$FUNCNAME: option default: invalid argument: \`'" || return;
builtin printf -v _RECALL_SCRIPT %s "${1}";
shift;
}
_RECALL_SCRIPT="$(
{ IFS='' echo -En "$_RECALL_SCRIPT"; } | \
$FUNCNAME --parse identifiers $_RECALL_LABEL
)";
[[ $1 == -- ]] || {
[[ $1 == -o ]] && {
_RECALL_THIS="$2";
_RECALL_HEAD="#!`type -p bash`"$'\n\n'"`$FUNCNAME --build parser vars;`";
_RECALL_EXPORT=1;
}
} && shift;
[[ $_RECALL_EXPORT == 1 ]] || {
_RECALL_HEAD="rm $_RECALL_THIS;"$'\n'"unset -v `
$FUNCNAME --list internal vars`;"
}
cat <<EOF > $_RECALL_THIS
$_RECALL_HEAD
new.shared.return.trap ()
{
TRAP[\${#TRAP[@]}]="\${*}";
}
# custom init section for autotrap ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# new.shared.return.trap 'echo user trap'
$_RECALL_INIT
# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
$_RECALL_THIS ()
{
$_RECALL_SCRIPT
}
_auto_return_trap () {
unset -f $_RECALL_THIS new.shared.return.trap;
unset -f \$FUNCNAME;
unset -v TRAP;
}
new.shared.return.trap _auto_return_trap;
builtin trap 'for trap in "\${TRAP[@]}"; do eval \$trap; done; unset trap' RETURN;
for FILE in "\${@:-/dev/stdin}"; do
let FPOS=0 EOF=0 FNO++;
(( (\$# - FNO) == 0 )) && let EOS=1;
while (( ! EOF )); do
$_RECALL_EXACT builtin read $_RECALL_RECORD_AS $_RECALL_LABEL || EOF=1;
let IRL=\$((\${#$_RECALL_LABEL}));
{ (( EOF == 1 )) && (( FPOS == 0 )) && (( IRL == 0 )); } || {
let IRL++; # count delimiter
let FPOS+=\$IRL SPOS+=\$IRL RC++
let IRL--; # restore length
}
# execute parser
$_RECALL_THIS || { declare -i e=\$?;
return \$e 2>/dev/null || exit \$e;
}
done < "\$FILE";
done
EOF
[[ $_RECALL_EXPORT == 1 ]] || { builtin source $_RECALL_THIS "$@"; return; }
}
@hypersoft

Copy link
Copy Markdown
Author

The above generated source is from a prior version of this code.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment