diff options
Diffstat (limited to 'src/shared/machine-credential.c')
-rw-r--r-- | src/shared/machine-credential.c | 100 |
1 files changed, 52 insertions, 48 deletions
diff --git a/src/shared/machine-credential.c b/src/shared/machine-credential.c index 17f7afc..c1e76e4 100644 --- a/src/shared/machine-credential.c +++ b/src/shared/machine-credential.c @@ -19,76 +19,82 @@ static void machine_credential_done(MachineCredential *cred) { cred->size = 0; } -void machine_credential_free_all(MachineCredential *creds, size_t n) { - assert(creds || n == 0); +void machine_credential_context_done(MachineCredentialContext *ctx) { + assert(ctx); - FOREACH_ARRAY(cred, creds, n) + FOREACH_ARRAY(cred, ctx->credentials, ctx->n_credentials) machine_credential_done(cred); - free(creds); + free(ctx->credentials); } -int machine_credential_set(MachineCredential **credentials, size_t *n_credentials, const char *cred_string) { - _cleanup_free_ char *word = NULL, *data = NULL; +bool machine_credentials_contains(const MachineCredentialContext *ctx, const char *id) { + assert(ctx); + assert(id); + + FOREACH_ARRAY(cred, ctx->credentials, ctx->n_credentials) + if (streq(cred->id, id)) + return true; + + return false; +} + +int machine_credential_set(MachineCredentialContext *ctx, const char *cred_str) { + _cleanup_(machine_credential_done) MachineCredential cred = {}; ssize_t l; int r; - const char *p = ASSERT_PTR(cred_string); - assert(credentials && n_credentials); - assert(*credentials || *n_credentials == 0); + assert(ctx); - r = extract_first_word(&p, &word, ":", EXTRACT_DONT_COALESCE_SEPARATORS); + const char *p = ASSERT_PTR(cred_str); + + r = extract_first_word(&p, &cred.id, ":", EXTRACT_DONT_COALESCE_SEPARATORS); if (r < 0) return log_error_errno(r, "Failed to parse --set-credential= parameter: %m"); if (r == 0 || !p) - return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Missing value for --set-credential=: %s", cred_string); + return log_error_errno(SYNTHETIC_ERRNO(EINVAL), + "Missing value for --set-credential=: %s", cred_str); - if (!credential_name_valid(word)) - return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Credential name is not valid: %s", word); + if (!credential_name_valid(cred.id)) + return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Credential name is not valid: %s", cred.id); - FOREACH_ARRAY(cred, *credentials, *n_credentials) - if (streq(cred->id, word)) - return log_error_errno(SYNTHETIC_ERRNO(EEXIST), "Duplicate credential '%s', refusing.", word); + if (machine_credentials_contains(ctx, cred.id)) + return log_error_errno(SYNTHETIC_ERRNO(EEXIST), "Duplicate credential '%s', refusing.", cred.id); - l = cunescape(p, UNESCAPE_ACCEPT_NUL, &data); + l = cunescape(p, UNESCAPE_ACCEPT_NUL, &cred.data); if (l < 0) return log_error_errno(l, "Failed to unescape credential data: %s", p); + cred.size = l; - if (!GREEDY_REALLOC(*credentials, *n_credentials + 1)) + if (!GREEDY_REALLOC(ctx->credentials, ctx->n_credentials + 1)) return log_oom(); - (*credentials)[(*n_credentials)++] = (MachineCredential) { - .id = TAKE_PTR(word), - .data = TAKE_PTR(data), - .size = l, - }; + ctx->credentials[ctx->n_credentials++] = TAKE_STRUCT(cred); return 0; } -int machine_credential_load(MachineCredential **credentials, size_t *n_credentials, const char *cred_path) { +int machine_credential_load(MachineCredentialContext *ctx, const char *cred_path) { + _cleanup_(machine_credential_done) MachineCredential cred = {}; + _cleanup_free_ char *path_alloc = NULL; ReadFullFileFlags flags = READ_FULL_FILE_SECURE; - _cleanup_(erase_and_freep) char *data = NULL; - _cleanup_free_ char *word = NULL, *j = NULL; - const char *p = ASSERT_PTR(cred_path); - size_t size; int r; - assert(credentials && n_credentials); - assert(*credentials || *n_credentials == 0); + assert(ctx); + + const char *p = ASSERT_PTR(cred_path); - r = extract_first_word(&p, &word, ":", EXTRACT_DONT_COALESCE_SEPARATORS); + r = extract_first_word(&p, &cred.id, ":", EXTRACT_DONT_COALESCE_SEPARATORS); if (r < 0) return log_error_errno(r, "Failed to parse --load-credential= parameter: %m"); if (r == 0 || !p) return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Missing value for --load-credential=: %s", cred_path); - if (!credential_name_valid(word)) - return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Credential name is not valid: %s", word); + if (!credential_name_valid(cred.id)) + return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Credential name is not valid: %s", cred.id); - FOREACH_ARRAY(cred, *credentials, *n_credentials) - if (streq(cred->id, word)) - return log_error_errno(SYNTHETIC_ERRNO(EEXIST), "Duplicate credential '%s', refusing.", word); + if (machine_credentials_contains(ctx, cred.id)) + return log_error_errno(SYNTHETIC_ERRNO(EEXIST), "Duplicate credential '%s', refusing.", cred.id); if (is_path(p) && path_is_valid(p)) flags |= READ_FULL_FILE_CONNECT_SOCKET; @@ -97,31 +103,29 @@ int machine_credential_load(MachineCredential **credentials, size_t *n_credentia r = get_credentials_dir(&e); if (r < 0) - return log_error_errno(r, "Credential not available (no credentials passed at all): %s", word); + return log_error_errno(r, + "Credential not available (no credentials passed at all): %s", cred.id); - j = path_join(e, p); - if (!j) + path_alloc = path_join(e, p); + if (!path_alloc) return log_oom(); - p = j; + p = path_alloc; } else - return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Credential source appears to be neither a valid path nor a credential name: %s", p); + return log_error_errno(SYNTHETIC_ERRNO(EINVAL), + "Credential source appears to be neither a valid path nor a credential name: %s", p); r = read_full_file_full(AT_FDCWD, p, UINT64_MAX, SIZE_MAX, flags, NULL, - &data, &size); + &cred.data, &cred.size); if (r < 0) return log_error_errno(r, "Failed to read credential '%s': %m", p); - if (!GREEDY_REALLOC(*credentials, *n_credentials + 1)) + if (!GREEDY_REALLOC(ctx->credentials, ctx->n_credentials + 1)) return log_oom(); - (*credentials)[(*n_credentials)++] = (MachineCredential) { - .id = TAKE_PTR(word), - .data = TAKE_PTR(data), - .size = size, - }; + ctx->credentials[ctx->n_credentials++] = TAKE_STRUCT(cred); return 0; } |