From 7a1e78b91248acbcd5ffd64b82295bc9f03f9b22 Mon Sep 17 00:00:00 2001 From: tv Date: Wed, 29 Dec 2021 20:41:18 +0100 Subject: ircsink: add support for PLAIN SASL --- bin/ircsink | 65 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 64 insertions(+), 1 deletion(-) diff --git a/bin/ircsink b/bin/ircsink index 4e1a844..584e135 100755 --- a/bin/ircsink +++ b/bin/ircsink @@ -17,6 +17,25 @@ # # --port=PORT (default: 6667, or 6697 if --secure is specified) # +# --sasl=plain +# If specified, then use the PLAIN SASL mechanism. +# +# --sasl-allow-insecure +# If specified, allow SASL over plain TCP. Without this flag, it is +# mandatory to specify --secure instead. +# +# --sasl-pass=@FILE +# --sasl-pass=$VAR +# --sasl-pass="PASS +# Password to be used for SASL authentication, which can be read either +# from a file, an environment variable, or passed in as argument. +# +# Note: the characters @, $, and " have to be verbatim and might need to be +# quoted in the shell, e.g. ircsink --sasl-pass=\$SASL_PASS +# +# --sasl-user=USER (default: NICK) +# User to be used for SASL authentication. +# # --secure # If specified, then the connection will be made using openssl. # Otherwise netcat will be used. @@ -35,7 +54,7 @@ main() {( exec 3<&0 _args=$(getopt -n "$0" -s sh \ - -l help,nick:,port:,secure,server:,target: \ + -l help,nick:,port:,sasl:,sasl-allow-insecure,sasl-pass:,sasl-user:,secure,server:,target: \ -- "$0" "$@") eval set -- "$_args" unset _args @@ -43,6 +62,10 @@ main() {( help= nick= port= + sasl_allow_insecure= + sasl_mech= + sasl_pass= + sasl_user= secure= server= target= @@ -51,6 +74,22 @@ main() {( --help) help=1; shift;; --nick) nick=$2; shift 2;; --port) port=$2; shift 2;; + --sasl) + case $2 in + plain) sasl_mech=$2; shift 2;; + *) echo "$0: unsupported SASL mechanism: $2" >&2; exit 1;; + esac + ;; + --sasl-allow-insecure) sasl_allow_insecure=1; shift;; + --sasl-pass) + case $2 in + \@*) sasl_pass=$(cat "${2:1}"); shift 2;; + \$*) sasl_pass=$(env | awk -F= -v name="${2:1}" '$1==name{print$2}'); shift 2;; + \"*) sasl_pass=${2:1}; shift 2;; + *) echo "$0: don't know how to get SASL password: $2" >&2; exit 1;; + esac + ;; + --sasl-user) sasl_user=$2; shift 2;; --secure) secure=1; shift;; --server) server=$2; shift 2;; --target) target=$2; shift 2;; @@ -77,6 +116,15 @@ main() {( nick=$(hostname) fi + if test -n "$sasl_mech" && test -z "$sasl_user"; then + sasl_user=$nick + fi + + if test -n "$sasl_mech" && test -z "$secure" && test -z "$sasl_allow_insecure"; then + echo "$0: error: cannot use --sasl without --secure" >&2 + exit 1 + fi + if test -z "$port"; then case $secure in '') port=6667;; @@ -158,6 +206,21 @@ main() {( s/^PING (:.*)/PONG \1/p ' + case $sasl_mech in + plain) + echo2 "CAP REQ :sasl" + sed -nru '/^:[^ ]* CAP [0-9A-Za-z]+ ACK sasl/q' + + echo2 "AUTHENTICATE PLAIN" + sed -nru '/^:[^ ]* AUTHENTICATE +/q' + + echo sasl user: $sasl_user >&2 + message=$(printf '\0%s\0%s' "$sasl_user" "$sasl_pass" | base64) + echo "AUTHENTICATE $message" + echo "AUTHENTICATE ***REDACTED***" >&2 + ;; + esac + if is_channel "$target"; then echo2 "JOIN $target" fi -- cgit v1.2.3