
namespace local = ""
default namespace mal = "http://projectmallard.org/1.0/"
start = mal_page
mal_page = element page {
  attribute id { xsd:NMTOKEN },
  attribute type { "guide" | "topic" } ?,
  attribute style { xsd:NMTOKENS } ?,
  attribute groups { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_info ?,
  mal_block_title,
  mal_block *,
  mal_section *
}

mal_section = element section {
  attribute id { xsd:ID },
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_info ?,
  mal_block_title,
  mal_block *,
  mal_section *
}

mal_info = element info {
  mal_attr_external *,

  ( mal_info_desc ? &
    mal_info_credit * &
    mal_info_license * &
    mal_info_link * &
    mal_info_title * &
    mal_info_revision * &
    mal_external *
  )
}

mal_info_credit = element credit {
  attribute type { xsd:NMTOKENS } ?,
  attribute * - (mal:* | local:*) { text } *,

  ( mal_info_name &
    mal_info_email ? &
    mal_info_years ? &
    mal_external *
  )
}

mal_info_link = element link {
  attribute type { xsd:NMTOKEN },
  ( attribute xref { text } |
    attribute href { text }
  ),
  attribute group { text } ?
  attribute * - (mal:* | local:*) { text } *,

  mal_external *
}

mal_info_title = element title {
  attribute type { xsd:NMTOKEN },
  attribute role { xsd:NMTOKEN } ?,
  attribute * - (mal:* | local:*) { text } *,

  mal_inline
}

mal_info_license = element license {
  attribute href { text } ?,
  attribute * - (mal:* | local:*) { text } *,

  mal_block +
}

mal_info_desc = element desc {
  attribute * - (mal:* | local:*) { text } *,

  mal_inline
}

mal_info_revision = element revision {
  attribute version { text } ?,
  attribute docversion { text } ?,
  attribute pkgversion { text } ?,
  attribute date { xsd:date } ?,
  attribute status {
    "stub"   | "incomplete" | "draft" | "outdated" |
    "review" | "candidate"  | "final" } ?,
  attribute * - (mal:* | local:*) { text } *,

  mal_block_title ?,
  mal_block_desc ?,
  mal_external *
}

mal_info_years = element years {
  attribute * - (mal:* | local:*) { text } *,
  mal_inline
}

mal_info_email = element email {
  attribute * - (mal:* | local:*) { text } *,
  mal_inline
}

mal_info_name = element name {
  attribute * - (mal:* | local:*) { text } *,
  mal_inline
}

mal_block = (
  mal_block_basic |
  mal_block_formal |
  mal_block_lists |
  mal_table
)

mal_block_basic = (
  mal_block_code |
  mal_block_example |
  mal_block_media |
  mal_block_p |
  mal_block_screen
)
mal_block_formal = (
  mal_block_comment |
  mal_block_figure |
  mal_block_listing |
  mal_block_note |
  mal_block_quote |
  mal_block_synopsis
)
mal_block_lists = (
  mal_block_list |
  mal_block_steps |
  mal_block_terms |
  mal_block_tree
)
mal_block_code = element code {
  attribute style { xsd:NMTOKENS } ?,
  attribute mime { text } ?,
  mal_attr_external *,

  mal_inline
}

mal_block_example = element example {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block +
}

mal_block_media = element media {
  attribute type { "image" | "video" | "audio" | "application" } ?,
  attribute mime { text } ?,
  attribute src { text },
  attribute height { text } ?,
  attribute width { text } ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block *
}

mal_block_p = element p {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_block_screen = element screen {
  attribute style { xsd:NMTOKENS } ?,
  attribute mime { text } ?,
  mal_attr_external *,

  mal_inline
}

mal_block_quote = element quote {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block_title ?,
  mal_block_cite,
  mal_block +
}

mal_block_comment = element comment {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block_title ?,
  mal_block_cite,
  mal_block +
}

mal_block_figure = element figure {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block_title ?,
  mal_block_desc ?,
  mal_block +
}

mal_block_listing = element listing {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block_title ?,
  mal_block_desc ?,
  mal_block +
}

mal_block_note = element note {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block_title ?,
  mal_block +
}

mal_block_synopsis = element synopsis {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block_title ?,
  mal_block_desc ?,
  mal_block +
}

mal_block_list = element list {
  attribute type { xsd:NMTOKEN } ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block_title ?,
  mal_block_list_item +
}
mal_block_list_item = element item {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block +
}

mal_block_terms = element terms {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block_title ?,
  mal_block_terms_item +
}
mal_block_terms_item = element item {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block_title +,
  mal_block +
}

mal_block_steps = element steps {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block_title ?,
  mal_block_steps_item +
}
mal_block_steps_item = element item {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block +
}

mal_block_tree = element tree {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_block_title ?,
  mal_block_tree_item +
}
mal_block_tree_item = element item {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline,
  mal_block_tree_item *
}

mal_table_col = element col {
  attribute style { xsd:NMTOKENS } ?,
  attribute * - (mal:* | local:*) { text } *
}
mal_table_colgroup = element colgroup {
  attribute style { xsd:NMTOKENS } ?,
  attribute * - (mal:* | local:*) { text } *,

  mal_table_col *
}

mal_table_tr = element tr {
  attribute style { xsd:NMTOKENS } ?,
  attribute * - (mal:* | local:*) { text } *,

  mal_table_td *
}
mal_table_thead = element thead {
  attribute style { xsd:NMTOKENS } ?,
  attribute * - (mal:* | local:*) { text } *,

  mal_table_tr +
}
mal_table_tbody = element tbody {
  attribute style { xsd:NMTOKENS } ?,
  attribute * - (mal:* | local:*) { text } *,

  mal_table_tr +
}
mal_table_tfoot = element tfoot {
  attribute style { xsd:NMTOKENS } ?,
  attribute * - (mal:* | local:*) { text } *,

  mal_table_tr +
}

mal_table_td = element td {
  attribute style { xsd:NMTOKENS } ?,
  attribute * - (mal:* | local:*) { text } *,
  attribute rowspan { text } ?,
  attribute colspan { text } ?,

  mal_block +
}

mal_table = element table {
  attribute style { xsd:NMTOKENS } ?,
  attribute * - (mal:* | local:*) { text } *,
  attribute frame {
    "all" | "none" |
    list { ("top" | "bottom" | "left" | "right") * }
  } ?,
  attribute rules {
    "all" | "groups" | "none" |
    list { ("rows" | "rowgroups" | "cols" | "colgroups") * }
  } ?,
  attribute shade {
    "all" | "groups" | "none" |
    list { ("rows" | "rowgroups" | "cols" | "colgroups") * }
  } ?,

  mal_block_title ?,
  mal_block_desc ?,

  ( mal_table_col + |
    mal_table_colgroup +
  ) ?,

  ( mal_table_tr + |
    ( mal_table_thead ?,
      mal_table_tbody +,
      mal_table_tfoot ?
    )
  )
}

mal_block_desc = element desc {
  attribute style { xsd:NMTOKENS } ?,
  attribute * - (mal:* | local:*) { text } *,

  mal_inline
}

mal_block_cite = element cite {
  attribute style { xsd:NMTOKENS } ?,
  attribute * - (mal:* | local:*) { text } *,
  attribute date { text } ?,
  attribute href { text } ?,

  mal_inline
}

mal_block_subtitle = element subtitle {
  mal_inline
}

mal_block_title = element title {
  mal_inline
}

mal_inline = {
  mal_inline_app * &
  mal_inline_cmd * &
  mal_inline_code * &
  mal_inline_em * &
  mal_inline_file * &
  mal_inline_gui * &
  mal_inline_guiseq * &
  mal_inline_input * &
  mal_inline_key * &
  mal_inline_keyseq * &
  mal_inline_link * &
  mal_inline_media * &
  mal_inline_output * &
  mal_inline_span * &
  mal_inline_sys * &
  mal_inline_var * &
  element * - (mal:* | local:*) { mal_inline } * &
  text ?
}

mal_inline_app = element app {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_code = element code {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  attribute mime { text } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_cmd = element cmd {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  attribute mime { text } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_output = element output {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_em = element em {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_file = element file {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_gui = element gui {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_guiseq = element guiseq {
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mixed { mal_inline_gui + }
}

mal_inline_link = element link {
  ( attribute xref { text } |
    attribute href { text } |
    ( attribute xref { text }, attribute href { text } )
  ),
  attribute role { text } ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_media = element media {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  attribute type { "image" | "video" | "audio" | "application" } ?,
  attribute mime { text } ?,
  attribute src { text },
  attribute height { text } ?,
  attribute width { text } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_keyseq = element keyseq {
  attribute style { xsd:NMTOKENS } ?,
  attribute type { "combo" | "sequence" } ?,
  mal_attr_external *,

  mixed {
    (mal_inline_key | mal_inline_keyseq) *
  }
}

mal_inline_key = element key {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_span = element span {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_sys = element sys {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_input = element input {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_inline_var = element var {
  mal_attr_link ?,
  attribute style { xsd:NMTOKENS } ?,
  mal_attr_external *,

  mal_inline
}

mal_external = element * - (mal:* | local:*) {
  attribute * { text } *,
  mal_anything *
}
mal_anything = element * {
  attribute * { text } *,
  mal_anything *
}
mal_attr_external = attribute * - (mal:* | local:*) { text }

mal_attr_link =
  ( attribute xref { text } ?
  | { attribute dref { text } ?, attribute href { text } ? }
  )
