(module
  (@a)
  (@0)
  (@aas-3!@$d-@#4)
  (@@) (@$) (@+) (@0) (@.) (@!$@#$23414@#$)
  (@"a")
  (@" @ asd\2a 045 \" fdaf \t \u{45}")

  (@a x y z)
  (@a x-y $yz "aa" -2 0.3 0x3)
  (@a x-y$yz"aa"-2)
  (@a block func module i32.add)
  (@a 0x 8q 0xfa #4g0-.@f#^&@#$*0sf -- @#)
  (@a , ; ] [ }} }x{ ({) ,{{};}] ;)
  (@a (bla) () (5-g) ("aa" a) ($x) (bla bla) (x (y)) ")" "(" x")"y)
  (@a @ @x (@x) (@x y) (@) (@ x) (@(@(@(@)))))
  (@a (;bla;) (; ) ;)
    ;; bla)
    ;; bla (@x
  )
)

(assert_malformed (module quote "(@a \00)") "illegal character")
(assert_malformed (module quote "(@a \01)") "illegal character")
(assert_malformed (module quote "(@a \02)") "illegal character")
(assert_malformed (module quote "(@a \03)") "illegal character")
(assert_malformed (module quote "(@a \04)") "illegal character")
(assert_malformed (module quote "(@a \05)") "illegal character")
(assert_malformed (module quote "(@a \06)") "illegal character")
(assert_malformed (module quote "(@a \07)") "illegal character")
(assert_malformed (module quote "(@a \08)") "illegal character")
(module quote "(@a \09)")  ;; \t
(module quote "(@a \0a)")  ;; \n
(assert_malformed (module quote "(@a \0b)") "illegal character")
(assert_malformed (module quote "(@a \0c)") "illegal character")
(module quote "(@a \0d)")  ;; \r
(assert_malformed (module quote "(@a \0e)") "illegal character")
(assert_malformed (module quote "(@a \0f)") "illegal character")
(assert_malformed (module quote "(@a \10)") "illegal character")
(assert_malformed (module quote "(@a \11)") "illegal character")
(assert_malformed (module quote "(@a \12)") "illegal character")
(assert_malformed (module quote "(@a \13)") "illegal character")
(assert_malformed (module quote "(@a \14)") "illegal character")
(assert_malformed (module quote "(@a \15)") "illegal character")
(assert_malformed (module quote "(@a \16)") "illegal character")
(assert_malformed (module quote "(@a \17)") "illegal character")
(assert_malformed (module quote "(@a \18)") "illegal character")
(assert_malformed (module quote "(@a \19)") "illegal character")
(assert_malformed (module quote "(@a \1a)") "illegal character")
(assert_malformed (module quote "(@a \1b)") "illegal character")
(assert_malformed (module quote "(@a \1c)") "illegal character")
(assert_malformed (module quote "(@a \1d)") "illegal character")
(assert_malformed (module quote "(@a \1e)") "illegal character")
(assert_malformed (module quote "(@a \1f)") "illegal character")
(module quote "(@a \20)")  ;; space
(assert_malformed (module quote "(@a \7f)") "illegal character")
(assert_malformed (module quote "(@a \80)") "malformed UTF-8 encoding")
(assert_malformed (module quote "(@a \81)") "malformed UTF-8 encoding")
(assert_malformed (module quote "(@a \90)") "malformed UTF-8 encoding")
(assert_malformed (module quote "(@a \a0)") "malformed UTF-8 encoding")
(assert_malformed (module quote "(@a \b0)") "malformed UTF-8 encoding")
(assert_malformed (module quote "(@a \c0)") "malformed UTF-8 encoding")
(assert_malformed (module quote "(@a \d0)") "malformed UTF-8 encoding")
(assert_malformed (module quote "(@a \e0)") "malformed UTF-8 encoding")
(assert_malformed (module quote "(@a \f0)") "malformed UTF-8 encoding")
(assert_malformed (module quote "(@a \ff)") "malformed UTF-8 encoding")
(assert_malformed (module quote "(@a Heiße Würstchen)") "illegal character")
(assert_malformed (module quote "(@a )") "illegal character")

(assert_malformed (module quote "( @a)") "unknown operator")

(assert_malformed (module quote "(@)") "empty annotation id")
(assert_malformed (module quote "(@ )") "empty annotation id")
(assert_malformed (module quote "(@ x)") "empty annotation id")
(assert_malformed (module quote "(@(@a)x)") "empty annotation id")
(assert_malformed (module quote "(@\"\")") "empty annotation id")
(assert_malformed (module quote "(@ \"a\")") "empty annotation id")
(assert_malformed (module quote "(@\"\n\")") "empty annotation id")
(assert_malformed (module quote "(@\"\\ef\")") "malformed UTF-8")

(assert_malformed (module quote "(@x ") "unclosed annotation")
(assert_malformed (module quote "(@x ()") "unclosed annotation")
(assert_malformed (module quote "(@x (y (z))") "unclosed annotation")
(assert_malformed (module quote "(@x (@y )") "unclosed annotation")

(assert_malformed (module quote "(@x))") "unexpected token")
(assert_malformed (module quote "(@x ()))") "unexpected token")
(assert_malformed (module quote "(@x (y (z))))") "unexpected token")
(assert_malformed (module quote "(@x (@y )))") "unexpected token")

(assert_malformed (module quote "(@x \"") "unclosed string")
(assert_malformed (module quote "(@x \")") "unclosed string")

(assert_malformed (module quote "((@a)@b)") "unknown operator")
(assert_malformed (module quote "(func $(@a))") "empty identifier")
(assert_malformed (module quote "(func $(@a)f)") "empty identifier")

((@a) module (@a) $m (@a) (@a)
  ((@a) import (@a) "spectest" (@a) "global_i32" (@a)
    ((@a) global (@a) $g (@a) i32 (@a)) (@a)
  ) (@a)
  ((@a) import (@a) "spectest" (@a) "table" (@a)
    ((@a) table (@a) $t (@a) 10 (@a) 20 (@a) funcref (@a)) (@a)
  ) (@a)
  ((@a) import (@a) "spectest" (@a) "memory" (@a)
    ((@a) memory (@a) $m (@a) 1 (@a) 2 (@a)) (@a)
  ) (@a)
  ((@a) import (@a) "spectest" (@a) "print_i32_f32" (@a)
    ((@a) func (@a) $f (@a)
      ((@a) param (@a) i32 (@a) f32 (@a)) (@a)
      ((@a) result (@a)) (@a)
    ) (@a)
  ) (@a)

  ((@a) export (@a) "g" (@a)
    ((@a) global (@a) $g (@a)) (@a)
  ) (@a)
  ((@a) export (@a) "t" (@a)
    ((@a) table (@a) $t (@a)) (@a)
  ) (@a)
  ((@a) export (@a) "m" (@a)
    ((@a) memory (@a) $m (@a)) (@a)
  ) (@a)
  ((@a) export (@a) "f" (@a)
    ((@a) func (@a) $f (@a)) (@a)
  ) (@a)
)

((@a) module (@a) $m1 (@a) (@a)
  ((@a) global (@a) $g (@a)
    ((@a) export (@a) "g" (@a)) (@a)
    ((@a) import (@a) "spectest" (@a) "global_i32" (@a)) (@a)
    i32 (@a)
  ) (@a)
  ((@a) table (@a) $t (@a)
    ((@a) export (@a) "t" (@a)) (@a)
    ((@a) import (@a) "spectest" (@a) "table" (@a)) (@a)
    10 (@a) 20 (@a)
    funcref (@a)
  ) (@a)
  ((@a) memory (@a) $m (@a)
    ((@a) export (@a) "m" (@a)) (@a)
    ((@a) import (@a) "spectest" (@a) "memory" (@a)) (@a)
    1 (@a) 2 (@a)
  ) (@a)
  ((@a) func (@a) $f (@a)
    ((@a) export (@a) "f" (@a)) (@a)
    ((@a) import (@a) "spectest" (@a) "print_i32_f32" (@a)) (@a)
    ((@a) param (@a) i32 (@a) f32 (@a)) (@a)
    ((@a) result (@a)) (@a)
  ) (@a)
)

((@a) module (@a) $m2 (@a) (@a)
  ((@a) type (@a) $T (@a)
    ((@a) func (@a)
      ((@a) param (@a) i32 (@a) i64 (@a)) (@a)
      ((@a) param (@a) $x (@a) i32 (@a)) (@a)
      ((@a) result (@a) i32 (@a)) (@a)
    ) (@a)
  ) (@a)

  ((@a) global (@a) $g (@a)
    ((@a) export (@a) "g" (@a)) (@a)
    i32 (@a)
    ((@a) i32.const (@a) 42 (@a)) (@a)
  ) (@a)
  ((@a) table (@a) $t (@a)
    ((@a) export (@a) "t" (@a)) (@a)
    10 (@a) 20 (@a)
    funcref (@a)
  ) (@a)
  ((@a) memory (@a) $m (@a)
    ((@a) export (@a) "m" (@a)) (@a)
    1 (@a) 2 (@a)
  ) (@a)
  ((@a) func (@a) $f (@a)
    ((@a) export (@a) "f" (@a)) (@a)
    ((@a) param (@a) i32 (@a) i64 (@a)) (@a)
    ((@a) param (@a) $x (@a) i32 (@a)) (@a)
    ((@a) result (@a) i32 (@a)) (@a)
    ((@a) local (@a) i32 (@a) i32 (@a)) (@a)
    ((@a) local (@a) $y (@a) i32 (@a)) (@a)
    ((@a) block (@a)
      ((@a) result (@a) i32 (@a)) (@a)
      ((@a) i32.add (@a)
        ((@a) local.get (@a) $x (@a)) (@a)
        ((@a) local.get (@a) 0 (@a)) (@a)
      )
    )
  ) (@a)

  ((@a) elem (@a)
    ((@a) offset (@a) ((@a) i32.const (@a) 0 (@a)) (@a)) (@a)
    $f (@a) $f (@a) (@a) $f (@a)
  ) (@a)
  ((@a) data (@a)
    ((@a) offset (@a) ((@a) i32.const (@a) 0 (@a)) (@a)) (@a)
    "bla" (@a) "\43" (@a) (@a) "" (@a)
  ) (@a)

  (func $s)
  ((@a) start (@a) $s (@a)) (@a)
)

(module quote "(@a) (func)")
(module quote "(func) (@a)")
