Skip to content

Commit

Permalink
all: AVX-512 (#217)
Browse files Browse the repository at this point in the history
Extends avo to support most AVX-512 instruction sets.

The instruction type is extended to support suffixes. The K family of opmask
registers is added to the register package, and the operand package is updated
to support the new operand types. Move instruction deduction in `Load` and
`Store` is extended to support KMOV* and VMOV* forms.

Internal code generation packages were overhauled. Instruction database loading
required various messy changes to account for the additional complexities of the
AVX-512 instruction sets. The internal/api package was added to introduce a
separation between instruction forms in the database, and the functions avo
provides to create them. This was required since with instruction suffixes there
is no longer a one-to-one mapping between instruction constructors and opcodes.

AVX-512 bloated generated source code size substantially, initially increasing
compilation and CI test times to an unacceptable level. Two changes were made to
address this:

1.  Instruction constructors in the `x86` package moved to an optab-based
    approach. This compiles substantially faster than the verbose code
    generation we had before.

2.  The most verbose code-generated tests are moved under build tags and
    limited to a stress test mode. Stress test builds are run on
    schedule but not in regular CI.

An example of AVX-512 accelerated 16-lane MD5 is provided to demonstrate and
test the new functionality.

Updates #20 #163 #229

Co-authored-by: Vaughn Iverson <vsivsi@yahoo.com>
  • Loading branch information
mmcloughlin and vsivsi committed Nov 13, 2021
1 parent 2867bd7 commit b76e849
Show file tree
Hide file tree
Showing 71 changed files with 268,223 additions and 72,302 deletions.
1 change: 1 addition & 0 deletions .github/workflows/packages.yml
Original file line number Diff line number Diff line change
Expand Up @@ -561,6 +561,7 @@ jobs:
run: go test ./...
segmentio-asm:
runs-on: ubuntu-latest
if: false # skip: https://github.com/mmcloughlin/avo/issues/229
steps:
- name: Install Go
uses: actions/setup-go@37335c7bb261b353407cff977110895fa0b4f7d8 # v2.1.3
Expand Down
50 changes: 50 additions & 0 deletions .github/workflows/stress.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
name: stress

permissions:
contents: read

on:
schedule:
- cron: '33 3 * * 6'

jobs:
test:
runs-on: ubuntu-latest
env:
GOFLAGS: -tags=stress
steps:
- name: Install Go
uses: actions/setup-go@37335c7bb261b353407cff977110895fa0b4f7d8 # v2.1.3
with:
go-version: 1.17.x
- name: Configure Go Environment
run: |
echo GOPATH=${{ runner.workspace }} >> $GITHUB_ENV
echo ${{ runner.workspace }}/bin >> $GITHUB_PATH
- name: Go Environment
run: go env
- name: Checkout code
uses: actions/checkout@5a4ac9002d0be2fb38bd78e4b4dbde5606d7042f # v2.3.4
with:
persist-credentials: false
- name: Bootstrap
run: ./script/bootstrap

- name: Generate
run: ./script/generate
- name: Status
run: git status

- name: Build
run: go build ./...
- name: Test
run: go test -bench . ./...
- name: Coverage
run: ./script/coverage

- name: Upload Stress Unit Test Coverage
uses: codecov/codecov-action@51d810878be5422784e86451c0e7c14e5860ec47 # v2.0.2
with:
token: ${{ secrets.CODECOV_TOKEN }}
files: unittests.coverprofile
flags: stress
5 changes: 5 additions & 0 deletions .golangci.yml
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
run:
timeout: 5m

linters:
enable-all: true
disable:
Expand Down Expand Up @@ -27,3 +30,5 @@ issues:
- Error return value of .((os\.)?std(out|err)\..*|.*Close|.*Flush|os\.Remove(All)?|.*printf?|os\.(Un)?Setenv). is not checked
# gocritic: https://github.com/go-critic/go-critic/issues/762
- ' with `(len|cap|real|imag)`'
# We want to allow all caps in certain cases.
- "ALL_CAPS in Go names"
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -189,6 +189,7 @@ Implementations of full algorithms:
* **[sha1](examples/sha1):** [SHA-1](https://en.wikipedia.org/wiki/SHA-1) cryptographic hash.
* **[fnv1a](examples/fnv1a):** [FNV-1a](https://en.wikipedia.org/wiki/Fowler%E2%80%93Noll%E2%80%93Vo_hash_function#FNV-1a_hash) hash function.
* **[dot](examples/dot):** Vector dot product.
* **[md5x16](examples/md5x16):** AVX-512 accelerated [MD5](https://en.wikipedia.org/wiki/MD5).
* **[geohash](examples/geohash):** Integer [geohash](https://en.wikipedia.org/wiki/Geohash) encoding.
* **[stadtx](examples/stadtx):** [`StadtX` hash](https://github.com/demerphq/BeagleHash) port from [dgryski/go-stadtx](https://github.com/dgryski/go-stadtx).

Expand Down
5 changes: 3 additions & 2 deletions build/context.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@ import (
"github.com/mmcloughlin/avo/reg"
)

//go:generate avogen -output zinstructions.go build
//go:generate avogen -output zinstructions_test.go buildtest

// Context maintains state for incrementally building an avo File.
type Context struct {
pkg *packages.Package
Expand Down Expand Up @@ -175,8 +178,6 @@ func (c *Context) activefunc() *ir.Function {
return c.function
}

//go:generate avogen -output zinstructions.go build

// StaticGlobal adds a new static data section to the file and returns a pointer to it.
func (c *Context) StaticGlobal(name string) operand.Mem {
c.global = ir.NewStaticGlobal(name)
Expand Down
3 changes: 3 additions & 0 deletions build/global.go
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,9 @@ func YMM() reg.VecVirtual { return ctx.YMM() }
// ZMM allocates and returns a 512-bit vector register.
func ZMM() reg.VecVirtual { return ctx.ZMM() }

// K allocates and returns an opmask register.
func K() reg.OpmaskVirtual { return ctx.K() }

// Param returns a the named argument of the active function.
func Param(name string) gotypes.Component { return ctx.Param(name) }

Expand Down
Loading

0 comments on commit b76e849

Please sign in to comment.