微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

如何为未在bash中退出的gpg命令返回退出值以验证错误的密码?

如何解决如何为未在bash中退出的gpg命令返回退出值以验证错误的密码?

在GPG中,没有适当的文档说明如何通过bash代码检查有效的密码短语,因此这是一个hack。根据以下示例代码,用于检查在gpg-agent中缓存的GPG密码是否有效:

#!/bin/bash
KEY_ID=YOUR_KEY_ID
echo "1234" | gpg -q --batch --status-fd 1 --sign --local-user $KEY_ID --passphrase-fd 0 --output /dev/null
return_code=$?
if [ "$return_code" = 0 ]; then
 echo "Valid passphrase has been set in gpg-agent"
   else
 echo "Invalid passphrase or no passphrase is set in gpg-agent"
fi

如果设置了有效的密码短语,并且当我运行此bash脚本时,返回值为0。这是正确的

但是

如果未设置密码或无效密码,则可以看到该命令正在等待某些未知的输入或进程,并且该命令不会退出(闪烁光标,直到我以CTRL + C终止)。但这是一个很好的信号,表明提供了无效的密码短语。

我的问题是,如果提供了无效的密码短语,如何强制命令退出并获得返回值1,以便可以正确使用if else条件?

要从代码中排除问题的注意和信息(这不是问题):

设置gpg密码的方法有2种:

  1. gpg --export-secret-keys -a <KEY_ID>(可以验证密码)或
  2. bash中没有提示/usr/libexec/gpg-preset-passphrase -c $KEY_grip <<< $PAsspHRASE(这不验证密码)。我需要对cron使用命令。为什么?阅读下面的内容

要清除密码,我这样做: echo RELOADAGENT | gpg-connect-agent

KEY_ID-首次创建证书时得到的

KEY_grip-可以通过以下命令获得:gpg --with-keygrip --list-secret-keys $KEY_ID

PAsspHRASE-是您的证书的密码/密码,用于缓存在gpg-agent中。

请注意,如果您使用此方法在gpg-agent:/usr/libexec/gpg-preset-passphrase -c $KEY_grip <<< $PAsspHRASE中缓存密码,它将无法验证密码,因为错误的密码也可能会缓存在gpg-agent中。当以cron身份运行时,此方法是跳过交互式输入以防止脚本错误的唯一方法,因为用户没有输入。这就是我使用被黑代码的原因。

解决方法

我找到了这个问题的答案。由于错误,返回码未正确输出。我只需要修改代码,使其不使用默认的密码输入密码提示即可。根据此相关的错误(https://dev.gnupg.org/T5076),使用pin-entry密码短语可能导致返回码在随机时间卡住。简而言之,返回代码被卡在随机时间,但这可以使用以下选项解决:

--pinentry-mode=loopback

因此,以上选项是禁用密码输入的密码输入提示,我们可以使用gpg-preset-passphrase实用程序在终端中设置密码。因此,使用这种方法,我可以获得正确的返回码。

我发现此线程正在讨论如何在gpg-agent中禁用引脚输入,例如:here

这是验证密码短语时具有正确返回码的工作代码:

#!/bin/bash
gpg-agent --daemon
KEY_ID=ABC12321SS
GPG_PRESET_PASS="/usr/libexec/gpg-preset-passphrase" # This utility came with gpg
KEY_GRIP=$(gpg --with-keygrip --list-secret-keys "$KEY_ID" | grep -Pom1 '^ *Keygrip += +\K.*') # Get they key grip
# Ask passphrase
read -s -p "Enter a passphrase to cache into a running gpg-agent: " PASSPHRASE; echo
# Cache RAW passphrase here. RAW passphrase means un-validated passphrase. Passphrase can be valid or invalid cached in gpg-agent.
$GPG_PRESET_PASS -c $KEY_GRIP <<< $PASSPHRASE 
# AND NOW WE check if a RAW passphrase is cached:
RET_VAL=$?
if [ $RET_VAL = 0 ]; then
        echo "Un-validated (RAW) passphrase is cached"
        # This is the part that I must use --pinentry-mode=loopback,so I will get correct return code
        echo "Now validating a RAW cached passphrase from gpg-agent ..."
        test=$(echo "1234" | gpg -q --pinentry-mode=loopback --status-fd 1 --sign --local-user "$KEY_ID" --passphrase-fd 0 > /dev/null)
        RET_VAL=$?
        if [ $RET_VAL = 0 ]; then
                echo "Passphrase is valid"
        else
                echo "Passphrase is invalid"
                # Can clear the passphrase and ask again for RAW passphrase
        fi

else
        echo "Error when trying to cache RAW passphrase"
        exit 1
        # Run again the script to cache RAW passphrase
fi
,

如果可以的话, 您可以启动另一个脚本,该脚本可能会计时该脚本的执行时间。如果退出实际脚本,则输入正确的密码;否则,如果达到设置的时间,则终止脚本的PID,脚本结束。

,

您可以尝试以下操作:

echo "1234" | gpg -q --batch --status-fd 1 --sign --local-user <KEY_ID> --passphrase-fd 0 --output /dev/null ||
{
    echo "Invalid passphrase or no passphrase is set in gpg-agent"
    exit
}
echo "Valid passphrase has been set in gpg-agent"

我不确定这是否可以处理等待输入的情况。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。