psyclone.psyad.adjoint_visitor

A PSyIR visitor for PSyAD : the PSyclone Adjoint support. Applies transformations to tangent-linear PSyIR to return its PSyIR adjoint.

Classes

  • AdjointVisitor: An Adjoint Visitor that translates the PSyIR of a tangent-linear

class psyclone.psyad.adjoint_visitor.AdjointVisitor(active_variable_names)

An Adjoint Visitor that translates the PSyIR of a tangent-linear code into its adjoint form.

Parameters:

active_variable_names (list of str) – a list of the active variables.

Raises:

ValueError – if no active variables are supplied.

Inheritance

Inheritance diagram of AdjointVisitor
assignment_node(node)

This method is called if the visitor finds an Assignment node. The adjoint of this tangent-linear assignment is returned via the AssignmentTrans transformation. As the adjoint of a single tangent-linear assignment can consist of multiple assignments, a list of nodes is returned.

Parameters:

node (psyclone.psyir.nodes.Assignment) – an Assignment PSyIR node.

Returns:

a list of PSyIR nodes containing the adjoint of this node.

Return type:

list of psyclone.psyir.nodes.Node

Raises:

VisitorError – if the schedule_node method has not been called previously.

container_node(node)

This method is called if the visitor finds a Container node. A copy of the container is returned (as this does not change when converting from tangent linear to adjoint) containing processed descendants.

Parameters:

node (psyclone.psyir.nodes.Container) – a Container PSyIR node.

Returns:

a new PSyIR tree containing the adjoint of this node and its descendant nodes.

Return type:

psyclone.psyir.nodes.Node

ifblock_node(node)

This method is called if the visitor finds an ifblock node. An exception is raised if the condition of the ifblock node contains an active variable as this is not valid tangent-linear code. Otherwise, the ifblock and its condition are returned unchanged and the contents of the “then” and “else” parts of the ifblock are returned after being processed by PSyAD.

Parameters:

node (psyclone.psyir.nodes.IfBlock) – an IfBlock PSyIR node.

Returns:

a new PSyIR tree containing the adjoint equivalent of this node and its descendants.

Return type:

psyclone.psyir.nodes.IfBlock

Raises:

VisitorError if the condition of the ifblock contains any active variables.

Raises:
  • VisitorError – if the ifblock node is visited before a schedule.

  • VisitorError – if a passive ifblock node is found.

loop_node(node)

This method is called if the visitor finds a Loop node. If the loop (including any descendants) contains active variables then a new loop is returned which iterates in the reverse order of the original loop and the body of the new loop is the result of processing the body of the original loop. If the loop does not contain any active variables then an exception is raised as this case should have been dealt with by the schedule_node() method.

Parameters:

node (psyclone.psyir.nodes.Loop) – a Loop PSyIR node.

Returns:

a new PSyIR tree containing the adjoint equivalent of this node and its descendants.

Return type:

psyclone.psyir.nodes.Loop

Raises:
schedule_node(node)

This method is called if the visitor finds a Schedule node. A copy of the schedule is returned, as this does not change when converting from tangent linear to adjoint and its children are re-ordered and sorted dependending on whether they are active or passive nodes.

As a schedule contains variable scoping information, i.e. a symbol table, the symbols representing the active variable names supplied to the visitor are found and added to an internal list so they are available when processing any descendants.

Parameters:

node (psyclone.psyir.nodes.Schedule) – a Schedule PSyIR node.

Returns:

a new PSyIR tree containing the adjoint equivalent of this node and its descendants.

Return type:

psyclone.psyir.nodes.Schedule