The syntax of Icon in Backus-Naur form

Course links

<program> ::= {<declaration>}+

<declaration> ::= <global-declaration>
                | <invocable-declaration>
                | <link-declaration>
                | <procedure-declaration>
                | <record-declaration>

<global-declaration> ::= "global" <identifier-list>

<identifier-list> ::= <identifier>
                    | <identifier> "," <identifier-list>

<invocable-declaration> ::= "invocable" "all"
                          | "invocable" <proc-list>

<proc-list> ::= <string-literal>
              | <string-literal> "," <proc-list>

<link-declaration> ::= "link" <link-list>

<link-list> ::= <file-name>
              | <file-name> "," <link-list>

<file-name> ::= <identifier>
              | <string-literal>

<procedure-declaration> ::= <header> <locals> {<initial-clause>}* <expressions> "end"

<header> ::= "procedure" <identifier> "(" <identifiers> ")"
           | "procedure" <identifier> "(" {<identifier> ","}* <identifier> "[" "]" ")"

<identifiers> ::= {<identifier> {"," <identifier>}*}?

<locals> ::= {<local-specification> <identifier-list> {"," <local-specification> <identifier-list>}*}?

<local-specification> ::= "local"
                        | "static"

<initial-clause> ::= "initial" <expression> ";"

<expressions> ::= {<expression> ";" {<expression>}*}?

<expression> ::= <parenthesized-expression>
               | <compound-expression> 
               | <list-expression> 
               | <field-reference-expression> 
               | <subscripting-expression> 
               | <invocation-expression> 
               | <mutual-evaluation-expression> 
               | <prefix-expression> 
               | <infix-expression> 
               | <to-by-expression> 
               | <create-expression> 
               | <return-expression> 
               | <break-expression> 
               | <next-expression> 
               | <case-expression> 
               | <if-then-else-expression> 
               | <loop-expression> 
               | <identifier>
               | <keyword>
               | <literal>

<parenthesized-expression> ::= "(" {<expression>}? ")"

<compound-expression> ::= "{" <expressions> "}"

<list-expression> ::= "[" <expression-list> "]"

<expression-list> ::= {<expression-or-comma>}*

<expression-or-comma> ::= <expression>
                        | ","

<field-reference-expression> ::= <expression> "." <field-name>

<field-name> ::= <identifier>

<subscripting-expression> ::= <expression> "[" <expression-list> "]"
                            | <expression> "[" <range-specification> "]"

<range-specification> ::= <expression> ":" <expression>
                        | <expression> "+:" <expression>
                        | <expression> "-:" <expression>

<invocation-expression> ::= {<expression>}? "(" <expression-list> ")"
                          | {<expression>}? "{" <expression-list> "}"

<mutual-evaluation-expression> ::= "(" <expression-list> ")"

<prefix-expression> ::= <prefix-operator> <expression>

<prefix-operator> ::= "+"
                    | "-"
                    | "~"
                    | "="
                    | "@"
                    | "^"
                    | "*"
                    | "?"
                    | "!"
                    | "/"
                    | "\"
                    | "."

<infix-expression> ::= <expression> <infix-operator> <expression>

<infix-operator> ::= "+"
                   | "-"
                   | "*"
                   | "/"
                   | "%"
                   | "^"
                   | "++"
                   | "--"
                   | "**"
                   | "||"
                   | "|||"
                   | "."
                   | "@"
                   | "&"
                   | ">"
                   | ">="
                   | "="
                   | "<="
                   | "<"
                   | "~="
                   | ">>"
                   | ">>="
                   | "=="
                   | "<<="
                   | "<<"
                   | "~=="
                   | "==="
                   | "~==="
                   | ":="
                   | "+:="
                   | "-:="
                   | "*:="
                   | "/:="
                   | "%:="
                   | "^:="
                   | "++:="
                   | "--:="
                   | "**:="
                   | "||:="
                   | "|||:="
                   | ".:="
                   | "@:="
                   | "&:="
                   | ">:="
                   | ">=:="
                   | "=:="
                   | "<=:="
                   | "<:="
                   | "~=:="
                   | ">>:="
                   | ">>=:="
                   | "==:="
                   | "<<=:="
                   | "<<:="
                   | "~==:="
                   | "===:="
                   | "~===:="
                   | ":=:"
                   | "<-"
                   | "<->"
                   | "!"

<to-by-expression> ::= <expression> "to" <expression> {<by-clause>}?

<by-clause> ::= "by" <expression>

<create-expression> ::= "create" <expression>

<return-expression> ::= "return" {<expression>}?
                      | "suspend" {<expression>}? {<do-clause>}?
                      | "fail"

<do-clause> ::= "do" <expression>

<break-expression> ::= "break" {<expression>}?

<next-expression> ::= "next"

<case-expression> ::= "case" <expression> "of" "{" <case-list> "}"

<case-list> ::= <case-clause>
              | <case-clause> ";" <case-list>

<case-clause> ::= <expression> ":" <expression>
                | "default" ":" <expression>

<if-then-else-expression> ::= "if" <expression> "then" <expression> {<else-clause>}?

<else-expression> ::= "else" <expression>

<loop-expression> ::= "repeat" <expression>
                    | "while" <expression> {<do-clause>}?
                    | "until" <expression> {<do-clause>}?
                    | "every" <expression> {<do-clause>}?

<record-declaration> ::= "record" <identifier> "(" <field-names> ")"

<field-names> ::= {<field-name> {"," <field-name>}*}?

This grammar was adapted from the one in appendix A of The Icon programming language, third edition, by Ralph E. Griswold and Madge T. Griswold (San Jose, California: Peer-to-Peer Communications, 1997; ISBN 1-57389-001-3), pages 247-251.