diff options
author | P. J. McDermott <pjm@nac.net> | 2013-11-29 18:19:19 (EST) |
---|---|---|
committer | P. J. McDermott <pjm@nac.net> | 2013-11-29 18:19:19 (EST) |
commit | 9c84a8b630df472bed071f548c51cff62b14d396 (patch) | |
tree | 01554d2bb072ce64207a1693f535720f2223af25 /lib | |
parent | 6e0853329ef855d835d0e978be35553f2896a655 (diff) |
parse_control(): Support multiple paragraphs.
Diffstat (limited to 'lib')
-rw-r--r-- | lib/control.sh | 56 |
1 files changed, 41 insertions, 15 deletions
diff --git a/lib/control.sh b/lib/control.sh index 51a7aef..9f76c67 100644 --- a/lib/control.sh +++ b/lib/control.sh @@ -29,11 +29,14 @@ control_line_nr= parse_control() { local field_cb="${2}" - local req_fields="${3}" - local opt_fields="${4}" + local paragraph_cb="${3}" + local req_fields="${4}" + local opt_fields="${5}" local all_fields= - local got_fields= + local in_paragraph= local line= + local para_req_fields= + local got_fields= local name= local value= @@ -43,17 +46,39 @@ parse_control() req_fields="$(printf '%s\n' ${req_fields})" opt_fields="$(printf '%s\n' ${opt_fields})" all_fields="${LF}${req_fields}${LF}${opt_fields}${LF}" - got_fields="${LF}" + + in_paragraph='false' while IFS='' read -r line; do control_line_nr=$(($control_line_nr + 1)) if [ "x$(echo ${line})" = 'x' ]; then - parse_control_error 'control_empty_line' + # Paragraph end. + if ${in_paragraph}; then + # The first line is blank to consolidate + # initialization code (see heredocument below). + in_paragraph='false' + if ! "${paragraph_cb}"; then + return 0 + fi + if [ "x${para_req_fields}" != 'x' ]; then + para_req_fields="$(printf "%s$(get_msg \ + 'list_item_separator')" \ + ${para_req_fields})" + parse_control_error \ + 'control_missing_fields' \ + "${para_req_fields}" + fi + fi + para_req_fields="${req_fields}" + got_fields="${LF}" + name='' + value='' elif [ "x${line#\#}" != "x${line}" ]; then # Comment. - : + in_paragraph='true' elif [ "x${line# }" = "x${line}" ]; then # "Name: Value" line. + in_paragraph='true' if [ "x${name}" != 'x' ]; then if ! "${field_cb}" "${name}" "${value}"; then return 0 @@ -66,7 +91,7 @@ parse_control() parse_control_error 'control_bad_nv' continue fi - if [ "x${req_fields}" != 'x' ]; then + if [ "x${para_req_fields}" != 'x' ]; then if [ "x${all_fields%${LF}${name}${LF}*}" = \ "x${all_fields}" ]; then # Unknown field. @@ -76,8 +101,8 @@ parse_control() else # Remove field from list of required # fields. - req_fields="$(printf '%s' \ - "${req_fields}" | \ + para_req_fields="$(printf '%s' \ + "${para_req_fields}" | \ grep -Fv "${name}")" fi fi @@ -91,6 +116,7 @@ parse_control() fi else # Continuation line. + in_paragraph='true' if [ "x${name}" = 'x' ]; then # Expecting a "Name: Value" line. parse_control_error 'control_found_continuation' @@ -99,8 +125,14 @@ parse_control() value="${value}${LF}${line# }" fi done <<-EOF + $(cat "${control_file}") + EOF + # The first blank line above triggers the paragraph end code to + # consolidate initialization code. + # The second blank line above is needed because the command substitution + # removes any trailing newlines. if [ "x${name}" != 'x' ]; then if ! "${field_cb}" "${name}" "${value}"; then @@ -108,12 +140,6 @@ parse_control() fi fi - if [ "x${req_fields}" != 'x' ]; then - req_fields="$(printf "%s$(get_msg 'list_item_separator')" \ - ${req_fields})" - parse_control_error 'control_missing_fields' "${req_fields}" - fi - return 0 } |