<!---
// Copyright 2018 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
-->

## Introduction to the Go compiler's SSA backend

This package contains the compiler's Static Single Assignment form component. If
you're not familiar with SSA, its [Wikipedia
article](https://en.wikipedia.org/wiki/Static_single_assignment_form) is a good
starting point.

It is recommended that you first read [cmd/compile/README.md](../../README.md)
if you are not familiar with the Go compiler already. That document gives an
overview of the compiler, and explains what is SSA's part and purpose in it.

### Key concepts

The names described below may be loosely related to their Go counterparts, but
note that they are not equivalent. For example, a Go block statement has a
variable scope, yet SSA has no notion of variables nor variable scopes.

It may also be surprising that values and blocks are named after their unique
sequential IDs. They rarely correspond to named entities in the original code,
such as variables or function parameters. The sequential IDs also allow the
compiler to avoid maps, and it is always possible to track back the values to Go
code using debug and position information.

#### Values

Values are the basic building blocks of SSA. Per SSA's very definition, a
value is defined exactly once, but it may be used any number of times. A value
mainly consists of a unique identifier, an operator, a type, and some arguments.

An operator or `Op` describes the operation that computes the value. The
semantics of each operator can be found in `gen/*Ops.go`. For example, `OpAdd8`
takes two value arguments holding 8-bit integers and results in their addition.
Here is a possible SSA representation of the addition of two `uint8` values:

	// var c uint8 = a + b
	v4 = Add8 <uint8> v2 v3

A value's type will usually be a Go type. For example, the value in the example
above has a `uint8` type, and a constant boolean value will have a `bool` type.
However, certain types don't come from Go and are special; below we will cover
`memory`, the most common of them.

See [value.go](value.go) for more information.

#### Memory types

`memory` represents the global memory state. An `Op` that takes a memory
argument depends on that memory state, and an `Op` which has the memory type
impacts the state of memory. This ensures that memory operations are kept in the
right order. For example:

	// *a = 3
	// *b = *a
	v10 = Store <mem> {int} v6 v8 v1
	v14 = Store <mem> {int} v7 v8 v10

Here, `Store` stores its second argument (of type `int`) into the first argument
(of type `*int`). The last argument is the memory state; since the second store
depends on the memory value defined by the first store, the two stores cannot be
reordered.

See [cmd/compile/internal/types/type.go](../types/type.go) for more information.

#### Blocks

A block represents a basic block in the control flow graph of a function. It is,
essentially, a list of values that define the operation of this block. Besides
the list of values, blocks mainly consist of a unique identifier, a kind, and a
list of successor blocks.

The simplest kind is a `plain` block; it simply hands the control flow to
another block, thus its successors list contains one block.

Another common block kind is the `exit` block. These have a final value, called
control value, which must return a memory state. This is necessary for functions
to return some values, for example - the caller needs some memory state to
depend on, to ensure that it receives those return values correctly.

The last important block kind we will mention is the `if` block. Its control
value must be a boolean value, and it has exactly two successor blocks. The
control flow is handed to the first successor if the bool is true, and to the
second otherwise.

Here is a sample if-else control flow represented with basic blocks:

	// func(b bool) int {
	// 	if b {
	// 		return 2
	// 	}
	// 	return 3
	// }
	b1:
	  v1 = InitMem <mem>
	  v2 = SP <uintptr>
	  v5 = Addr <*int> {~r1} v2
	  v6 = Arg <bool> {b}
	  v8 = Const64 <int> [2]
	  v12 = Const64 <int> [3]
	  If v6 -> b2 b3
	b2: <- b1
	  v10 = VarDef <mem> {~r1} v1
	  v11 = Store <mem> {int} v5 v8 v10
	  Ret v11
	b3: <- b1
	  v14 = VarDef <mem> {~r1} v1
	  v15 = Store <mem> {int} v5 v12 v14
	  Ret v15

<!---
TODO: can we come up with a shorter example that still shows the control flow?
-->

See [block.go](block.go) for more information.

#### Functions

A function represents a function declaration along with its body. It mainly
consists of a name, a type (its signature), a list of blocks that form its body,
and the entry block within said list.

When a function is called, the control flow is handed to its entry block. If the
function terminates, the control flow will eventually reach an exit block, thus
ending the function call.

Note that a function may have zero or multiple exit blocks, just like a Go
function can have any number of return points, but it must have exactly one
entry point block.

Also note that some SSA functions are autogenerated, such as the hash functions
for each type used as a map key.

For example, this is what an empty function can look like in SSA, with a single
exit block that returns an uninteresting memory state:

	foo func()
	  b1:
	    v1 = InitMem <mem>
	    Ret v1

See [func.go](func.go) for more information.

### Compiler passes

Having a program in SSA form is not very useful on its own. Its advantage lies
in how easy it is to write optimizations that modify the program to make it
better. The way the Go compiler accomplishes this is via a list of passes.

Each pass transforms a SSA function in some way. For example, a dead code
elimination pass will remove blocks and values that it can prove will never be
executed, and a nil check elimination pass will remove nil checks which it can
prove to be redundant.

Compiler passes work on one function at a time, and by default run sequentially
and exactly once.

The `lower` pass is special; it converts the SSA representation from being
machine-independent to being machine-dependent. That is, some abstract operators
are replaced with their non-generic counterparts, potentially reducing or
increasing the final number of values.

<!---
TODO: Probably explain here why the ordering of the passes matters, and why some
passes like deadstore have multiple variants at different stages.
-->

See the `passes` list defined in [compile.go](compile.go) for more information.

### Playing with SSA

A good way to see and get used to the compiler's SSA in action is via
`GOSSAFUNC`. For example, to see func `Foo`'s initial SSA form and final
generated assembly, one can run:

	GOSSAFUNC=Foo go build

The generated `ssa.html` file will also contain the SSA func at each of the
compile passes, making it easy to see what each pass does to a particular
program. You can also click on values and blocks to highlight them, to help
follow the control flow and values.

<!---
TODO: need more ideas for this section
-->

### Hacking on SSA

While most compiler passes are implemented directly in Go code, some others are
code generated. This is currently done via rewrite rules, which have their own
syntax and are maintained in `gen/*.rules`. Simpler optimizations can be written
easily and quickly this way, but rewrite rules are not suitable for more complex
optimizations.

To read more on rewrite rules, have a look at the top comments in
[gen/generic.rules](gen/generic.rules) and [gen/rulegen.go](gen/rulegen.go).

Similarly, the code to manage operators is also code generated from
`gen/*Ops.go`, as it is easier to maintain a few tables than a lot of code.
After changing the rules or operators, see [gen/README](gen/README) for
instructions on how to generate the Go code again.

<!---
TODO: more tips and info could likely go here
-->
