in source/aws_profile.c [849:964]
static bool s_parse_profile_declaration(
const struct aws_byte_cursor *line_cursor,
struct profile_file_parse_context *context) {
/*
* Strip comment and right-side whitespace
*/
struct aws_byte_cursor profile_line_cursor = s_trim_trailing_comment(line_cursor);
struct aws_byte_cursor profile_cursor = aws_byte_cursor_right_trim_pred(&profile_line_cursor, s_is_whitespace);
/*
* "[" + <whitespace>? + <"profile ">? + <profile name = identifier> + <whitespace>? + "]"
*/
if (!s_parse_by_character_predicate(&profile_cursor, s_is_profile_start, NULL, 1)) {
/*
* This isn't a profile declaration, try something else
*/
return false;
}
context->has_seen_profile = true;
context->current_profile = NULL;
context->current_property = NULL;
s_parse_by_character_predicate(&profile_cursor, s_is_whitespace, NULL, 0);
/*
* Check if the profile name starts with the 'profile' keyword. We need to check for
* "profile" and at least one whitespace character. A partial match
* ("[profilefoo]" for example) should rewind and use the whole name properly.
*/
struct aws_byte_cursor backtrack_cursor = profile_cursor;
bool has_profile_prefix = s_parse_by_token(&profile_cursor, s_profile_token, NULL) &&
s_parse_by_character_predicate(&profile_cursor, s_is_whitespace, NULL, 1);
if (has_profile_prefix) {
if (context->profile_collection->profile_source == AWS_PST_CREDENTIALS) {
AWS_LOGF_WARN(
AWS_LS_SDKUTILS_PROFILE,
"Profile declarations in credentials files are not allowed to begin with the \"profile\" keyword");
s_log_parse_context(AWS_LL_WARN, context);
context->parse_error = AWS_ERROR_SDKUTILS_PARSE_RECOVERABLE;
return true;
}
s_parse_by_character_predicate(&profile_cursor, s_is_whitespace, NULL, 0);
} else {
profile_cursor = backtrack_cursor;
}
struct aws_byte_cursor profile_name;
if (!s_parse_by_character_predicate(&profile_cursor, s_is_identifier, &profile_name, 0)) {
AWS_LOGF_WARN(AWS_LS_SDKUTILS_PROFILE, "Profile declarations must contain a valid identifier for a name");
s_log_parse_context(AWS_LL_WARN, context);
context->parse_error = AWS_ERROR_SDKUTILS_PARSE_RECOVERABLE;
return true;
}
if (context->profile_collection->profile_source == AWS_PST_CONFIG && !has_profile_prefix &&
!s_is_default_profile_name(&profile_name)) {
AWS_LOGF_WARN(
AWS_LS_SDKUTILS_PROFILE,
"Non-default profile declarations in config files must use the \"profile\" keyword");
s_log_parse_context(AWS_LL_WARN, context);
context->parse_error = AWS_ERROR_SDKUTILS_PARSE_RECOVERABLE;
return true;
}
s_parse_by_character_predicate(&profile_cursor, s_is_whitespace, NULL, 0);
/*
* Special case the right side bracket check. We need to distinguish between a missing right bracket
* (fatal error) and invalid profile name (spaces, non-identifier characters).
*
* Do so by consuming all non right-bracket characters. If the remainder is empty it is missing,
* otherwise it is an invalid profile name (non-empty invalid_chars) or a good definition
* (empty invalid_chars cursor).
*/
struct aws_byte_cursor invalid_chars;
s_parse_by_character_predicate(&profile_cursor, s_is_not_profile_end, &invalid_chars, 0);
if (profile_cursor.len == 0) {
AWS_LOGF_WARN(AWS_LS_SDKUTILS_PROFILE, "Profile declaration missing required ending bracket");
s_log_parse_context(AWS_LL_WARN, context);
context->parse_error = AWS_ERROR_SDKUTILS_PARSE_FATAL;
return true;
}
if (invalid_chars.len > 0) {
AWS_LOGF_WARN(
AWS_LS_SDKUTILS_PROFILE,
"Profile declaration contains invalid characters: \"" PRInSTR "\"",
AWS_BYTE_CURSOR_PRI(invalid_chars));
s_log_parse_context(AWS_LL_WARN, context);
context->parse_error = AWS_ERROR_SDKUTILS_PARSE_RECOVERABLE;
return true;
}
/*
* Apply to the profile collection
*/
if (s_profile_collection_add_profile(
context->profile_collection, &profile_name, has_profile_prefix, context, &context->current_profile)) {
AWS_LOGF_ERROR(AWS_LS_SDKUTILS_PROFILE, "Failed to add profile to profile collection");
s_log_parse_context(AWS_LL_ERROR, context);
context->parse_error = AWS_ERROR_SDKUTILS_PARSE_FATAL;
return true;
}
return true;
}