ForAllSingle

A forall statement with a single assignment.

Declaration

Syntax

ForAllSingle(do_loop_head head, stmt assign_stmt)

Arguments

Argument

Description

head

the do_loop_head giving the index and its range.

assign_stmt

the assignment performed for every index value.

Return values

None.

Description

forall differs from a loop in its evaluation order: every right hand side is evaluated for all index values before any assignment happens, so an assignment cannot see the values written by another index.

A forall construct with several statements is lowered to a sequence of ForAllSingle nodes, one per assignment, which preserves that ordering because each statement completes for all indices before the next begins.

Examples

(ForAllSingle
  :head (do_loop_head
    :v (Var
      :v (SymbolRef 1 "i")
    )
    :start (IntegerConstant
      :n 1
      :type (Integer
        :kind 4
      )
      :intboz_type :Decimal
    )
    :end (IntegerConstant
      :n 3
      :type (Integer
        :kind 4
      )
      :intboz_type :Decimal
    )
    :increment (IntegerConstant
      :n 1
      :type (Integer
        :kind 4
      )
      :intboz_type :Decimal
    )
  )
  :assign_stmt (Assignment
    :target (ArrayItem
      :v (Var
        :v (SymbolRef 1 "a")
      )
      :args [
        (array_index
          :left nil
          :right (Var
            :v (SymbolRef 1 "i")
          )
          :step nil
        )
      ]
      :type (Integer
        :kind 4
      )
      :storage_format :ColMajor
      :value nil
    )
    :value (Var
      :v (SymbolRef 1 "i")
    )
    :overloaded nil
    :realloc_lhs false
    :move_allocation false
  )
)

It comes from this complete ASR text document:

(TranslationUnit
  :symtab (SymbolTable
    :id 0
    :symbols {
      "main" (Program
        :symtab (SymbolTable
          :id 1
          :symbols {
            "a" (Variable
              :parent_symtab 1
              :name "a"
              :dependencies []
              :intent :Local
              :symbolic_value nil
              :value nil
              :storage :Default
              :type (Array
                :type (Integer
                  :kind 4
                )
                :dims [
                  (dimension
                    :start (IntegerConstant
                      :n 1
                      :type (Integer
                        :kind 4
                      )
                      :intboz_type :Decimal
                    )
                    :length (IntegerConstant
                      :n 3
                      :type (Integer
                        :kind 4
                      )
                      :intboz_type :Decimal
                    )
                  )
                ]
                :physical_type :FixedSizeArray
              )
              :type_declaration nil
              :abi :Source
              :access :Public
              :presence :Required
              :value_attr false
              :target_attr false
              :contiguous_attr false
              :bindc_name nil
              :is_volatile false
              :is_protected false
              :pass_attr :NotMethod
              :self_argument nil
              :codims []
            )
            "i" (Variable
              :parent_symtab 1
              :name "i"
              :dependencies []
              :intent :Local
              :symbolic_value nil
              :value nil
              :storage :Default
              :type (Integer
                :kind 4
              )
              :type_declaration nil
              :abi :Source
              :access :Public
              :presence :Required
              :value_attr false
              :target_attr false
              :contiguous_attr false
              :bindc_name nil
              :is_volatile false
              :is_protected false
              :pass_attr :NotMethod
              :self_argument nil
              :codims []
            )
          }
        )
        :name "main"
        :dependencies []
        :body [
          (ForAllSingle
            :head (do_loop_head
              :v (Var
                :v (SymbolRef 1 "i")
              )
              :start (IntegerConstant
                :n 1
                :type (Integer
                  :kind 4
                )
                :intboz_type :Decimal
              )
              :end (IntegerConstant
                :n 3
                :type (Integer
                  :kind 4
                )
                :intboz_type :Decimal
              )
              :increment (IntegerConstant
                :n 1
                :type (Integer
                  :kind 4
                )
                :intboz_type :Decimal
              )
            )
            :assign_stmt (Assignment
              :target (ArrayItem
                :v (Var
                  :v (SymbolRef 1 "a")
                )
                :args [
                  (array_index
                    :left nil
                    :right (Var
                      :v (SymbolRef 1 "i")
                    )
                    :step nil
                  )
                ]
                :type (Integer
                  :kind 4
                )
                :storage_format :ColMajor
                :value nil
              )
              :value (Var
                :v (SymbolRef 1 "i")
              )
              :overloaded nil
              :realloc_lhs false
              :move_allocation false
            )
          )
        ]
      )
    }
  )
  :items []
)

See Also

DoConcurrentLoop, Where, do_loop_head