mkcerts upgrades, mostly EAB (read: ZSSL) stuff, but also if it requests challenge attempt too fast it won't get stuck forever. Also simplified that whole section a bit.
This commit is contained in:
177
mkcerts.sh
177
mkcerts.sh
@@ -15,14 +15,14 @@ function signCert { openssl x509 -req -in $1.csr -out $1.crt -CA $2.crt -CAkey $
|
||||
|
||||
# Deal with LE's faggotry
|
||||
shopt -s expand_aliases
|
||||
if [ $1=nigger ]; then mode=nigger; shift; fi
|
||||
if [ $mode=nigger ]; then
|
||||
alias carl=curl -H "User-Agent:nigger/faggots (https://letsencrypt.org/2025/12/02/from-90-to-45.html)"
|
||||
if [ "$1" = "nigger" ]; then mode=nigger; echo $1; shift; echo $1; fi
|
||||
if [ "$mode" = "nigger" ]; then
|
||||
alias carl='curl -H "User-Agent:nigger/faggots (https://letsencrypt.org/2025/12/02/from-90-to-45.html)"'
|
||||
sleepval=0
|
||||
timer=0
|
||||
backoff=0
|
||||
else
|
||||
alias carl=curl -H "User-Agent:rakkacme (http://rakka.au/)"
|
||||
alias carl='curl -H "User-Agent:rakkacme (http://rakka.au/)"'
|
||||
sleepval=1
|
||||
timer=10
|
||||
backoff=1
|
||||
@@ -32,6 +32,7 @@ fi
|
||||
|
||||
function ifsrev { __temp=$(tr "$2" '\n' <<< "$1" | tac | tr '\n' "$2"); echo -n ${__temp:0:-1}; }
|
||||
function b64u { cat | base64 -w 0 | tr '/+' '_-' | tr -d '= '; } # u for url-safe
|
||||
function ub64u { tr '_-' '/+' | base64 -d | hexdump -v -e '/1 ""' -e '/1 "%02x" ""'; } # u for un-
|
||||
function short256 { __temp=$(cat | sha256sum); echo -n ${__temp:0:-3}; }
|
||||
function hex2bin { cat | sed 's/\([0-9a-f]\{2\}\)/\\\\\\x\1/g' | xargs printf; }
|
||||
|
||||
@@ -108,105 +109,73 @@ function usoa # update SOA
|
||||
function complete_challenges
|
||||
{
|
||||
read_ACME # get thumb. It fucks up sig but I don't care, send_req fixes it.
|
||||
declare -A chals toks
|
||||
declare -A toks
|
||||
urls=$(jq -r '.[]' <<< "$1")
|
||||
while read url; do
|
||||
read dom chalurl tok <<< "$(send_req $url | jq -r '.identifier.value+" "+(.challenges | .[] | select(.type == "dns-01") | .url+" "+.token)')"
|
||||
chals[$dom]="${chals[$dom]}$(base64 -w 0 <<< "$chalurl");"
|
||||
toks[$dom]="${toks[$dom]}$(base64 -w 0 <<< "$tok");"
|
||||
chals="$chals $chalurl"
|
||||
toks[$dom]="${toks[$dom]} $tok"
|
||||
done <<< "$urls"
|
||||
for dom in ${!toks[@]}; do
|
||||
apply_challenge $dom ${toks[$dom]}
|
||||
done
|
||||
systemctl reload named # Actually update DNS for real final7
|
||||
declare -a pending
|
||||
for dom in ${!chals[@]}; do
|
||||
IFS=';' read -a chalurls <<< ${chals[$dom]}
|
||||
for chalurl in ${chalurls[@]}; do
|
||||
sleep $sleepval # Spam a bit less
|
||||
rurl=$(base64 -d <<< $chalurl)
|
||||
send_req $rurl '{}' > /dev/null # need empty dict to tell server to validate challenge, empty body only checks status. Just another certified ACME moment.
|
||||
pending+=("$rurl")
|
||||
done
|
||||
done
|
||||
try_challenges $chals
|
||||
# now we wait for validations
|
||||
echo "beginning validation" >&2
|
||||
echo "pending list contains: ${pending[@]}" >&2
|
||||
echo "pending list contains: $chals" >&2
|
||||
dirty=1
|
||||
tick=0
|
||||
while [ $dirty -gt 0 ]; do
|
||||
dirty=0
|
||||
for url in ${pending[@]}; do
|
||||
sleep $sleepval
|
||||
echo "checking $url" >&2
|
||||
oof=$(send_req $url)
|
||||
oof2=$(jq -r .status <<< "$oof")
|
||||
nonce=$(get_nonce) # For some reason checking status doesn't come back with a nonce, or comes back with same nonce.
|
||||
if [ $oof2 != valid ]; then dirty=1; echo -n "in" >&2; fi
|
||||
echo "valid" >&2
|
||||
done
|
||||
status_challenges $chals
|
||||
dirty=$?
|
||||
echo "sleeping for $timer" >&2
|
||||
sleep $timer # This gets slower each iteration, to spam the server less
|
||||
timer=$(($timer+$backoff))
|
||||
tick=$(($tick+$sleepval))
|
||||
echo "tick: $tick, backoff: $backoff" >&2
|
||||
if [ $tick -ge $backoff ]; then tick=0; backoff=$(($backoff+$sleepval)); fi
|
||||
if [ $tick -ge $backoff ]; then
|
||||
tick=0
|
||||
backoff=$(($backoff+$sleepval))
|
||||
try_challenges $chals
|
||||
fi
|
||||
done
|
||||
}
|
||||
|
||||
function apply_challenge
|
||||
{
|
||||
echo "applying challenge for $1: $2" >&2
|
||||
dnsname="/var/named/$(ifsrev $1 .).zone"
|
||||
dom=$1
|
||||
shift
|
||||
echo "applying challenge for $dom: $@" >&2
|
||||
dnsname="/var/named/$(ifsrev $dom .).zone"
|
||||
czf $dnsname
|
||||
szf $dnsname $(tr ';' '\n' <<< $2 | base64 -d | tr '\n' ' ') # Actually update the DNS
|
||||
szf $dnsname $@ # Actually update the DNS
|
||||
usoa $dnsname # And don't forget to update the SOA number
|
||||
}
|
||||
|
||||
# CORE ACTIONS
|
||||
|
||||
function gen_ACME_key { openssl genrsa -traditional 2048 > account.key; }
|
||||
|
||||
function register_acc
|
||||
function try_challenges
|
||||
{
|
||||
# Create account:
|
||||
read_ACME
|
||||
url=$(echo $endpoints | jq -r .newAccount)
|
||||
req='{"termsOfServiceAgreed": true, "contact": ["mailto:zerglingman@fedora.email"], "externalAccountBinding":"zerglingman@fedora.email"}'
|
||||
out=$(send_req "$url" "$req" yes)
|
||||
echo $out >&2
|
||||
loc=$(grep -i 'location' <<< "$out" | grep -io http.*$)
|
||||
load_kid $loc
|
||||
echo $loc
|
||||
}
|
||||
|
||||
function get_cert
|
||||
{
|
||||
conf=$1
|
||||
shift
|
||||
url=$(echo $endpoints | jq -r .newOrder)
|
||||
req='{"identifiers": ['
|
||||
for n in $@; do
|
||||
req=$req'{"type": "dns", "value": "'$n'"}, {"type": "dns", "value": "*.'$n'"}, ' # Do not put wildcard domains in; this will do it automatically. You still need to put them in the nuconf.
|
||||
for url in $@; do
|
||||
sleep $sleepval # Spam a bit less
|
||||
echo "trying $url" >&2
|
||||
send_req $url '{}' > /dev/null # need empty dict to tell server to validate challenge, empty body only checks status. Just another certified ACME moment.
|
||||
done
|
||||
req=${req:0:-2}']}'
|
||||
order=$(send_req $url "$req" yes)
|
||||
headers=$(sed -n 1,/^$/p <<< "$order")
|
||||
order=$(sed 1,/^$/d <<< "$order")
|
||||
# I can just access the headers lol
|
||||
# No I can't, assfucked by subshells again
|
||||
orderurl=$(grep -i location <<< "$headers" | grep -io http.*$)
|
||||
echo "order URL is: $orderurl" >&2
|
||||
auths=$(jq '.authorizations' <<< "$order")
|
||||
finalise=$(jq -r '.finalize' <<< "$order")
|
||||
complete_challenges "$auths"
|
||||
openssl req -new -key live.key -out live.csr -sha256 -noenc -config $conf -outform DER
|
||||
# I guess I should just include the conf file
|
||||
send_req $finalise '{"csr":"'$(cat live.csr | b64u)'"}'
|
||||
certurl=$(send_req $orderurl | jq -r .certificate)
|
||||
carl $certurl > out.crt
|
||||
}
|
||||
|
||||
function status_challenges
|
||||
{
|
||||
dirt=0
|
||||
for url in $@; do
|
||||
sleep $sleepval
|
||||
echo "checking $url" >&2
|
||||
oof=$(send_req $url)
|
||||
oof2=$(jq -r .status <<< "$oof")
|
||||
nonce=$(get_nonce) # For some reason checking status doesn't come back with a nonce, or comes back with same nonce.
|
||||
if [ $oof2 != valid ]; then dirt=1; echo -n "in" >&2; fi
|
||||
echo "valid" >&2
|
||||
done
|
||||
return $dirt
|
||||
}
|
||||
# SERVER COMMUNICATION
|
||||
|
||||
function send_req
|
||||
@@ -228,6 +197,70 @@ function send_req
|
||||
echo $req_resp
|
||||
}
|
||||
|
||||
# CORE ACTIONS
|
||||
|
||||
function gen_ACME_key { openssl genrsa -traditional 2048 > account.key; }
|
||||
|
||||
function register_acc
|
||||
{
|
||||
# These things have to occur before we process anything else because their values get used in EAB sneablies
|
||||
url=$(echo $endpoints | jq -r .newAccount)
|
||||
read_ACME
|
||||
|
||||
email=$1; shift
|
||||
if [ "$1" == "eab" ]; then
|
||||
shift
|
||||
kid="$1"
|
||||
hmac="$2"
|
||||
eab='{"alg":"HS256","kid":"'"$kid"'","url":"'"$url"'"}' # do NOT put the comma in, because we gotta b64 it a dozen times first.
|
||||
eab=`b64u <<< "$eab"`
|
||||
jerk2=`b64u <<< "$jerk"`
|
||||
key=`ub64u <<< "$hmac"`
|
||||
eab_sig="`echo -n "$eab.$jerk2" | openssl mac -digest sha256 -macopt "hexkey:$key" -binary hmac | b64u`"
|
||||
eab='"externalAccountBinding":{"protected":"'$eab'", "payload":"'$jerk2'", "signature":"'$eab_sig'"}, '
|
||||
elif [ -n "$1" ]; then
|
||||
eab='"externalAccountBinding":"'"$1"'", '
|
||||
fi
|
||||
# Create account:
|
||||
req='{"termsOfServiceAgreed": true, '"$eab"'"contact": ["mailto:'"$email"'"]}'
|
||||
out=$(send_req "$url" "$req" yes)
|
||||
echo "$out" >&2
|
||||
loc=$(grep -i 'location' <<< "$out" | grep -io http.*$)
|
||||
load_kid $loc
|
||||
echo $loc
|
||||
}
|
||||
|
||||
function get_cert
|
||||
{
|
||||
conf=$1
|
||||
shift
|
||||
url=$(echo $endpoints | jq -r .newOrder)
|
||||
req='{"identifiers": ['
|
||||
for n in $@; do
|
||||
req=$req'{"type": "dns", "value": "'$n'"}, {"type": "dns", "value": "*.'$n'"}, ' # Do not put wildcard domains in; this will do it automatically. You still need to put them in the nuconf.
|
||||
done
|
||||
req=${req:0:-2}']}'
|
||||
order=$(send_req $url "$req" yes)
|
||||
echo "$order" >&2
|
||||
headers=$(sed -n 1,/^$/p <<< "$order")
|
||||
order=$(sed 1,/^$/d <<< "$order")
|
||||
# I can just access the headers lol
|
||||
# No I can't, assfucked by subshells again
|
||||
orderurl=$(grep -i location <<< "$headers" | grep -io http.*$)
|
||||
echo "order URL is: $orderurl" >&2
|
||||
auths=$(jq '.authorizations' <<< "$order")
|
||||
finalise=$(jq -r '.finalize' <<< "$order")
|
||||
complete_challenges "$auths"
|
||||
openssl req -new -key live.key -out live.csr -sha256 -noenc -config $conf -outform DER
|
||||
# I guess I should just include the conf file
|
||||
send_req $finalise '{"csr":"'$(cat live.csr | b64u)'"}'
|
||||
sleep 10
|
||||
order2=`send_req $orderurl`
|
||||
echo $order2 >&2
|
||||
certurl=`jq -r .certificate <<< "$order2"`
|
||||
carl $certurl > out.crt
|
||||
}
|
||||
|
||||
# MAIN
|
||||
|
||||
get_CA_URLs $1
|
||||
|
||||
Reference in New Issue
Block a user