gpg: Add --list-gcrypt-config and "curve" item for --list-config.

* common/openpgp-oid.c (curve_supported_p): New.
(openpgp_enum_curves): New.
* common/t-openpgp-oid.c (test_openpgp_enum_curves): New.
(main): Add option --verbose.
* g10/gpg.c (opts): Add --list-gcrypt-config.
(list_config): Add items "curve" and "curveoid".  Remove unused code.
--

GnuPG-bug-id: 1917
Signed-off-by: Werner Koch <wk@gnupg.org>
This commit is contained in:
Werner Koch 2015-03-10 15:26:02 +01:00
parent bb5a1b7c73
commit 14af2be022
No known key found for this signature in database
GPG Key ID: E3FDFF218E45B72B
6 changed files with 133 additions and 19 deletions

View File

@ -347,3 +347,41 @@ openpgp_oid_to_curve (const char *oidstr)
return "?";
}
/* Return true if the curve with NAME is supported. */
static int
curve_supported_p (const char *name)
{
int result = 0;
gcry_sexp_t keyparms;
if (!gcry_sexp_build (&keyparms, NULL, "(public-key(ecc(curve %s)))", name))
{
result = !!gcry_pk_get_curve (keyparms, 0, NULL);
gcry_sexp_release (keyparms);
}
return result;
}
/* Enumerate available and supported OpenPGP curves. The caller needs
to set the integer variable at ITERP to zero and keep on calling
this fucntion until NULL is returned. */
const char *
openpgp_enum_curves (int *iterp)
{
int idx = *iterp;
while (idx >= 0 && idx < DIM (oidtable) && oidtable[idx].name)
{
if (curve_supported_p (oidtable[idx].name))
{
*iterp = idx + 1;
return oidtable[idx].alias? oidtable[idx].alias : oidtable[idx].name;
}
idx++;
}
*iterp = idx;
return NULL;
}

View File

@ -35,6 +35,10 @@
#define BADOID "1.3.6.1.4.1.11591.2.12242973"
static int verbose;
static void
test_openpgp_oid_from_str (void)
{
@ -184,15 +188,51 @@ test_openpgp_oid_is_ed25519 (void)
}
static void
test_openpgp_enum_curves (void)
{
int iter = 0;
const char *name;
int p256 = 0;
int p384 = 0;
int p521 = 0;
while ((name = openpgp_enum_curves (&iter)))
{
if (verbose)
printf ("curve: %s\n", name);
if (!strcmp (name, "nistp256"))
p256++;
else if (!strcmp (name, "nistp384"))
p384++;
else if (!strcmp (name, "nistp521"))
p521++;
}
if (p256 != 1 || p384 != 1 || p521 != 1)
{
/* We can only check the basic RFC-6637 requirements. */
fputs ("standard ECC curve missing\n", stderr);
exit (1);
}
}
int
main (int argc, char **argv)
{
(void)argc;
(void)argv;
if (argc)
{ argc--; argv++; }
if (argc && !strcmp (argv[0], "--verbose"))
{
verbose = 1;
argc--; argv++;
}
test_openpgp_oid_from_str ();
test_openpgp_oid_to_str ();
test_openpgp_oid_is_ed25519 ();
test_openpgp_enum_curves ();
return 0;
}

View File

@ -224,6 +224,7 @@ char *openpgp_oid_to_str (gcry_mpi_t a);
int openpgp_oid_is_ed25519 (gcry_mpi_t a);
const char *openpgp_curve_to_oid (const char *name, unsigned int *r_nbits);
const char *openpgp_oid_to_curve (const char *oid);
const char *openpgp_enum_curves (int *idxp);

View File

@ -287,19 +287,22 @@ pkd:0:1024:B665B1435F4C2 .... FF26ABB:
semicolons. The algorithm numbers are as specified in
RFC-4880. Note that in contrast to the --status-fd
interface these are _not_ the Libgcrypt identifiers.
Using =pubkeyname= prints names instead of numbers.
: cfg:pubkey:1;2;3;16;17
- cipher :: The third field contains the symmetric ciphers this
version of GnuPG supports, separated by semicolons.
The cipher numbers are as specified in RFC-4880.
Using =ciphername= prints names instead of numbers.
: cfg:cipher:2;3;4;7;8;9;10
- digest :: The third field contains the digest (hash) algorithms
this version of GnuPG supports, separated by
semicolons. The digest numbers are as specified in
RFC-4880.
RFC-4880. Using =digestname= prints names instead of
numbers.
: cfg:digest:1;2;3;8;9;10
@ -319,6 +322,12 @@ pkd:0:1024:B665B1435F4C2 .... FF26ABB:
would result in:
: cfg:group:mynames:patti;joe;0x12345678;paige
- curve :: The third field contains the curve names this version
of GnuPG supports, separated by semicolons. Using
=curveoid= prints OIDs instead of numbers.
: cfg:curve:ed25519;nistp256;nistp384;nistp521
* Format of the --status-fd output

View File

@ -2945,6 +2945,10 @@ source distribution for the details of which configuration items may be
listed. @option{--list-config} is only usable with
@option{--with-colons} set.
@item --list-gcrypt-config
@opindex list-gcrypt-config
Display various internal configuration parameters of Libgcrypt.
@item --gpgconf-list
@opindex gpgconf-list
This command is similar to @option{--list-config} but in general only

View File

@ -116,6 +116,7 @@ enum cmd_and_opt_values
aQuickSignKey,
aQuickLSignKey,
aListConfig,
aListGcryptConfig,
aGPGConfList,
aGPGConfTest,
aListPackets,
@ -449,6 +450,7 @@ static ARGPARSE_OPTS opts[] = {
ARGPARSE_c (aChangePIN, "change-pin", N_("change a card's PIN")),
#endif
ARGPARSE_c (aListConfig, "list-config", "@"),
ARGPARSE_c (aListGcryptConfig, "list-gcrypt-config", "@"),
ARGPARSE_c (aGPGConfList, "gpgconf-list", "@" ),
ARGPARSE_c (aGPGConfTest, "gpgconf-test", "@" ),
ARGPARSE_c (aListPackets, "list-packets","@"),
@ -1578,8 +1580,11 @@ print_algo_names(int (*checker)(int),const char *(*mapper)(int))
static void
list_config(char *items)
{
int show_all=(items==NULL);
char *name=NULL;
int show_all = !items;
char *name = NULL;
const char *s;
struct groupitem *giter;
int first, iter;
if(!opt.with_colons)
return;
@ -1590,18 +1595,16 @@ list_config(char *items)
if(show_all || ascii_strcasecmp(name,"group")==0)
{
struct groupitem *iter;
for(iter=opt.grouplist;iter;iter=iter->next)
for (giter = opt.grouplist; giter; giter = giter->next)
{
strlist_t sl;
es_fprintf (es_stdout, "cfg:group:");
es_write_sanitized (es_stdout, iter->name, strlen(iter->name),
es_write_sanitized (es_stdout, giter->name, strlen(giter->name),
":", NULL);
es_putc (':', es_stdout);
for(sl=iter->values;sl;sl=sl->next)
for(sl=giter->values; sl; sl=sl->next)
{
es_write_sanitized (es_stdout, sl->d, strlen (sl->d),
":;", NULL);
@ -1686,20 +1689,31 @@ list_config(char *items)
any=1;
}
if(show_all || ascii_strcasecmp(name,"ccid-reader-id")==0)
if (show_all || !ascii_strcasecmp(name,"ccid-reader-id"))
{
#if defined(ENABLE_CARD_SUPPORT) && defined(HAVE_LIBUSB) \
&& GNUPG_MAJOR_VERSION == 1
/* We ignore this for GnuPG 1.4 backward compatibility. */
any=1;
}
char *p, *p2, *list = ccid_get_reader_list ();
if (show_all || !ascii_strcasecmp (name,"curve"))
{
es_printf ("cfg:curve:");
for (iter=0, first=1; (s = openpgp_enum_curves (&iter)); first=0)
es_printf ("%s%s", first?"":";", s);
es_printf ("\n");
any=1;
}
for (p=list; p && (p2 = strchr (p, '\n')); p = p2+1)
/* Curve OIDs are rarely useful and thus only printed if requested. */
if (name && !ascii_strcasecmp (name,"curveoid"))
{
es_printf ("cfg:curveoid:");
for (iter=0, first=1; (s = openpgp_enum_curves (&iter)); first = 0)
{
*p2 = 0;
es_printf ("cfg:ccid-reader-id:%s\n", p);
s = openpgp_curve_to_oid (s, NULL);
es_printf ("%s%s", first?"":";", s? s:"[?]");
}
free (list);
#endif
es_printf ("\n");
any=1;
}
@ -2265,6 +2279,7 @@ main (int argc, char **argv)
{
case aCheckKeys:
case aListConfig:
case aListGcryptConfig:
case aGPGConfList:
case aGPGConfTest:
case aListPackets:
@ -4222,6 +4237,13 @@ main (int argc, char **argv)
}
break;
case aListGcryptConfig:
/* Fixme: It would be nice to integrate that with
--list-config but unfortunately there is no way yet to have
libgcrypt print it to an estream for further parsing. */
gcry_control (GCRYCTL_PRINT_CONFIG, stdout);
break;
case aListPackets:
opt.list_packets=2;
default: