ssh: Use ssh_userauth_publickey_auto
The new ssh_userauth_publickey_auto_get_current_identity allows us to get all information we need when a key has to be unlocked.
This commit is contained in:
parent
1cd33185f2
commit
050d3e54ed
|
@ -92,6 +92,11 @@ if test "$enable_polkit" != "no"; then
|
||||||
fi
|
fi
|
||||||
if test "$enable_ssh" != "no"; then
|
if test "$enable_ssh" != "no"; then
|
||||||
PKG_CHECK_MODULES(libssh, [libssh >= 0.8.5])
|
PKG_CHECK_MODULES(libssh, [libssh >= 0.8.5])
|
||||||
|
old_CFLAGS=$CFLAGS; CFLAGS=$libssh_CFLAGS
|
||||||
|
old_LIBS=$LIBS; LIBS=$libssh_LIBS
|
||||||
|
AC_CHECK_FUNCS(ssh_userauth_publickey_auto_get_current_identity)
|
||||||
|
CFLAGS=$old_CFLAGS
|
||||||
|
LIBS=$old_LIBS
|
||||||
fi
|
fi
|
||||||
|
|
||||||
# pam
|
# pam
|
||||||
|
|
|
@ -840,6 +840,50 @@ do_password_auth (CockpitSshData *data)
|
||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef HAVE_SSH_USERAUTH_PUBLICKEY_AUTO_GET_CURRENT_IDENTITY
|
||||||
|
|
||||||
|
static int
|
||||||
|
intercept_prompt (const char *prompt, char *buf, size_t len,
|
||||||
|
int echo, int verify, void *userdata)
|
||||||
|
{
|
||||||
|
CockpitSshData *data = userdata;
|
||||||
|
char *identity = NULL;
|
||||||
|
if (ssh_userauth_publickey_auto_get_current_identity (data->session, &identity) == SSH_OK)
|
||||||
|
{
|
||||||
|
data->problem_error = g_strdup_printf ("locked identity: %s", identity);
|
||||||
|
ssh_string_free_char (identity);
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
do_auto_auth (CockpitSshData *data)
|
||||||
|
{
|
||||||
|
struct ssh_callbacks_struct cb = { .userdata = data, .auth_function = intercept_prompt };
|
||||||
|
ssh_callbacks_init (&cb);
|
||||||
|
ssh_set_callbacks (data->session, &cb);
|
||||||
|
int rc = ssh_userauth_publickey_auto (data->session, NULL, NULL);
|
||||||
|
ssh_set_callbacks (data->session, NULL);
|
||||||
|
return rc;
|
||||||
|
}
|
||||||
|
|
||||||
|
#else
|
||||||
|
|
||||||
|
/* When prompting for a key passphrase, versions of libssh without
|
||||||
|
ssh_userauth_publickey_auto_get_current_identity don't provide
|
||||||
|
enough information to say which key it is for. We need that
|
||||||
|
information since Cockpit will offer to load the key into the agent
|
||||||
|
in order to log in.
|
||||||
|
|
||||||
|
Thus, we have to reimplement ssh_userauth_publickey_auto to get the
|
||||||
|
necessary information.
|
||||||
|
|
||||||
|
We would like to iterate over all configured identities, the same
|
||||||
|
way that the real ssh_userauth_publickey does, but there is no
|
||||||
|
API to do that either. So we hard code all the names, based on
|
||||||
|
what ssh-add would add to the agent.
|
||||||
|
*/
|
||||||
|
|
||||||
struct CockpitSshPromptData {
|
struct CockpitSshPromptData {
|
||||||
CockpitSshData *data;
|
CockpitSshData *data;
|
||||||
const gchar *identity;
|
const gchar *identity;
|
||||||
|
@ -860,50 +904,6 @@ prompt_for_identity_password (const char *prompt, char *buf, size_t len,
|
||||||
static int
|
static int
|
||||||
do_auto_auth (CockpitSshData *data)
|
do_auto_auth (CockpitSshData *data)
|
||||||
{
|
{
|
||||||
/* HACK: When prompting for a key passphrase, libssh doesn't provide
|
|
||||||
enough information to say which key it is for, but we need that
|
|
||||||
information since Cockpit will offer to load the key into the
|
|
||||||
agent in order to log in.
|
|
||||||
|
|
||||||
To get this information, we reimplement
|
|
||||||
ssh_userauth_publickey_auto here in a way that passes that
|
|
||||||
information to the callback.
|
|
||||||
|
|
||||||
We would like to iterate over all configured identities, the same
|
|
||||||
way that the real ssh_userauth_publickey does, but there is no
|
|
||||||
API to do that either. So we hard code all the names, based on
|
|
||||||
what ssh-add would add to the agent.
|
|
||||||
|
|
||||||
This whole thing is meant to be replaced with something like this
|
|
||||||
eventually:
|
|
||||||
|
|
||||||
static int
|
|
||||||
intercept_prompt (const char *prompt, char *buf, size_t len,
|
|
||||||
int echo, int verify, void *userdata)
|
|
||||||
{
|
|
||||||
CockpitSshData *data = userdata;
|
|
||||||
char *identity = NULL;
|
|
||||||
if (ssh_userauth_publickey_auto_get_current_identity (data->session, &identity) == SSH_OK)
|
|
||||||
{
|
|
||||||
data->problem_error = g_strdup_printf ("locked identity: %s", identity);
|
|
||||||
ssh_string_free_char (identity);
|
|
||||||
}
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int
|
|
||||||
do_auto_auth (CockpitSshData *data)
|
|
||||||
{
|
|
||||||
struct ssh_callbacks_struct cb = { .userdata = data, .auth_function = intercept_prompt };
|
|
||||||
ssh_callbacks_init (&cb);
|
|
||||||
ssh_set_callbacks (data->session, &cb);
|
|
||||||
int rc = ssh_userauth_publickey_auto (data->session, NULL, NULL);
|
|
||||||
ssh_set_callbacks (data->session, NULL);
|
|
||||||
return rc;
|
|
||||||
}
|
|
||||||
|
|
||||||
See https://gitlab.com/libssh/libssh-mirror/-/merge_requests/134
|
|
||||||
*/
|
|
||||||
|
|
||||||
int rc;
|
int rc;
|
||||||
const gchar *msg;
|
const gchar *msg;
|
||||||
|
@ -1020,6 +1020,8 @@ do_auto_auth (CockpitSshData *data)
|
||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
static int
|
static int
|
||||||
do_key_auth (CockpitSshData *data)
|
do_key_auth (CockpitSshData *data)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in New Issue