Git Product home page Git Product logo

Comments (7)

nhorman avatar nhorman commented on July 21, 2024 1

I believe the answer to question 1 is yes, its always ok to propose/consider a change like this. I would encourage you to open a pull request. We can't guarantee the outcome of course, as thats dependent on the review of the pr and issues that may be identified with it. If you're not ready to invest the time in a full PR, I would encourage you to write a design document here first for an initial comment round to better determine its feasibility.

from openssl.

beldmit avatar beldmit commented on July 21, 2024

I'm not sure it's doable in general. E.g. when we have a 3rd-party provider providing a signature algorithm working together with some common hash algorithm taken from the default provider.

Probably a provider documentation + some testing against the current configuration file will be OK.

from openssl.

baentsch avatar baentsch commented on July 21, 2024

I'm not sure it's doable in general. E.g. when we have a 3rd-party provider providing a signature algorithm working together with some common hash algorithm taken from the default provider.

Agreed. But should such providers not register a suitable name? But then again, as per @levitte 's comment providers only register the sigalg name, not the TLS one....

Probably a provider documentation + some testing against the current configuration file will be OK.

The original problem by @mouse07410 would arguably not be solved that way as the use case there (if I got it right) encompasses more than one provider.

from openssl.

mattcaswell avatar mattcaswell commented on July 21, 2024

s there a mechanism by which the unwary user can retrieve a list of all permitted values to the "SignatureAlgorithms" config parameter, e.g., along the lines of openssl list -signature-algorithms (which does take providers into account, but does not output "fully qualified" algorithm names for use by the configuration, e.g. and incl. hash algs)?

There is a programmatic mechanism to query all the available providers about TLS SignatureAlgorithms that they want to plug in. Providers adding new TLS SignatureAlgorithms do so via the TLS-SIGALG capability, which can be queried via the OSSL_PROVIDER_get_capabilities() function. Libssl does exactly this to query all providers, e.g. see:

openssl/ssl/t1_lib.c

Lines 692 to 733 in 9fcf57b

static int discover_provider_sigalgs(OSSL_PROVIDER *provider, void *vctx)
{
struct provider_ctx_data_st pgd;
pgd.ctx = vctx;
pgd.provider = provider;
OSSL_PROVIDER_get_capabilities(provider, "TLS-SIGALG",
add_provider_sigalgs, &pgd);
/*
* Always OK, even if provider doesn't support the capability:
* Reconsider testing retval when legacy sigalgs are also loaded this way.
*/
return 1;
}
int ssl_load_sigalgs(SSL_CTX *ctx)
{
size_t i;
SSL_CERT_LOOKUP lu;
if (!OSSL_PROVIDER_do_all(ctx->libctx, discover_provider_sigalgs, ctx))
return 0;
/* now populate ctx->ssl_cert_info */
if (ctx->sigalg_list_len > 0) {
OPENSSL_free(ctx->ssl_cert_info);
ctx->ssl_cert_info = OPENSSL_zalloc(sizeof(lu) * ctx->sigalg_list_len);
if (ctx->ssl_cert_info == NULL)
return 0;
for(i = 0; i < ctx->sigalg_list_len; i++) {
ctx->ssl_cert_info[i].nid = OBJ_txt2nid(ctx->sigalg_list[i].sigalg_name);
ctx->ssl_cert_info[i].amask = SSL_aANY;
}
}
/*
* For now, leave it at this: legacy sigalgs stay in their own
* data structures until "legacy cleanup" occurs.
*/
return 1;
}

The complication is that libssl adds the provider plugged-in sigalgs with its own hard-coded built-in list:

openssl/ssl/t1_lib.c

Lines 1509 to 1595 in 9fcf57b

int ssl_setup_sigalgs(SSL_CTX *ctx)
{
size_t i, cache_idx, sigalgs_len;
const SIGALG_LOOKUP *lu;
SIGALG_LOOKUP *cache = NULL;
uint16_t *tls12_sigalgs_list = NULL;
EVP_PKEY *tmpkey = EVP_PKEY_new();
int ret = 0;
if (ctx == NULL)
goto err;
sigalgs_len = OSSL_NELEM(sigalg_lookup_tbl) + ctx->sigalg_list_len;
cache = OPENSSL_malloc(sizeof(const SIGALG_LOOKUP) * sigalgs_len);
if (cache == NULL || tmpkey == NULL)
goto err;
tls12_sigalgs_list = OPENSSL_malloc(sizeof(uint16_t) * sigalgs_len);
if (tls12_sigalgs_list == NULL)
goto err;
ERR_set_mark();
/* First fill cache and tls12_sigalgs list from legacy algorithm list */
for (i = 0, lu = sigalg_lookup_tbl;
i < OSSL_NELEM(sigalg_lookup_tbl); lu++, i++) {
EVP_PKEY_CTX *pctx;
cache[i] = *lu;
tls12_sigalgs_list[i] = tls12_sigalgs[i];
/*
* Check hash is available.
* This test is not perfect. A provider could have support
* for a signature scheme, but not a particular hash. However the hash
* could be available from some other loaded provider. In that case it
* could be that the signature is available, and the hash is available
* independently - but not as a combination. We ignore this for now.
*/
if (lu->hash != NID_undef
&& ctx->ssl_digest_methods[lu->hash_idx] == NULL) {
cache[i].enabled = 0;
continue;
}
if (!EVP_PKEY_set_type(tmpkey, lu->sig)) {
cache[i].enabled = 0;
continue;
}
pctx = EVP_PKEY_CTX_new_from_pkey(ctx->libctx, tmpkey, ctx->propq);
/* If unable to create pctx we assume the sig algorithm is unavailable */
if (pctx == NULL)
cache[i].enabled = 0;
EVP_PKEY_CTX_free(pctx);
}
/* Now complete cache and tls12_sigalgs list with provider sig information */
cache_idx = OSSL_NELEM(sigalg_lookup_tbl);
for (i = 0; i < ctx->sigalg_list_len; i++) {
TLS_SIGALG_INFO si = ctx->sigalg_list[i];
cache[cache_idx].name = si.name;
cache[cache_idx].sigalg = si.code_point;
tls12_sigalgs_list[cache_idx] = si.code_point;
cache[cache_idx].hash = si.hash_name?OBJ_txt2nid(si.hash_name):NID_undef;
cache[cache_idx].hash_idx = ssl_get_md_idx(cache[cache_idx].hash);
cache[cache_idx].sig = OBJ_txt2nid(si.sigalg_name);
cache[cache_idx].sig_idx = i + SSL_PKEY_NUM;
cache[cache_idx].sigandhash = OBJ_txt2nid(si.sigalg_name);
cache[cache_idx].curve = NID_undef;
/* all provided sigalgs are enabled by load */
cache[cache_idx].enabled = 1;
cache_idx++;
}
ERR_pop_to_mark();
ctx->sigalg_lookup_cache = cache;
ctx->tls12_sigalgs = tls12_sigalgs_list;
ctx->tls12_sigalgs_len = sigalgs_len;
cache = NULL;
tls12_sigalgs_list = NULL;
ret = 1;
err:
OPENSSL_free(cache);
OPENSSL_free(tls12_sigalgs_list);
EVP_PKEY_free(tmpkey);
return ret;
}

So the full list of TLS sigalgs are the combination of these two things. The above code also checks the built-in list to confirm if it is actually usable from the available providers. Only available sigalgs from the combined list are actually usable by TLS applications.

So, it would be feasible to extend the list app with a way to query the capabilities of the providers to see what TLS sig-algs can be plugged in. But there is currently no mechanism to query which of the "built-in" TLS sig-algs are actually usable.

from openssl.

baentsch avatar baentsch commented on July 21, 2024

So the full list of TLS sigalgs are the combination of these two things.

Right. One actually would only have to traverse the list of all currently active TLS_SIGALG_INFO structs -- also delivering the hashes. Let me give that a try extending the list app...

But there is currently no mechanism to query which of the "built-in" TLS sig-algs are actually usable.

Nevertheless it shows which ones may be available (in sigalg_lookup_tbl), right? And that was the original ask: How does the unwary user learn about the names of all possibly configurable (TLS) "SignatureAlgorithms". Only question in my mind right now: Can the list app get access to sigalg_lookup_tbl?

from openssl.

mattcaswell avatar mattcaswell commented on July 21, 2024

Can the list app get access to sigalg_lookup_tbl?

Unfortunately not - this is an internal global variable in libssl and is not exposed.

from openssl.

baentsch avatar baentsch commented on July 21, 2024

Can the list app get access to sigalg_lookup_tbl?

Unfortunately not - this is an internal global variable in libssl and is not exposed.

Hmm -- may I ask what you'd think about these two initial thoughts for ways how to deal with this then?

  1. Would it be OK to consider adding an API to do so, e.g., by populating a (then also publicly accessible) TLS_SIGALG_INFO list from that struct? This would arguably be a sub-optimal solution as that'd perpetuate this "internal" mechanism, though. Sub-thought: There seems to be an "apps"-based subset of the information in sigalg_lookup_tbl, namely in signature_tls13_scheme_list: Would that be something that an app listing the "built-in" TLS sigalgs could sensibly use (and maybe extend to be completely in sync with sigalg_lookup_tbl)? But duplicating this information also feels wrong (brittle code if only one place gets changed).
  2. What should happen if one queries the default provider just like a "normal" provider: Would that be a way to glean the same information as in sigalg_lookup_tbl? Or do I see it right that one first would have to enhance the "built-in" provider(s) to follow the provider documentation concerning the "TLS-SIGALG" Capability (that I created, admittedly :)? This at first glance seems doable, mirroring the logic in for TLS groups: Would this be worth while doing/a welcome enhancement in general and beyond this issue?

from openssl.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.