From ee8a8866321adbc02629945bfb1b7ddbf47d5c40 Mon Sep 17 00:00:00 2001 From: "O'Keefe, Colin B" Date: Tue, 20 Feb 2024 12:08:50 -0800 Subject: [PATCH 1/4] Include Extern specification --- grammars/Quil.g4 | 11 +++- specgen/spec/sec-other.s | 109 +++++++++++++++++++++++++++++++++++ specgen/spec/sec-structure.s | 2 + 3 files changed, 121 insertions(+), 1 deletion(-) diff --git a/grammars/Quil.g4 b/grammars/Quil.g4 index 7b5918f..783140b 100644 --- a/grammars/Quil.g4 +++ b/grammars/Quil.g4 @@ -29,6 +29,8 @@ instr : gate | include | pragma | memoryDescriptor + | extern + | call ; // C. Static and Parametric Gates @@ -118,6 +120,13 @@ include : INCLUDE STRING ; pragma : PRAGMA IDENTIFIER pragma_name* STRING? ; pragma_name : IDENTIFIER | INT ; + +// N. Declaring and Calling External Functions + +extern : EXTERN IDENTIFIER ; +call : CALL IDENTIFIER call_arg+ ; +call_arg : addr | number ; + // Expressions (in order of precedence) expression : LPAREN expression RPAREN #parenthesisExp @@ -131,7 +140,7 @@ expression : LPAREN expression RPAREN #parenthesisExp | addr #addrExp ; -function : SIN | COS | SQRT | EXP | CIS ; +function : SIN | COS | SQRT | EXP | CIS | IDENTIFIER; sign : PLUS | MINUS ; // Numbers diff --git a/specgen/spec/sec-other.s b/specgen/spec/sec-other.s index b5a8201..251ac98 100644 --- a/specgen/spec/sec-other.s +++ b/specgen/spec/sec-other.s @@ -22,11 +22,120 @@ semantics.} PRAGMA @ms{Identifier} @rep{@group{@ms{Identifier} @alt @ms{Integer}}} @rep[:max 1]{@ms{String}} } + +@subsection[:title "Extern Functions"] + +@p{Programmers and researchers may wish to avail themselves of a rich +vocabulary of analytic and stochastic functions in the designs of +their experiments and algorithms. Quantum control systems or quantum +simulators that consume Quil code may support a variety of functions +that operate on classical data. Quil addresses these cases by +supporting the declaration of extern functions.} + +@subsubsection[:title "Declaring Externs"] + +@p{Declaring an identifier to be an extern indicates that the +identifier can appear in call instructions.} + +@syntax[:name "Extern Function Declaration"]{ + EXTERN @ms{Identifier} +} + +@subsubsection[:title "Extern Signature Pragmas"] + +@p{Under some circumstances it may be desirable to specify the +function signature of an external function. Signature declarations are +supplied by way of a special pragma.} + +@syntax[:name "Extern Signature Pragma"]{ + PRAGMA EXTERN @ms{Identifier} "@ms{Extern Signature}" +} + +@syntax[:name "Extern Signature"]{ + @rep[:min 0 :max 1]{@ms{Base Type}} ( @ms{Extern Parameter} @rep[:min 0]{@group{ , @ms{Extern Parameter} }} ) +} + +@syntax[:name "Extern Parameter"]{ + @ms{Identifier} : @rep[:min 0 :max 1]{mut} @ms{Type} +} + +@subsubsection[:title "Call Instructions"] + +@p{Declared externs may be appear in call instructions. The precise +meaning of an extern call is left up to the implementor. From the +perspective of the abstract machine, a call to an external function +increments the program counter and has some effect on classical +memory.} + +@syntax[:name "Extern Call Instruction"]{ + CALL @ms{Identifier} @rep[:min 1]{@group{@ms{Identifier} @alt @ms{Memory Reference} @alt @ms{Complex}}} +} + +@p{When a supplied function type signature specifies a return type, +then calls to the associated extern are assumed to write their return +value to a memory reference passed in at the first argument position. +E.g. the following are equivalent:} + +@clist{ +PRAMGA EXTERN rng "INTEGER (seed : INTEGER)" +EXTERN rng; +DECLARE num INTEGER +... snip ... + +CALL rng num 10 +} + +@p{is roughly the same as} + +@clist{ +PRAMGA EXTERN rng "(out : mut INTEGER, seed : INTEGER)" +EXTERN rng; +DECLARE num INTEGER +... snip ... + +CALL rng num 10 +} + + +@subsubsection[:title "Externs in Arithmetic Expressions"] + +@p{Extern calls may appear in arithmetic expressions with some +restrictions: the extern MUST have a known function signature, which +MUST include a return type, and which MUST NOT include any mutable +parameters.} + +@p{For example, this is OK:} + +@clist{ +PRAMGA EXTERN prng "REAL (seed : REAL)" +EXTERN prng; +RX(prng(pi) / 4) +} + +@p{But this is not:} + +@clist{ + +PRAGMA EXTERN irng "INTEGER (seed : mut INTEGER)" +EXTERN irng; +EXTERN prng; +DECLARE num INTEGER; + +... snip ... + +RX(irng(num)) # WRONG: the seed parameter is declared mutable + +RZ(prng(33)) # WRONG: we don't know the signature of prng + +} + + @subsection[:title "File Inclusion"] @p{One can include a valid Quil file in another valid Quil file by inclusion.} + @syntax[:name "File Include"]{ INCLUDE @ms{String} } diff --git a/specgen/spec/sec-structure.s b/specgen/spec/sec-structure.s index 974dd24..e18503f 100644 --- a/specgen/spec/sec-structure.s +++ b/specgen/spec/sec-structure.s @@ -252,6 +252,7 @@ object, like classical memory registers.} @ms{Gate Definition} @alt @ms{Circuit Definition} @alt @ms{Classical Memory Declaration} +@alt @ms{Extern Function Declaration} @ms{Terminator} } @p{A @emph{directive} specifies information to software processing @@ -270,6 +271,7 @@ Quil, such as the @quil{INCLUDE} directive for including files.} @alt @ms{Measurement Instruction} @alt @ms{Circuit Application} @alt @ms{Classical Memory Instruction} +@alt @ms{Extern Call Instruction} @alt @ms{Reset Instruction} @alt @ms{Wait Instruction} @alt @ms{Branch Instruction} From e1555bd389d7d16e50ad29bb572b5bbafb34a2f1 Mon Sep 17 00:00:00 2001 From: "O'Keefe, Colin B" Date: Tue, 20 Feb 2024 12:14:09 -0800 Subject: [PATCH 2/4] Add EXTERN and CALL to list of reserved keywords --- specgen/spec/sec-structure.s | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/specgen/spec/sec-structure.s b/specgen/spec/sec-structure.s index e18503f..d546a75 100644 --- a/specgen/spec/sec-structure.s +++ b/specgen/spec/sec-structure.s @@ -125,7 +125,7 @@ i pi ADD AND AS CONTROLLED CONVERT DAGGER DECLARE DEFCIRCUIT DEFGATE DIV EQ EXCHANGE FORKED GE GT HALT INCLUDE IOR JUMP JUMP-UNLESS JUMP-WHEN LABEL LE LOAD LT MATRIX MEASURE MOVE MUL NEG NOP NOT OFFSET PAULI-SUM -PERMUTATION PRAGMA RESET SHARING STORE SUB WAIT XOR +PERMUTATION PRAGMA RESET SHARING STORE SUB WAIT XOR EXTERN CALL } } From c99bcda32651a20084eac7e0c6f90416c4eb1bdd Mon Sep 17 00:00:00 2001 From: "O'Keefe, Colin B" Date: Tue, 20 Feb 2024 15:59:53 -0800 Subject: [PATCH 3/4] draft version bump --- specgen/quil.lisp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/specgen/quil.lisp b/specgen/quil.lisp index e485653..c6b3bb2 100644 --- a/specgen/quil.lisp +++ b/specgen/quil.lisp @@ -229,7 +229,7 @@ (let ((doc (make-instance 'document :title "Quil Specification" :author "Robert S. Smith; Rigetti & Co. Inc.; and contributors" - :version "2021.1 (DRAFT)" + :version "2024.1 (DRAFT)" :body (append (include (spec/ "sec-intro.s")) (include (spec/ "sec-opsem.s")) From 1e5d18dbc07bf0f47d3374d592d33db4bfaf61c1 Mon Sep 17 00:00:00 2001 From: "O'Keefe, Colin B" Date: Mon, 1 Apr 2024 13:03:18 -0700 Subject: [PATCH 4/4] Nits and typos --- specgen/quil.lisp | 2 +- specgen/spec/sec-other.s | 29 +++++++++++++++-------------- 2 files changed, 16 insertions(+), 15 deletions(-) diff --git a/specgen/quil.lisp b/specgen/quil.lisp index c6b3bb2..e485653 100644 --- a/specgen/quil.lisp +++ b/specgen/quil.lisp @@ -229,7 +229,7 @@ (let ((doc (make-instance 'document :title "Quil Specification" :author "Robert S. Smith; Rigetti & Co. Inc.; and contributors" - :version "2024.1 (DRAFT)" + :version "2021.1 (DRAFT)" :body (append (include (spec/ "sec-intro.s")) (include (spec/ "sec-opsem.s")) diff --git a/specgen/spec/sec-other.s b/specgen/spec/sec-other.s index 251ac98..f6824e1 100644 --- a/specgen/spec/sec-other.s +++ b/specgen/spec/sec-other.s @@ -45,7 +45,7 @@ identifier can appear in call instructions.} @p{Under some circumstances it may be desirable to specify the function signature of an external function. Signature declarations are -supplied by way of a special pragma.} +supplied by way of a pragma.} @syntax[:name "Extern Signature Pragma"]{ PRAGMA EXTERN @ms{Identifier} "@ms{Extern Signature}" @@ -59,25 +59,26 @@ supplied by way of a special pragma.} @ms{Identifier} : @rep[:min 0 :max 1]{mut} @ms{Type} } +@p{Type signatures to extern functions require every function parameter to be named.} + @subsubsection[:title "Call Instructions"] -@p{Declared externs may be appear in call instructions. The precise -meaning of an extern call is left up to the implementor. From the -perspective of the abstract machine, a call to an external function -increments the program counter and has some effect on classical -memory.} +@p{Declared externs may be appear in CALL instructions. The precise +effect of an extern function on classical memory is left up to the +implementor. From the perspective of the abstract machine, the effect +of processing a CALL instruction is to increment the program counter.} @syntax[:name "Extern Call Instruction"]{ CALL @ms{Identifier} @rep[:min 1]{@group{@ms{Identifier} @alt @ms{Memory Reference} @alt @ms{Complex}}} } -@p{When a supplied function type signature specifies a return type, -then calls to the associated extern are assumed to write their return -value to a memory reference passed in at the first argument position. +@p{When a function type signature specifies a return type, then calls +to the associated extern are assumed to write a return value to a +memory reference that appears in the first argument position. E.g. the following are equivalent:} @clist{ -PRAMGA EXTERN rng "INTEGER (seed : INTEGER)" +PRAGMA EXTERN rng "INTEGER (seed : INTEGER)" EXTERN rng; DECLARE num INTEGER ... snip ... @@ -85,10 +86,10 @@ DECLARE num INTEGER CALL rng num 10 } -@p{is roughly the same as} +@p{is equivalent to} @clist{ -PRAMGA EXTERN rng "(out : mut INTEGER, seed : INTEGER)" +PRAGMA EXTERN rng "(out : mut INTEGER, seed : INTEGER)" EXTERN rng; DECLARE num INTEGER ... snip ... @@ -100,14 +101,14 @@ CALL rng num 10 @subsubsection[:title "Externs in Arithmetic Expressions"] @p{Extern calls may appear in arithmetic expressions with some -restrictions: the extern MUST have a known function signature, which +restrictions: the extern MUST have a declared function signature, which MUST include a return type, and which MUST NOT include any mutable parameters.} @p{For example, this is OK:} @clist{ -PRAMGA EXTERN prng "REAL (seed : REAL)" +PRAGMA EXTERN prng "REAL (seed : REAL)" EXTERN prng; RX(prng(pi) / 4) }