mirror of
https://github.com/tinygo-org/tinygo.git
synced 2026-08-09 21:43:40 +00:00
Compare commits
1 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 3e5f602655 |
@@ -57,27 +57,3 @@ jobs:
|
||||
--header 'Content-Type: application/json' \
|
||||
-d '{"branch": "dev"}' \
|
||||
-u "${{ secrets.CIRCLECI_API_TOKEN }}"
|
||||
- name: Trigger Bluetooth repo build on CircleCI
|
||||
run: |
|
||||
curl --location --request POST 'https://circleci.com/api/v2/project/github/tinygo-org/bluetooth/pipeline' \
|
||||
--header 'Content-Type: application/json' \
|
||||
-d '{"branch": "dev"}' \
|
||||
-u "${{ secrets.CIRCLECI_API_TOKEN }}"
|
||||
- name: Trigger TinyFS repo build on CircleCI
|
||||
run: |
|
||||
curl --location --request POST 'https://circleci.com/api/v2/project/github/tinygo-org/tinyfs/pipeline' \
|
||||
--header 'Content-Type: application/json' \
|
||||
-d '{"branch": "dev"}' \
|
||||
-u "${{ secrets.CIRCLECI_API_TOKEN }}"
|
||||
- name: Trigger TinyFont repo build on CircleCI
|
||||
run: |
|
||||
curl --location --request POST 'https://circleci.com/api/v2/project/github/tinygo-org/tinyfont/pipeline' \
|
||||
--header 'Content-Type: application/json' \
|
||||
-d '{"branch": "dev"}' \
|
||||
-u "${{ secrets.CIRCLECI_API_TOKEN }}"
|
||||
- name: Trigger TinyDraw repo build on CircleCI
|
||||
run: |
|
||||
curl --location --request POST 'https://circleci.com/api/v2/project/github/tinygo-org/tinydraw/pipeline' \
|
||||
--header 'Content-Type: application/json' \
|
||||
-d '{"branch": "dev"}' \
|
||||
-u "${{ secrets.CIRCLECI_API_TOKEN }}"
|
||||
|
||||
@@ -239,4 +239,3 @@ jobs:
|
||||
rm xtensa-esp32-elf-gcc8_2_0-esp-2020r2-linux-amd64.tar.gz
|
||||
- run: make smoketest
|
||||
- run: make wasmtest
|
||||
- run: make tinygo-baremetal
|
||||
|
||||
@@ -15,7 +15,7 @@ jobs:
|
||||
uses: actions/setup-go@v2
|
||||
with:
|
||||
go-version: '1.17'
|
||||
- uses: brechtm/setup-scoop@v2
|
||||
- uses: MinoruSekine/setup-scoop@v1
|
||||
- name: Install Dependencies
|
||||
shell: bash
|
||||
run: |
|
||||
|
||||
@@ -208,20 +208,19 @@ lib/wasi-libc/sysroot/lib/wasm32-wasi/libc.a:
|
||||
# Build the Go compiler.
|
||||
tinygo:
|
||||
@if [ ! -f "$(LLVM_BUILDDIR)/bin/llvm-config" ]; then echo "Fetch and build LLVM first by running:"; echo " make llvm-source"; echo " make $(LLVM_BUILDDIR)"; exit 1; fi
|
||||
CGO_CPPFLAGS="$(CGO_CPPFLAGS)" CGO_CXXFLAGS="$(CGO_CXXFLAGS)" CGO_LDFLAGS="$(CGO_LDFLAGS)" $(GO) build -buildmode exe -o build/tinygo$(EXE) -tags byollvm -ldflags="-X github.com/tinygo-org/tinygo/goenv.GitSha1=`git rev-parse --short HEAD`" .
|
||||
CGO_CPPFLAGS="$(CGO_CPPFLAGS)" CGO_CXXFLAGS="$(CGO_CXXFLAGS)" CGO_LDFLAGS="$(CGO_LDFLAGS)" $(GO) build -buildmode exe -o build/tinygo$(EXE) -tags byollvm -ldflags="-X main.gitSha1=`git rev-parse --short HEAD`" .
|
||||
|
||||
test: wasi-libc
|
||||
CGO_CPPFLAGS="$(CGO_CPPFLAGS)" CGO_CXXFLAGS="$(CGO_CXXFLAGS)" CGO_LDFLAGS="$(CGO_LDFLAGS)" $(GO) test $(GOTESTFLAGS) -timeout=20m -buildmode exe -tags byollvm ./builder ./cgo ./compileopts ./compiler ./interp ./transform .
|
||||
|
||||
# Standard library packages that pass tests on darwin, linux, wasi, and windows, but take over a minute in wasi
|
||||
# Tests that take over a minute in wasi
|
||||
TEST_PACKAGES_SLOW = \
|
||||
compress/bzip2 \
|
||||
compress/flate \
|
||||
crypto/dsa \
|
||||
index/suffixarray \
|
||||
|
||||
# Standard library packages that pass tests quickly on darwin, linux, wasi, and windows
|
||||
TEST_PACKAGES_FAST = \
|
||||
TEST_PACKAGES_BASE = \
|
||||
compress/lzw \
|
||||
compress/zlib \
|
||||
container/heap \
|
||||
@@ -265,63 +264,47 @@ TEST_PACKAGES_FAST = \
|
||||
unicode/utf16 \
|
||||
unicode/utf8 \
|
||||
|
||||
# archive/zip requires os.ReadAt, which is not yet supported on windows
|
||||
# Standard library packages that pass tests natively
|
||||
TEST_PACKAGES := \
|
||||
$(TEST_PACKAGES_BASE)
|
||||
|
||||
# archive/zip requires ReadAt, which is not yet supported on windows
|
||||
# debug/plan9obj requires os.ReadAt, which is not yet supported on windows
|
||||
# io/fs requires os.ReadDir, which is not yet supported on windows or wasi
|
||||
# testing/fstest requires os.ReadDir, which is not yet supported on windows or wasi
|
||||
|
||||
# Additional standard library packages that pass tests on individual platforms
|
||||
TEST_PACKAGES_LINUX := \
|
||||
ifneq ($(OS),Windows_NT)
|
||||
TEST_PACKAGES := \
|
||||
$(TEST_PACKAGES) \
|
||||
archive/zip \
|
||||
debug/dwarf \
|
||||
debug/plan9obj \
|
||||
io/fs \
|
||||
testing/fstest
|
||||
|
||||
TEST_PACKAGES_DARWIN := $(TEST_PACKAGES_LINUX)
|
||||
|
||||
# Report platforms on which each standard library package is known to pass tests
|
||||
jointmp := $(shell echo /tmp/join.$$$$)
|
||||
report-stdlib-tests-pass:
|
||||
@for t in $(TEST_PACKAGES_DARWIN); do echo "$$t darwin"; done | sort > $(jointmp).darwin
|
||||
@for t in $(TEST_PACKAGES_LINUX); do echo "$$t linux"; done | sort > $(jointmp).linux
|
||||
@for t in $(TEST_PACKAGES_FAST) $(TEST_PACKAGES_SLOW); do echo "$$t darwin linux wasi windows"; done | sort > $(jointmp).portable
|
||||
@join -a1 -a2 $(jointmp).darwin $(jointmp).linux | \
|
||||
join -a1 -a2 - $(jointmp).portable
|
||||
@rm $(jointmp).*
|
||||
|
||||
# Standard library packages that pass tests quickly on the current platform
|
||||
ifeq ($(shell uname),Darwin)
|
||||
TEST_PACKAGES_HOST := $(TEST_PACKAGES_FAST) $(TEST_PACKAGES_DARWIN)
|
||||
endif
|
||||
ifeq ($(shell uname),Linux)
|
||||
TEST_PACKAGES_HOST := $(TEST_PACKAGES_FAST) $(TEST_PACKAGES_LINUX)
|
||||
endif
|
||||
ifeq ($(OS),Windows_NT)
|
||||
TEST_PACKAGES_HOST := $(TEST_PACKAGES_FAST)
|
||||
endif
|
||||
|
||||
# Standard library packages that pass tests on wasi
|
||||
TEST_PACKAGES_WASI = \
|
||||
$(TEST_PACKAGES_BASE)
|
||||
|
||||
# Test known-working standard library packages.
|
||||
# TODO: parallelize, and only show failing tests (no implied -v flag).
|
||||
.PHONY: tinygo-test
|
||||
tinygo-test:
|
||||
$(TINYGO) test $(TEST_PACKAGES_HOST) $(TEST_PACKAGES_SLOW)
|
||||
$(TINYGO) test $(TEST_PACKAGES) $(TEST_PACKAGES_SLOW)
|
||||
tinygo-test-fast:
|
||||
$(TINYGO) test $(TEST_PACKAGES_HOST)
|
||||
$(TINYGO) test $(TEST_PACKAGES)
|
||||
tinygo-bench:
|
||||
$(TINYGO) test -bench . $(TEST_PACKAGES_HOST) $(TEST_PACKAGES_SLOW)
|
||||
$(TINYGO) test -bench . $(TEST_PACKAGES) $(TEST_PACKAGES_SLOW)
|
||||
tinygo-bench-fast:
|
||||
$(TINYGO) test -bench . $(TEST_PACKAGES_HOST)
|
||||
|
||||
# Same thing, except for wasi rather than the current platform.
|
||||
$(TINYGO) test -bench . $(TEST_PACKAGES)
|
||||
tinygo-test-wasi:
|
||||
$(TINYGO) test -target wasi $(TEST_PACKAGES_FAST) $(TEST_PACKAGES_SLOW)
|
||||
$(TINYGO) test -target wasi $(TEST_PACKAGES_WASI) $(TEST_PACKAGES_SLOW)
|
||||
tinygo-test-wasi-fast:
|
||||
$(TINYGO) test -target wasi $(TEST_PACKAGES_FAST)
|
||||
$(TINYGO) test -target wasi $(TEST_PACKAGES_WASI)
|
||||
tinygo-bench-wasi:
|
||||
$(TINYGO) test -target wasi -bench . $(TEST_PACKAGES_FAST) $(TEST_PACKAGES_SLOW)
|
||||
$(TINYGO) test -target wasi -bench . $(TEST_PACKAGES_WASI) $(TEST_PACKAGES_SLOW)
|
||||
tinygo-bench-wasi-fast:
|
||||
$(TINYGO) test -target wasi -bench . $(TEST_PACKAGES_FAST)
|
||||
$(TINYGO) test -target wasi -bench . $(TEST_PACKAGES_WASI)
|
||||
|
||||
# Test external packages in a large corpus.
|
||||
test-corpus:
|
||||
@@ -331,10 +314,6 @@ test-corpus-fast:
|
||||
test-corpus-wasi: wasi-libc
|
||||
CGO_CPPFLAGS="$(CGO_CPPFLAGS)" CGO_CXXFLAGS="$(CGO_CXXFLAGS)" CGO_LDFLAGS="$(CGO_LDFLAGS)" $(GO) test $(GOTESTFLAGS) -timeout=1h -buildmode exe -tags byollvm -run TestCorpus . -corpus=testdata/corpus.yaml -target=wasi
|
||||
|
||||
tinygo-baremetal:
|
||||
# Regression tests that run on a baremetal target and don't fit in either main_test.go or smoketest.
|
||||
# regression test for #2666: e.g. encoding/hex must pass on baremetal
|
||||
$(TINYGO) test -target cortex-m-qemu encoding/hex
|
||||
|
||||
.PHONY: smoketest
|
||||
smoketest:
|
||||
@@ -358,8 +337,6 @@ smoketest:
|
||||
@$(MD5SUM) test.hex
|
||||
$(TINYGO) build -size short -o test.hex -target=pca10040 examples/echo
|
||||
@$(MD5SUM) test.hex
|
||||
$(TINYGO) build -size short -o test.hex -target=pca10040 examples/echo2
|
||||
@$(MD5SUM) test.hex
|
||||
$(TINYGO) build -size short -o test.hex -target=circuitplay-express examples/i2s
|
||||
@$(MD5SUM) test.hex
|
||||
$(TINYGO) build -size short -o test.hex -target=pca10040 examples/mcp3008
|
||||
|
||||
+15
-64
@@ -105,15 +105,6 @@ func Build(pkgName, outpath string, config *compileopts.Config, action func(Buil
|
||||
defer os.RemoveAll(dir)
|
||||
}
|
||||
|
||||
// Look up the build cache directory, which is used to speed up incremental
|
||||
// builds.
|
||||
cacheDir := goenv.Get("GOCACHE")
|
||||
if cacheDir == "off" {
|
||||
// Use temporary build directory instead, effectively disabling the
|
||||
// build cache.
|
||||
cacheDir = dir
|
||||
}
|
||||
|
||||
// Check for a libc dependency.
|
||||
// As a side effect, this also creates the headers for the given libc, if
|
||||
// the libc needs them.
|
||||
@@ -204,21 +195,6 @@ func Build(pkgName, outpath string, config *compileopts.Config, action func(Buil
|
||||
var packageJobs []*compileJob
|
||||
packageBitcodePaths := make(map[string]string)
|
||||
packageActionIDs := make(map[string]string)
|
||||
|
||||
if config.Options.GlobalValues["runtime"]["buildVersion"] == "" {
|
||||
version := goenv.Version
|
||||
if strings.HasSuffix(goenv.Version, "-dev") && goenv.GitSha1 != "" {
|
||||
version += "-" + goenv.GitSha1
|
||||
}
|
||||
if config.Options.GlobalValues == nil {
|
||||
config.Options.GlobalValues = make(map[string]map[string]string)
|
||||
}
|
||||
if config.Options.GlobalValues["runtime"] == nil {
|
||||
config.Options.GlobalValues["runtime"] = make(map[string]string)
|
||||
}
|
||||
config.Options.GlobalValues["runtime"]["buildVersion"] = version
|
||||
}
|
||||
|
||||
for _, pkg := range lprogram.Sorted() {
|
||||
pkg := pkg // necessary to avoid a race condition
|
||||
|
||||
@@ -262,6 +238,12 @@ func Build(pkgName, outpath string, config *compileopts.Config, action func(Buil
|
||||
|
||||
// Determine the path of the bitcode file (which is a serialized version
|
||||
// of a LLVM module).
|
||||
cacheDir := goenv.Get("GOCACHE")
|
||||
if cacheDir == "off" {
|
||||
// Use temporary build directory instead, effectively disabling the
|
||||
// build cache.
|
||||
cacheDir = dir
|
||||
}
|
||||
bitcodePath := filepath.Join(cacheDir, "pkg-"+hex.EncodeToString(hash[:])+".bc")
|
||||
packageBitcodePaths[pkg.ImportPath] = bitcodePath
|
||||
|
||||
@@ -434,7 +416,7 @@ func Build(pkgName, outpath string, config *compileopts.Config, action func(Buil
|
||||
// Load and link all the bitcode files. This does not yet optimize
|
||||
// anything, it only links the bitcode files together.
|
||||
ctx := llvm.NewContext()
|
||||
mod = ctx.NewModule("main")
|
||||
mod = ctx.NewModule("")
|
||||
for _, pkg := range lprogram.Sorted() {
|
||||
pkgMod, err := ctx.ParseBitcodeFile(packageBitcodePaths[pkg.ImportPath])
|
||||
if err != nil {
|
||||
@@ -530,14 +512,8 @@ func Build(pkgName, outpath string, config *compileopts.Config, action func(Buil
|
||||
}
|
||||
return ioutil.WriteFile(outpath, llvmBuf.Bytes(), 0666)
|
||||
case ".bc":
|
||||
var buf llvm.MemoryBuffer
|
||||
if config.UseThinLTO() {
|
||||
buf = llvm.WriteThinLTOBitcodeToMemoryBuffer(mod)
|
||||
} else {
|
||||
buf = llvm.WriteBitcodeToMemoryBuffer(mod)
|
||||
}
|
||||
defer buf.Dispose()
|
||||
return ioutil.WriteFile(outpath, buf.Bytes(), 0666)
|
||||
data := llvm.WriteBitcodeToMemoryBuffer(mod).Bytes()
|
||||
return ioutil.WriteFile(outpath, data, 0666)
|
||||
case ".ll":
|
||||
data := []byte(mod.String())
|
||||
return ioutil.WriteFile(outpath, data, 0666)
|
||||
@@ -557,17 +533,10 @@ func Build(pkgName, outpath string, config *compileopts.Config, action func(Buil
|
||||
dependencies: []*compileJob{programJob},
|
||||
result: objfile,
|
||||
run: func(*compileJob) error {
|
||||
var llvmBuf llvm.MemoryBuffer
|
||||
if config.UseThinLTO() {
|
||||
llvmBuf = llvm.WriteThinLTOBitcodeToMemoryBuffer(mod)
|
||||
} else {
|
||||
var err error
|
||||
llvmBuf, err = machine.EmitToMemoryBuffer(mod, llvm.ObjectFile)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
llvmBuf, err := machine.EmitToMemoryBuffer(mod, llvm.ObjectFile)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer llvmBuf.Dispose()
|
||||
return ioutil.WriteFile(objfile, llvmBuf.Bytes(), 0666)
|
||||
},
|
||||
}
|
||||
@@ -600,7 +569,7 @@ func Build(pkgName, outpath string, config *compileopts.Config, action func(Buil
|
||||
job := &compileJob{
|
||||
description: "compile extra file " + path,
|
||||
run: func(job *compileJob) error {
|
||||
result, err := compileAndCacheCFile(abspath, dir, config.CFlags(), config.UseThinLTO(), config.Options.PrintCommands)
|
||||
result, err := compileAndCacheCFile(abspath, dir, config.CFlags(), config.Options.PrintCommands)
|
||||
job.result = result
|
||||
return err
|
||||
},
|
||||
@@ -618,7 +587,7 @@ func Build(pkgName, outpath string, config *compileopts.Config, action func(Buil
|
||||
job := &compileJob{
|
||||
description: "compile CGo file " + abspath,
|
||||
run: func(job *compileJob) error {
|
||||
result, err := compileAndCacheCFile(abspath, dir, pkg.CFlags, config.UseThinLTO(), config.Options.PrintCommands)
|
||||
result, err := compileAndCacheCFile(abspath, dir, pkg.CFlags, config.Options.PrintCommands)
|
||||
job.result = result
|
||||
return err
|
||||
},
|
||||
@@ -687,24 +656,6 @@ func Build(pkgName, outpath string, config *compileopts.Config, action func(Buil
|
||||
if config.Options.PrintCommands != nil {
|
||||
config.Options.PrintCommands(config.Target.Linker, ldflags...)
|
||||
}
|
||||
if config.UseThinLTO() {
|
||||
ldflags = append(ldflags,
|
||||
"--thinlto-cache-dir="+filepath.Join(cacheDir, "thinlto"),
|
||||
"-plugin-opt=mcpu="+config.CPU(),
|
||||
"-plugin-opt=O"+strconv.Itoa(optLevel),
|
||||
"-plugin-opt=thinlto")
|
||||
if config.CodeModel() != "default" {
|
||||
ldflags = append(ldflags,
|
||||
"-mllvm", "-code-model="+config.CodeModel())
|
||||
}
|
||||
if sizeLevel >= 2 {
|
||||
// Workaround with roughly the same effect as
|
||||
// https://reviews.llvm.org/D119342.
|
||||
// Can hopefully be removed in LLVM 15.
|
||||
ldflags = append(ldflags,
|
||||
"-mllvm", "--rotation-max-header-size=0")
|
||||
}
|
||||
}
|
||||
err = link(config.Target.Linker, ldflags...)
|
||||
if err != nil {
|
||||
return &commandError{"failed to link", executable, err}
|
||||
@@ -895,7 +846,7 @@ func optimizeProgram(mod llvm.Module, config *compileopts.Config) error {
|
||||
}
|
||||
}
|
||||
|
||||
if config.GOOS() != "darwin" && !config.UseThinLTO() {
|
||||
if config.GOOS() != "darwin" {
|
||||
transform.ApplyFunctionSections(mod) // -ffunction-sections
|
||||
}
|
||||
|
||||
|
||||
+6
-14
@@ -56,7 +56,7 @@ import (
|
||||
// depfile but without invalidating its name. For this reason, the depfile is
|
||||
// written on each new compilation (even when it seems unnecessary). However, it
|
||||
// could in rare cases lead to a stale file fetched from the cache.
|
||||
func compileAndCacheCFile(abspath, tmpdir string, cflags []string, thinlto bool, printCommands func(string, ...string)) (string, error) {
|
||||
func compileAndCacheCFile(abspath, tmpdir string, cflags []string, printCommands func(string, ...string)) (string, error) {
|
||||
// Hash input file.
|
||||
fileHash, err := hashFile(abspath)
|
||||
if err != nil {
|
||||
@@ -67,11 +67,6 @@ func compileAndCacheCFile(abspath, tmpdir string, cflags []string, thinlto bool,
|
||||
unlock := lock(filepath.Join(goenv.Get("GOCACHE"), fileHash+".c.lock"))
|
||||
defer unlock()
|
||||
|
||||
ext := ".o"
|
||||
if thinlto {
|
||||
ext = ".bc"
|
||||
}
|
||||
|
||||
// Create cache key for the dependencies file.
|
||||
buf, err := json.Marshal(struct {
|
||||
Path string
|
||||
@@ -104,7 +99,7 @@ func compileAndCacheCFile(abspath, tmpdir string, cflags []string, thinlto bool,
|
||||
}
|
||||
|
||||
// Obtain hashes of all the files listed as a dependency.
|
||||
outpath, err := makeCFileCachePath(dependencies, depfileNameHash, ext)
|
||||
outpath, err := makeCFileCachePath(dependencies, depfileNameHash)
|
||||
if err == nil {
|
||||
if _, err := os.Stat(outpath); err == nil {
|
||||
return outpath, nil
|
||||
@@ -117,7 +112,7 @@ func compileAndCacheCFile(abspath, tmpdir string, cflags []string, thinlto bool,
|
||||
return "", err
|
||||
}
|
||||
|
||||
objTmpFile, err := ioutil.TempFile(goenv.Get("GOCACHE"), "tmp-*"+ext)
|
||||
objTmpFile, err := ioutil.TempFile(goenv.Get("GOCACHE"), "tmp-*.o")
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
@@ -129,9 +124,6 @@ func compileAndCacheCFile(abspath, tmpdir string, cflags []string, thinlto bool,
|
||||
depTmpFile.Close()
|
||||
flags := append([]string{}, cflags...) // copy cflags
|
||||
flags = append(flags, "-MD", "-MV", "-MTdeps", "-MF", depTmpFile.Name()) // autogenerate dependencies
|
||||
if thinlto {
|
||||
flags = append(flags, "-flto=thin")
|
||||
}
|
||||
flags = append(flags, "-c", "-o", objTmpFile.Name(), abspath)
|
||||
if strings.ToLower(filepath.Ext(abspath)) == ".s" {
|
||||
// If this is an assembly file (.s or .S, lowercase or uppercase), then
|
||||
@@ -189,7 +181,7 @@ func compileAndCacheCFile(abspath, tmpdir string, cflags []string, thinlto bool,
|
||||
}
|
||||
|
||||
// Move temporary object file to final location.
|
||||
outpath, err := makeCFileCachePath(dependencySlice, depfileNameHash, ext)
|
||||
outpath, err := makeCFileCachePath(dependencySlice, depfileNameHash)
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
@@ -204,7 +196,7 @@ func compileAndCacheCFile(abspath, tmpdir string, cflags []string, thinlto bool,
|
||||
// Create a cache path (a path in GOCACHE) to store the output of a compiler
|
||||
// job. This path is based on the dep file name (which is a hash of metadata
|
||||
// including compiler flags) and the hash of all input files in the paths slice.
|
||||
func makeCFileCachePath(paths []string, depfileNameHash, ext string) (string, error) {
|
||||
func makeCFileCachePath(paths []string, depfileNameHash string) (string, error) {
|
||||
// Hash all input files.
|
||||
fileHashes := make(map[string]string, len(paths))
|
||||
for _, path := range paths {
|
||||
@@ -229,7 +221,7 @@ func makeCFileCachePath(paths []string, depfileNameHash, ext string) (string, er
|
||||
outFileNameBuf := sha512.Sum512_224(buf)
|
||||
cacheKey := hex.EncodeToString(outFileNameBuf[:])
|
||||
|
||||
outpath := filepath.Join(goenv.Get("GOCACHE"), "obj-"+cacheKey+ext)
|
||||
outpath := filepath.Join(goenv.Get("GOCACHE"), "obj-"+cacheKey+".o")
|
||||
return outpath, nil
|
||||
}
|
||||
|
||||
|
||||
@@ -103,10 +103,6 @@ func (l *Library) load(config *compileopts.Config, tmpdir string) (job *compileJ
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
err = os.Chmod(temporaryHeaderPath, 0o755) // TempDir uses 0o700 by default
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
err = os.Rename(temporaryHeaderPath, headerPath)
|
||||
if err != nil {
|
||||
switch {
|
||||
@@ -186,10 +182,6 @@ func (l *Library) load(config *compileopts.Config, tmpdir string) (job *compileJ
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = os.Chmod(f.Name(), 0o644) // TempFile uses 0o600 by default
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
// Store this archive in the cache.
|
||||
return os.Rename(f.Name(), archiveFilePath)
|
||||
},
|
||||
|
||||
+1
-1
@@ -16,7 +16,7 @@ import (
|
||||
)
|
||||
|
||||
/*
|
||||
#include <clang-c/Index.h> // If this fails, libclang headers aren't available. Please take a look here: https://tinygo.org/docs/guides/build/
|
||||
#include <clang-c/Index.h> // if this fails, install libclang-11-dev
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
|
||||
@@ -5,12 +5,12 @@ package cgo
|
||||
|
||||
/*
|
||||
#cgo linux CFLAGS: -I/usr/lib/llvm-11/include
|
||||
#cgo darwin,amd64 CFLAGS: -I/usr/local/opt/llvm@11/include
|
||||
#cgo darwin,arm64 CFLAGS: -I/opt/homebrew/opt/llvm@11/include
|
||||
#cgo darwin amd64 CFLAGS: -I/usr/local/opt/llvm@11/include
|
||||
#cgo darwin arm64 CFLAGS: -I/opt/homebrew/opt/llvm@11/include
|
||||
#cgo freebsd CFLAGS: -I/usr/local/llvm11/include
|
||||
#cgo linux LDFLAGS: -L/usr/lib/llvm-11/lib -lclang
|
||||
#cgo darwin,amd64 LDFLAGS: -L/usr/local/opt/llvm@11/lib -lclang -lffi
|
||||
#cgo darwin,arm64 LDFLAGS: -L/opt/homebrew/opt/llvm@11/lib -lclang -lffi
|
||||
#cgo darwin amd64 LDFLAGS: -L/usr/local/opt/llvm@11/lib -lclang -lffi
|
||||
#cgo darwin arm64 LDFLAGS: -L/opt/homebrew/opt/llvm@11/lib -lclang -lffi
|
||||
#cgo freebsd LDFLAGS: -L/usr/local/llvm11/lib -lclang
|
||||
*/
|
||||
import "C"
|
||||
|
||||
@@ -5,12 +5,12 @@ package cgo
|
||||
|
||||
/*
|
||||
#cgo linux CFLAGS: -I/usr/lib/llvm-12/include
|
||||
#cgo darwin,amd64 CFLAGS: -I/usr/local/opt/llvm@12/include
|
||||
#cgo darwin,arm64 CFLAGS: -I/opt/homebrew/opt/llvm@12/include
|
||||
#cgo darwin amd64 CFLAGS: -I/usr/local/opt/llvm@12/include
|
||||
#cgo darwin arm64 CFLAGS: -I/opt/homebrew/opt/llvm@12/include
|
||||
#cgo freebsd CFLAGS: -I/usr/local/llvm12/include
|
||||
#cgo linux LDFLAGS: -L/usr/lib/llvm-12/lib -lclang
|
||||
#cgo darwin,amd64 LDFLAGS: -L/usr/local/opt/llvm@12/lib -lclang -lffi
|
||||
#cgo darwin,arm64 LDFLAGS: -L/opt/homebrew/opt/llvm@12/lib -lclang -lffi
|
||||
#cgo darwin amd64 LDFLAGS: -L/usr/local/opt/llvm@12/lib -lclang -lffi
|
||||
#cgo darwin arm64 LDFLAGS: -L/opt/homebrew/opt/llvm@12/lib -lclang -lffi
|
||||
#cgo freebsd LDFLAGS: -L/usr/local/llvm12/lib -lclang
|
||||
*/
|
||||
import "C"
|
||||
|
||||
@@ -5,12 +5,12 @@ package cgo
|
||||
|
||||
/*
|
||||
#cgo linux CFLAGS: -I/usr/lib/llvm-13/include
|
||||
#cgo darwin,amd64 CFLAGS: -I/usr/local/opt/llvm@13/include
|
||||
#cgo darwin,arm64 CFLAGS: -I/opt/homebrew/opt/llvm@13/include
|
||||
#cgo darwin amd64 CFLAGS: -I/usr/local/opt/llvm@13/include
|
||||
#cgo darwin arm64 CFLAGS: -I/opt/homebrew/opt/llvm@13/include
|
||||
#cgo freebsd CFLAGS: -I/usr/local/llvm13/include
|
||||
#cgo linux LDFLAGS: -L/usr/lib/llvm-13/lib -lclang
|
||||
#cgo darwin,amd64 LDFLAGS: -L/usr/local/opt/llvm@13/lib -lclang -lffi
|
||||
#cgo darwin,arm64 LDFLAGS: -L/opt/homebrew/opt/llvm@13/lib -lclang -lffi
|
||||
#cgo darwin amd64 LDFLAGS: -L/usr/local/opt/llvm@13/lib -lclang -lffi
|
||||
#cgo darwin arm64 LDFLAGS: -L/opt/homebrew/opt/llvm@13/lib -lclang -lffi
|
||||
#cgo freebsd LDFLAGS: -L/usr/local/llvm13/lib -lclang
|
||||
*/
|
||||
import "C"
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
// are slightly different from the ones defined in libclang.go, but they
|
||||
// should be ABI compatible.
|
||||
|
||||
#include <clang-c/Index.h> // If this fails, libclang headers aren't available. Please take a look here: https://tinygo.org/docs/guides/build/
|
||||
#include <clang-c/Index.h> // if this fails, install libclang-11-dev
|
||||
|
||||
CXCursor tinygo_clang_getTranslationUnitCursor(CXTranslationUnit tu) {
|
||||
return clang_getTranslationUnitCursor(tu);
|
||||
|
||||
@@ -176,34 +176,6 @@ func (c *Config) AutomaticStackSize() bool {
|
||||
return false
|
||||
}
|
||||
|
||||
// UseThinLTO returns whether ThinLTO should be used for the given target. Some
|
||||
// targets (such as wasm) are not yet supported.
|
||||
// We should try and remove as many exceptions as possible in the future, so
|
||||
// that this optimization can be applied in more places.
|
||||
func (c *Config) UseThinLTO() bool {
|
||||
parts := strings.Split(c.Triple(), "-")
|
||||
if parts[0] == "wasm32" {
|
||||
// wasm-ld doesn't seem to support ThinLTO yet.
|
||||
return false
|
||||
}
|
||||
if parts[0] == "avr" || parts[0] == "xtensa" {
|
||||
// These use external (GNU) linkers which might perhaps support ThinLTO
|
||||
// through a plugin, but it's too much hassle to set up.
|
||||
return false
|
||||
}
|
||||
if len(parts) >= 2 && strings.HasPrefix(parts[2], "macos") {
|
||||
// We use an external linker here at the moment.
|
||||
return false
|
||||
}
|
||||
if len(parts) >= 2 && parts[2] == "windows" {
|
||||
// Linker error (undefined runtime.trackedGlobalsBitmap) when linking
|
||||
// for Windows. Disable it for now until that's figured out and fixed.
|
||||
return false
|
||||
}
|
||||
// Other architectures support ThinLTO.
|
||||
return true
|
||||
}
|
||||
|
||||
// RP2040BootPatch returns whether the RP2040 boot patch should be applied that
|
||||
// calculates and patches in the checksum for the 2nd stage bootloader.
|
||||
func (c *Config) RP2040BootPatch() bool {
|
||||
@@ -245,29 +217,6 @@ func (c *Config) LibcPath(name string) (path string, precompiled bool) {
|
||||
return filepath.Join(goenv.Get("GOCACHE"), name+"-"+archname), false
|
||||
}
|
||||
|
||||
// DefaultBinaryExtension returns the default extension for binaries, such as
|
||||
// .exe, .wasm, or no extension (depending on the target).
|
||||
func (c *Config) DefaultBinaryExtension() string {
|
||||
parts := strings.Split(c.Triple(), "-")
|
||||
if parts[0] == "wasm32" {
|
||||
// WebAssembly files always have the .wasm file extension.
|
||||
return ".wasm"
|
||||
}
|
||||
if len(parts) >= 3 && parts[2] == "windows" {
|
||||
// Windows uses .exe.
|
||||
return ".exe"
|
||||
}
|
||||
if len(parts) >= 3 && parts[2] == "unknown" {
|
||||
// There appears to be a convention to use the .elf file extension for
|
||||
// ELF files intended for microcontrollers. I'm not aware of the origin
|
||||
// of this, it's just something that is used by many projects.
|
||||
// I think it's a good tradition, so let's keep it.
|
||||
return ".elf"
|
||||
}
|
||||
// Linux, MacOS, etc, don't use a file extension. Use it as a fallback.
|
||||
return ""
|
||||
}
|
||||
|
||||
// CFlags returns the flags to pass to the C compiler. This is necessary for CGo
|
||||
// preprocessing.
|
||||
func (c *Config) CFlags() []string {
|
||||
|
||||
@@ -32,8 +32,8 @@ type Options struct {
|
||||
PrintIR bool
|
||||
DumpSSA bool
|
||||
VerifyIR bool
|
||||
PrintCommands func(cmd string, args ...string) `json:"-"`
|
||||
Semaphore chan struct{} `json:"-"` // -p flag controls cap
|
||||
PrintCommands func(cmd string, args ...string)
|
||||
Semaphore chan struct{} // -p flag controls cap
|
||||
Debug bool
|
||||
PrintSizes string
|
||||
PrintAllocs *regexp.Regexp // regexp string
|
||||
@@ -46,7 +46,6 @@ type Options struct {
|
||||
OpenOCDCommands []string
|
||||
LLVMFeatures string
|
||||
Directory string
|
||||
PrintJSON bool
|
||||
}
|
||||
|
||||
// Verify performs a validation on the given options, raising an error if options are not valid.
|
||||
|
||||
@@ -234,15 +234,10 @@ func Sizes(machine llvm.TargetMachine) types.Sizes {
|
||||
panic("unknown pointer size")
|
||||
}
|
||||
|
||||
// Construct a complex128 type because that's likely the type with the
|
||||
// biggest alignment on most/all ABIs.
|
||||
ctx := llvm.NewContext()
|
||||
defer ctx.Dispose()
|
||||
complex128Type := ctx.StructType([]llvm.Type{ctx.DoubleType(), ctx.DoubleType()}, false)
|
||||
return &stdSizes{
|
||||
IntSize: int64(intWidth / 8),
|
||||
PtrSize: int64(targetData.PointerSize()),
|
||||
MaxAlign: int64(targetData.ABITypeAlignment(complex128Type)),
|
||||
MaxAlign: int64(targetData.PrefTypeAlignment(targetData.IntPtrType())),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1233,7 +1228,7 @@ func (b *builder) createBuiltin(argTypes []types.Type, argValues []llvm.Value, c
|
||||
case "cap":
|
||||
value := argValues[0]
|
||||
var llvmCap llvm.Value
|
||||
switch argTypes[0].Underlying().(type) {
|
||||
switch argTypes[0].(type) {
|
||||
case *types.Chan:
|
||||
llvmCap = b.createRuntimeCall("chanCap", []llvm.Value{value}, "cap")
|
||||
case *types.Slice:
|
||||
|
||||
@@ -15,5 +15,5 @@ require (
|
||||
golang.org/x/sys v0.0.0-20220114195835-da31bd327af9
|
||||
golang.org/x/tools v0.1.6-0.20210813165731-45389f592fe9
|
||||
gopkg.in/yaml.v2 v2.4.0
|
||||
tinygo.org/x/go-llvm v0.0.0-20220211075103-ee4aad45c3a1
|
||||
tinygo.org/x/go-llvm v0.0.0-20220121152956-4fa2ab2718f3
|
||||
)
|
||||
|
||||
@@ -80,5 +80,5 @@ gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8
|
||||
gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
|
||||
gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY=
|
||||
gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
|
||||
tinygo.org/x/go-llvm v0.0.0-20220211075103-ee4aad45c3a1 h1:6G8AxueDdqobCEqQrmHPLaEH1AZ1p6Y7rGElDNT7N98=
|
||||
tinygo.org/x/go-llvm v0.0.0-20220211075103-ee4aad45c3a1/go.mod h1:GFbusT2VTA4I+l4j80b17KFK+6whv69Wtny5U+T8RR0=
|
||||
tinygo.org/x/go-llvm v0.0.0-20220121152956-4fa2ab2718f3 h1:vQSFy0kNQegAfL/F6iyWQa4bF941Xc1gyJUkGy2m448=
|
||||
tinygo.org/x/go-llvm v0.0.0-20220121152956-4fa2ab2718f3/go.mod h1:GFbusT2VTA4I+l4j80b17KFK+6whv69Wtny5U+T8RR0=
|
||||
|
||||
@@ -14,12 +14,6 @@ import (
|
||||
// Update this value before release of new version of software.
|
||||
const Version = "0.23.0-dev"
|
||||
|
||||
var (
|
||||
// This variable is set at build time using -ldflags parameters.
|
||||
// See: https://stackoverflow.com/a/11355611
|
||||
GitSha1 string
|
||||
)
|
||||
|
||||
// GetGorootVersion returns the major and minor version for a given GOROOT path.
|
||||
// If the goroot cannot be determined, (0, 0) is returned.
|
||||
func GetGorootVersion(goroot string) (major, minor int, err error) {
|
||||
|
||||
@@ -492,9 +492,9 @@ func (r *runner) run(fn *function, params []value, parentMem *memoryView, indent
|
||||
// Call a function with a definition available. Run it as usual,
|
||||
// possibly trying to recover from it if it failed to execute.
|
||||
if r.debug {
|
||||
argStrings := make([]string, len(operands)-1)
|
||||
for i, v := range operands[1:] {
|
||||
argStrings[i] = v.String()
|
||||
argStrings := make([]string, len(operands))
|
||||
for i := range argStrings {
|
||||
argStrings[i] = operands[i+1].String()
|
||||
}
|
||||
fmt.Fprintln(os.Stderr, indent+"call:", callFn.name+"("+strings.Join(argStrings, ", ")+")")
|
||||
}
|
||||
|
||||
@@ -36,6 +36,12 @@ import (
|
||||
"go.bug.st/serial/enumerator"
|
||||
)
|
||||
|
||||
var (
|
||||
// This variable is set at build time using -ldflags parameters.
|
||||
// See: https://stackoverflow.com/a/11355611
|
||||
gitSha1 string
|
||||
)
|
||||
|
||||
// commandError is an error type to wrap os/exec.Command errors. This provides
|
||||
// some more information regarding what went wrong while running a command.
|
||||
type commandError struct {
|
||||
@@ -142,27 +148,7 @@ func Build(pkgName, outpath string, options *compileopts.Options) error {
|
||||
return err
|
||||
}
|
||||
|
||||
if options.PrintJSON {
|
||||
b, err := json.MarshalIndent(config, "", " ")
|
||||
if err != nil {
|
||||
handleCompilerError(err)
|
||||
}
|
||||
fmt.Printf("%s\n", string(b))
|
||||
return nil
|
||||
}
|
||||
|
||||
return builder.Build(pkgName, outpath, config, func(result builder.BuildResult) error {
|
||||
if outpath == "" {
|
||||
if strings.HasSuffix(pkgName, ".go") {
|
||||
// A Go file was specified directly on the command line.
|
||||
// Base the binary name off of it.
|
||||
outpath = filepath.Base(pkgName[:len(pkgName)-3]) + config.DefaultBinaryExtension()
|
||||
} else {
|
||||
// Pick a default output path based on the main directory.
|
||||
outpath = filepath.Base(result.MainDir) + config.DefaultBinaryExtension()
|
||||
}
|
||||
}
|
||||
|
||||
if err := os.Rename(result.Binary, outpath); err != nil {
|
||||
// Moving failed. Do a file copy.
|
||||
inf, err := os.Open(result.Binary)
|
||||
@@ -1026,8 +1012,8 @@ func getBMPPorts() (gdbPort, uartPort string, err error) {
|
||||
|
||||
func usage(command string) {
|
||||
version := goenv.Version
|
||||
if strings.HasSuffix(version, "-dev") && goenv.GitSha1 != "" {
|
||||
version += "-" + goenv.GitSha1
|
||||
if strings.HasSuffix(version, "-dev") && gitSha1 != "" {
|
||||
version += "-" + gitSha1
|
||||
}
|
||||
|
||||
switch command {
|
||||
@@ -1222,13 +1208,13 @@ func main() {
|
||||
llvmFeatures := flag.String("llvm-features", "", "comma separated LLVM features to enable")
|
||||
cpuprofile := flag.String("cpuprofile", "", "cpuprofile output")
|
||||
|
||||
var flagJSON, flagDeps, flagTest bool
|
||||
if command == "help" || command == "list" || command == "info" || command == "build" {
|
||||
flag.BoolVar(&flagJSON, "json", false, "print data in JSON format")
|
||||
var flagJSON, flagDeps, flagTest *bool
|
||||
if command == "help" || command == "list" || command == "info" {
|
||||
flagJSON = flag.Bool("json", false, "print data in JSON format")
|
||||
}
|
||||
if command == "help" || command == "list" {
|
||||
flag.BoolVar(&flagDeps, "deps", false, "supply -deps flag to go list")
|
||||
flag.BoolVar(&flagTest, "test", false, "supply -test flag to go list")
|
||||
flagDeps = flag.Bool("deps", false, "supply -deps flag to go list")
|
||||
flagTest = flag.Bool("test", false, "supply -test flag to go list")
|
||||
}
|
||||
var outpath string
|
||||
if command == "help" || command == "build" || command == "build-library" || command == "test" {
|
||||
@@ -1305,7 +1291,6 @@ func main() {
|
||||
Programmer: *programmer,
|
||||
OpenOCDCommands: ocdCommands,
|
||||
LLVMFeatures: *llvmFeatures,
|
||||
PrintJSON: flagJSON,
|
||||
}
|
||||
if *printCommands {
|
||||
options.PrintCommands = printCommand
|
||||
@@ -1334,6 +1319,11 @@ func main() {
|
||||
|
||||
switch command {
|
||||
case "build":
|
||||
if outpath == "" {
|
||||
fmt.Fprintln(os.Stderr, "No output filename supplied (-o).")
|
||||
usage(command)
|
||||
os.Exit(1)
|
||||
}
|
||||
pkgName := "."
|
||||
if flag.NArg() == 1 {
|
||||
pkgName = filepath.ToSlash(flag.Arg(0))
|
||||
@@ -1542,7 +1532,7 @@ func main() {
|
||||
fmt.Fprintln(os.Stderr, err)
|
||||
os.Exit(1)
|
||||
}
|
||||
if flagJSON {
|
||||
if *flagJSON {
|
||||
json, _ := json.MarshalIndent(struct {
|
||||
GOROOT string `json:"goroot"`
|
||||
GOOS string `json:"goos"`
|
||||
@@ -1581,13 +1571,13 @@ func main() {
|
||||
os.Exit(1)
|
||||
}
|
||||
var extraArgs []string
|
||||
if flagJSON {
|
||||
if *flagJSON {
|
||||
extraArgs = append(extraArgs, "-json")
|
||||
}
|
||||
if flagDeps {
|
||||
if *flagDeps {
|
||||
extraArgs = append(extraArgs, "-deps")
|
||||
}
|
||||
if flagTest {
|
||||
if *flagTest {
|
||||
extraArgs = append(extraArgs, "-test")
|
||||
}
|
||||
cmd, err := loader.List(config, extraArgs, flag.Args())
|
||||
@@ -1624,8 +1614,8 @@ func main() {
|
||||
goversion = s
|
||||
}
|
||||
version := goenv.Version
|
||||
if strings.HasSuffix(goenv.Version, "-dev") && goenv.GitSha1 != "" {
|
||||
version += "-" + goenv.GitSha1
|
||||
if strings.HasSuffix(goenv.Version, "-dev") && gitSha1 != "" {
|
||||
version += "-" + gitSha1
|
||||
}
|
||||
fmt.Printf("tinygo version %s %s/%s (using go version %s and LLVM version %s)\n", version, runtime.GOOS, runtime.GOARCH, goversion, llvm.Version)
|
||||
case "env":
|
||||
|
||||
@@ -1,31 +0,0 @@
|
||||
// This is a echo console running on the os.Stdin and os.Stdout.
|
||||
// Stdin and os.Stdout are connected to machine.Serial in the baremetal target.
|
||||
//
|
||||
// Serial can be switched with the -serial option as follows
|
||||
// 1. tinygo flash -target wioterminal -serial usb examples/echo2
|
||||
// 2. tinygo flash -target wioterminal -serial uart examples/echo2
|
||||
//
|
||||
// This example will also work with standard Go.
|
||||
package main
|
||||
|
||||
import (
|
||||
"bufio"
|
||||
"fmt"
|
||||
"os"
|
||||
)
|
||||
|
||||
func main() {
|
||||
fmt.Printf("Echo console enabled. Type something then press enter:\r\n")
|
||||
|
||||
scanner := bufio.NewScanner(os.Stdin)
|
||||
|
||||
for {
|
||||
msg := ""
|
||||
fmt.Scanf("%s\n", &msg)
|
||||
fmt.Printf("You typed (scanf) : %s\r\n", msg)
|
||||
|
||||
if scanner.Scan() {
|
||||
fmt.Printf("You typed (scanner) : %s\r\n", scanner.Text())
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,49 +0,0 @@
|
||||
//go:build esp32c312f
|
||||
// +build esp32c312f
|
||||
|
||||
package machine
|
||||
|
||||
// Built-in RGB LED
|
||||
const (
|
||||
LED_RED = IO3
|
||||
LED_GREEN = IO4
|
||||
LED_BLUE = IO5
|
||||
LED = LED_RED
|
||||
)
|
||||
|
||||
const (
|
||||
IO0 Pin = 0
|
||||
IO1 Pin = 1
|
||||
IO10 Pin = 10
|
||||
IO18 Pin = 18
|
||||
IO19 Pin = 19
|
||||
IO2 Pin = 2
|
||||
IO3 Pin = 3
|
||||
IO4 Pin = 4
|
||||
IO5 Pin = 5
|
||||
IO6 Pin = 6
|
||||
IO7 Pin = 7
|
||||
IO8 Pin = 8
|
||||
IO9 Pin = 9
|
||||
RXD Pin = 20
|
||||
TXD Pin = 21
|
||||
)
|
||||
|
||||
// ADC pins
|
||||
const (
|
||||
ADC0 Pin = ADC1_0
|
||||
ADC1 Pin = ADC2_0
|
||||
|
||||
ADC1_0 Pin = IO0
|
||||
ADC1_1 Pin = IO1
|
||||
ADC1_2 Pin = IO2
|
||||
ADC1_3 Pin = IO3
|
||||
ADC1_4 Pin = IO4
|
||||
ADC2_0 Pin = IO5
|
||||
)
|
||||
|
||||
// UART0 pins
|
||||
const (
|
||||
UART_TX_PIN = TXD
|
||||
UART_RX_PIN = RXD
|
||||
)
|
||||
@@ -1742,7 +1742,6 @@ type USBCDC struct {
|
||||
waitTxc bool
|
||||
waitTxcRetryCount uint8
|
||||
sent bool
|
||||
configured bool
|
||||
}
|
||||
|
||||
var (
|
||||
@@ -1924,13 +1923,6 @@ func (usbcdc *USBCDC) Configure(config UARTConfig) {
|
||||
// enable IRQ
|
||||
intr := interrupt.New(sam.IRQ_USB, handleUSB)
|
||||
intr.Enable()
|
||||
|
||||
usbcdc.configured = true
|
||||
}
|
||||
|
||||
// Configured returns whether usbcdc is configured or not.
|
||||
func (usbcdc *USBCDC) Configured() bool {
|
||||
return usbcdc.configured
|
||||
}
|
||||
|
||||
func handlePadCalibration() {
|
||||
|
||||
@@ -1033,9 +1033,6 @@ func (uart *UART) Configure(config UARTConfig) error {
|
||||
uart.Bus.CTRLA.Set((1 << sam.SERCOM_USART_INT_CTRLA_MODE_Pos) |
|
||||
(1 << sam.SERCOM_USART_INT_CTRLA_SAMPR_Pos)) // sample rate of 16x
|
||||
|
||||
// set clock
|
||||
setSERCOMClockGenerator(uart.SERCOM, sam.GCLK_PCHCTRL_GEN_GCLK1)
|
||||
|
||||
// Set baud rate
|
||||
uart.SetBaudRate(config.BaudRate)
|
||||
|
||||
@@ -1127,8 +1124,7 @@ type I2CConfig struct {
|
||||
|
||||
const (
|
||||
// SERCOM_FREQ_REF is always reference frequency on SAMD51 regardless of CPU speed.
|
||||
SERCOM_FREQ_REF = 48000000
|
||||
SERCOM_FREQ_REF_GCLK0 = 120000000
|
||||
SERCOM_FREQ_REF = 48000000
|
||||
|
||||
// Default rise time in nanoseconds, based on 4.7K ohm pull up resistors
|
||||
riseTimeNanoseconds = 125
|
||||
@@ -1182,9 +1178,6 @@ func (i2c *I2C) Configure(config I2CConfig) error {
|
||||
i2c.Bus.SYNCBUSY.HasBits(sam.SERCOM_I2CM_SYNCBUSY_SWRST) {
|
||||
}
|
||||
|
||||
// set clock
|
||||
setSERCOMClockGenerator(i2c.SERCOM, sam.GCLK_PCHCTRL_GEN_GCLK1)
|
||||
|
||||
// Set i2c controller mode
|
||||
//SERCOM_I2CM_CTRLA_MODE( I2C_MASTER_OPERATION )
|
||||
// sam.SERCOM_I2CM_CTRLA_MODE_I2C_MASTER = 5?
|
||||
@@ -1490,18 +1483,8 @@ func (spi SPI) Configure(config SPIConfig) error {
|
||||
spi.Bus.CTRLA.ClearBits(sam.SERCOM_SPIM_CTRLA_CPOL)
|
||||
}
|
||||
|
||||
// set clock
|
||||
freqRef := uint32(0)
|
||||
if config.Frequency > SERCOM_FREQ_REF/2 {
|
||||
setSERCOMClockGenerator(spi.SERCOM, sam.GCLK_PCHCTRL_GEN_GCLK0)
|
||||
freqRef = uint32(SERCOM_FREQ_REF_GCLK0)
|
||||
} else {
|
||||
setSERCOMClockGenerator(spi.SERCOM, sam.GCLK_PCHCTRL_GEN_GCLK1)
|
||||
freqRef = uint32(SERCOM_FREQ_REF)
|
||||
}
|
||||
|
||||
// Set synch speed for SPI
|
||||
baudRate := freqRef / (2 * config.Frequency)
|
||||
baudRate := SERCOM_FREQ_REF / (2 * config.Frequency)
|
||||
if baudRate > 0 {
|
||||
baudRate--
|
||||
}
|
||||
@@ -1982,7 +1965,6 @@ type USBCDC struct {
|
||||
waitTxc bool
|
||||
waitTxcRetryCount uint8
|
||||
sent bool
|
||||
configured bool
|
||||
}
|
||||
|
||||
var (
|
||||
@@ -2167,13 +2149,6 @@ func (usbcdc *USBCDC) Configure(config UARTConfig) {
|
||||
interrupt.New(sam.IRQ_USB_SOF_HSOF, handleUSBIRQ).Enable()
|
||||
interrupt.New(sam.IRQ_USB_TRCPT0, handleUSBIRQ).Enable()
|
||||
interrupt.New(sam.IRQ_USB_TRCPT1, handleUSBIRQ).Enable()
|
||||
|
||||
usbcdc.configured = true
|
||||
}
|
||||
|
||||
// Configured returns whether usbcdc is configured or not.
|
||||
func (usbcdc *USBCDC) Configured() bool {
|
||||
return usbcdc.configured
|
||||
}
|
||||
|
||||
func handlePadCalibration() {
|
||||
|
||||
@@ -28,42 +28,6 @@ var (
|
||||
sercomSPIM5 = SPI{Bus: sam.SERCOM5_SPIM, SERCOM: 5}
|
||||
)
|
||||
|
||||
// setSERCOMClockGenerator sets the GCLK for sercom
|
||||
func setSERCOMClockGenerator(sercom uint8, gclk uint32) {
|
||||
switch sercom {
|
||||
case 0:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM0_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 1:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM1_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 2:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM2_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 3:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM3_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 4:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM4_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 5:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM5_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
}
|
||||
}
|
||||
|
||||
// This chip has three TCC peripherals, which have PWM as one feature.
|
||||
var (
|
||||
TCC0 = (*TCC)(sam.TCC0)
|
||||
|
||||
@@ -28,42 +28,6 @@ var (
|
||||
sercomSPIM5 = SPI{Bus: sam.SERCOM5_SPIM, SERCOM: 5}
|
||||
)
|
||||
|
||||
// setSERCOMClockGenerator sets the GCLK for sercom
|
||||
func setSERCOMClockGenerator(sercom uint8, gclk uint32) {
|
||||
switch sercom {
|
||||
case 0:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM0_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 1:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM1_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 2:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM2_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 3:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM3_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 4:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM4_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 5:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM5_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
}
|
||||
}
|
||||
|
||||
// This chip has five TCC peripherals, which have PWM as one feature.
|
||||
var (
|
||||
TCC0 = (*TCC)(sam.TCC0)
|
||||
|
||||
@@ -28,42 +28,6 @@ var (
|
||||
sercomSPIM5 = SPI{Bus: sam.SERCOM5_SPIM, SERCOM: 5}
|
||||
)
|
||||
|
||||
// setSERCOMClockGenerator sets the GCLK for sercom
|
||||
func setSERCOMClockGenerator(sercom uint8, gclk uint32) {
|
||||
switch sercom {
|
||||
case 0:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM0_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 1:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM1_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 2:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM2_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 3:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM3_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 4:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM4_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 5:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM5_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
}
|
||||
}
|
||||
|
||||
// This chip has five TCC peripherals, which have PWM as one feature.
|
||||
var (
|
||||
TCC0 = (*TCC)(sam.TCC0)
|
||||
|
||||
@@ -32,52 +32,6 @@ var (
|
||||
sercomSPIM7 = SPI{Bus: sam.SERCOM7_SPIM, SERCOM: 7}
|
||||
)
|
||||
|
||||
// setSERCOMClockGenerator sets the GCLK for sercom
|
||||
func setSERCOMClockGenerator(sercom uint8, gclk uint32) {
|
||||
switch sercom {
|
||||
case 0:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM0_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 1:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM1_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 2:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM2_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 3:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM3_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 4:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM4_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 5:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM5_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 6:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM6_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM6_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM6_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 7:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM7_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM7_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM7_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
}
|
||||
}
|
||||
|
||||
// This chip has five TCC peripherals, which have PWM as one feature.
|
||||
var (
|
||||
TCC0 = (*TCC)(sam.TCC0)
|
||||
|
||||
@@ -32,52 +32,6 @@ var (
|
||||
sercomSPIM7 = SPI{Bus: sam.SERCOM7_SPIM, SERCOM: 7}
|
||||
)
|
||||
|
||||
// setSERCOMClockGenerator sets the GCLK for sercom
|
||||
func setSERCOMClockGenerator(sercom uint8, gclk uint32) {
|
||||
switch sercom {
|
||||
case 0:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM0_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 1:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM1_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 2:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM2_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 3:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM3_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 4:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM4_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 5:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM5_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 6:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM6_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM6_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM6_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 7:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM7_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM7_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM7_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
}
|
||||
}
|
||||
|
||||
// This chip has five TCC peripherals, which have PWM as one feature.
|
||||
var (
|
||||
TCC0 = (*TCC)(sam.TCC0)
|
||||
|
||||
@@ -28,42 +28,6 @@ var (
|
||||
sercomSPIM5 = SPI{Bus: sam.SERCOM5_SPIM, SERCOM: 5}
|
||||
)
|
||||
|
||||
// setSERCOMClockGenerator sets the GCLK for sercom
|
||||
func setSERCOMClockGenerator(sercom uint8, gclk uint32) {
|
||||
switch sercom {
|
||||
case 0:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM0_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 1:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM1_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 2:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM2_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 3:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM3_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 4:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM4_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 5:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM5_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
}
|
||||
}
|
||||
|
||||
// This chip has five TCC peripherals, which have PWM as one feature.
|
||||
var (
|
||||
TCC0 = (*TCC)(sam.TCC0)
|
||||
|
||||
@@ -32,52 +32,6 @@ var (
|
||||
sercomSPIM7 = SPI{Bus: sam.SERCOM7_SPIM, SERCOM: 7}
|
||||
)
|
||||
|
||||
// setSERCOMClockGenerator sets the GCLK for sercom
|
||||
func setSERCOMClockGenerator(sercom uint8, gclk uint32) {
|
||||
switch sercom {
|
||||
case 0:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM0_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM0_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 1:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBAMASK.SetBits(sam.MCLK_APBAMASK_SERCOM1_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM1_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 2:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM2_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM2_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 3:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBBMASK.SetBits(sam.MCLK_APBBMASK_SERCOM3_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM3_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 4:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM4_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM4_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 5:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM5_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM5_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 6:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM6_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM6_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM6_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
case 7:
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM7_CORE].ClearBits(sam.GCLK_PCHCTRL_CHEN)
|
||||
sam.MCLK.APBDMASK.SetBits(sam.MCLK_APBDMASK_SERCOM7_)
|
||||
sam.GCLK.PCHCTRL[sam.PCHCTRL_GCLK_SERCOM7_CORE].Set((gclk << sam.GCLK_PCHCTRL_GEN_Pos) |
|
||||
sam.GCLK_PCHCTRL_CHEN)
|
||||
}
|
||||
}
|
||||
|
||||
// This chip has five TCC peripherals, which have PWM as one feature.
|
||||
var (
|
||||
TCC0 = (*TCC)(sam.TCC0)
|
||||
|
||||
@@ -5,15 +5,11 @@ package machine
|
||||
|
||||
import (
|
||||
"device/esp"
|
||||
"runtime/interrupt"
|
||||
"runtime/volatile"
|
||||
"sync"
|
||||
"unsafe"
|
||||
)
|
||||
|
||||
const deviceName = esp.Device
|
||||
const maxPin = 22
|
||||
const cpuInterruptFromPin = 6
|
||||
|
||||
// CPUFrequency returns the current CPU frequency of the chip.
|
||||
// Currently it is a fixed frequency but it may allow changing in the future.
|
||||
@@ -28,18 +24,6 @@ const (
|
||||
PinInputPulldown
|
||||
)
|
||||
|
||||
type PinChange uint8
|
||||
|
||||
// Pin change interrupt constants for SetInterrupt.
|
||||
const (
|
||||
PinNoInterrupt PinChange = iota
|
||||
PinRising
|
||||
PinFalling
|
||||
PinToggle
|
||||
PinLowLevel
|
||||
PinHighLevel
|
||||
)
|
||||
|
||||
// Configure this pin with the given configuration.
|
||||
func (p Pin) Configure(config PinConfig) {
|
||||
if p == NoPin {
|
||||
@@ -100,11 +84,6 @@ func (p Pin) mux() *volatile.Register32 {
|
||||
return (*volatile.Register32)(unsafe.Pointer((uintptr(unsafe.Pointer(&esp.IO_MUX.GPIO0)) + uintptr(p)*4)))
|
||||
}
|
||||
|
||||
// pin returns the PIN register corresponding to the given GPIO pin.
|
||||
func (p Pin) pin() *volatile.Register32 {
|
||||
return (*volatile.Register32)(unsafe.Pointer((uintptr(unsafe.Pointer(&esp.GPIO.PIN0)) + uintptr(p)*4)))
|
||||
}
|
||||
|
||||
// Set the pin to high or low.
|
||||
// Warning: only use this on an output pin!
|
||||
func (p Pin) Set(value bool) {
|
||||
@@ -150,70 +129,6 @@ func (p Pin) portMaskClear() (*volatile.Register32, uint32) {
|
||||
return &esp.GPIO.OUT_W1TC, 1 << p
|
||||
}
|
||||
|
||||
// SetInterrupt sets an interrupt to be executed when a particular pin changes
|
||||
// state. The pin should already be configured as an input, including a pull up
|
||||
// or down if no external pull is provided.
|
||||
//
|
||||
// You can pass a nil func to unset the pin change interrupt. If you do so,
|
||||
// the change parameter is ignored and can be set to any value (such as 0).
|
||||
// If the pin is already configured with a callback, you must first unset
|
||||
// this pins interrupt before you can set a new callback.
|
||||
func (p Pin) SetInterrupt(change PinChange, callback func(Pin)) (err error) {
|
||||
if p >= maxPin {
|
||||
return ErrInvalidInputPin
|
||||
}
|
||||
|
||||
if callback == nil || change == PinNoInterrupt {
|
||||
// Disable this pin interrupt
|
||||
p.pin().ClearBits(esp.GPIO_PIN_PIN_INT_TYPE_Msk | esp.GPIO_PIN_PIN_INT_ENA_Msk)
|
||||
|
||||
if pinCallbacks[p] != nil {
|
||||
pinCallbacks[p] = nil
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
if pinCallbacks[p] != nil {
|
||||
// The pin was already configured.
|
||||
// To properly re-configure a pin, unset it first and set a new
|
||||
// configuration.
|
||||
return ErrNoPinChangeChannel
|
||||
}
|
||||
pinCallbacks[p] = callback
|
||||
|
||||
onceSetupPinInterrupt.Do(func() {
|
||||
err = setupPinInterrupt()
|
||||
})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
p.pin().Set(
|
||||
(p.pin().Get() & ^uint32(esp.GPIO_PIN_PIN_INT_TYPE_Msk|esp.GPIO_PIN_PIN_INT_ENA_Msk)) |
|
||||
uint32(change)<<esp.GPIO_PIN_PIN_INT_TYPE_Pos | uint32(1)<<esp.GPIO_PIN_PIN_INT_ENA_Pos)
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
var (
|
||||
pinCallbacks [maxPin]func(Pin)
|
||||
onceSetupPinInterrupt sync.Once
|
||||
)
|
||||
|
||||
func setupPinInterrupt() error {
|
||||
esp.INTERRUPT_CORE0.GPIO_INTERRUPT_PRO_MAP.Set(cpuInterruptFromPin)
|
||||
return interrupt.New(cpuInterruptFromPin, func(interrupt.Interrupt) {
|
||||
status := esp.GPIO.STATUS.Get()
|
||||
for i, mask := 0, uint32(1); i < maxPin; i, mask = i+1, mask<<1 {
|
||||
if (status&mask) != 0 && pinCallbacks[i] != nil {
|
||||
pinCallbacks[i](Pin(i))
|
||||
}
|
||||
}
|
||||
// clear interrupt bit
|
||||
esp.GPIO.STATUS_W1TC.SetBits(status)
|
||||
}).Enable()
|
||||
}
|
||||
|
||||
var DefaultUART = UART0
|
||||
|
||||
var (
|
||||
|
||||
@@ -60,6 +60,9 @@ var (
|
||||
ErrNotConfigured = errors.New("device has not been configured")
|
||||
)
|
||||
|
||||
//go:linkname gosched runtime.Gosched
|
||||
func gosched()
|
||||
|
||||
// PutcharUART writes a byte to the UART synchronously, without using interrupts
|
||||
// or calling the scheduler
|
||||
func PutcharUART(u *UART, c byte) {
|
||||
|
||||
+4
-13
@@ -3,9 +3,7 @@
|
||||
|
||||
package machine
|
||||
|
||||
import (
|
||||
"errors"
|
||||
)
|
||||
import "errors"
|
||||
|
||||
var errUARTBufferEmpty = errors.New("UART buffer empty")
|
||||
|
||||
@@ -42,14 +40,10 @@ const (
|
||||
|
||||
// Read from the RX buffer.
|
||||
func (uart *UART) Read(data []byte) (n int, err error) {
|
||||
if len(data) == 0 {
|
||||
return 0, nil
|
||||
}
|
||||
|
||||
// check if RX buffer is empty
|
||||
size := uart.Buffered()
|
||||
for size == 0 {
|
||||
gosched()
|
||||
size = uart.Buffered()
|
||||
if size == 0 {
|
||||
return 0, nil
|
||||
}
|
||||
|
||||
// Make sure we do not read more from buffer than the data slice can hold.
|
||||
@@ -95,6 +89,3 @@ func (uart *UART) Buffered() int {
|
||||
func (uart *UART) Receive(data byte) {
|
||||
uart.Buffer.Put(data)
|
||||
}
|
||||
|
||||
//go:linkname gosched runtime.Gosched
|
||||
func gosched() int
|
||||
|
||||
+3
-7
@@ -606,14 +606,10 @@ func newUSBSetup(data []byte) usbSetup {
|
||||
|
||||
// Read from the RX buffer.
|
||||
func (usbcdc *USBCDC) Read(data []byte) (n int, err error) {
|
||||
if len(data) == 0 {
|
||||
return 0, nil
|
||||
}
|
||||
|
||||
// check if RX buffer is empty
|
||||
size := usbcdc.Buffered()
|
||||
for size == 0 {
|
||||
gosched()
|
||||
size = usbcdc.Buffered()
|
||||
if size == 0 {
|
||||
return 0, nil
|
||||
}
|
||||
|
||||
// Make sure we do not read more from buffer than the data slice can hold.
|
||||
|
||||
@@ -34,19 +34,6 @@ func (p *ProcessState) Success() bool {
|
||||
return false // TODO
|
||||
}
|
||||
|
||||
// Sys returns system-dependent exit information about
|
||||
// the process. Convert it to the appropriate underlying
|
||||
// type, such as syscall.WaitStatus on Unix, to access its contents.
|
||||
func (p *ProcessState) Sys() interface{} {
|
||||
return nil // TODO
|
||||
}
|
||||
|
||||
// ExitCode returns the exit code of the exited process, or -1
|
||||
// if the process hasn't exited or was terminated by a signal.
|
||||
func (p *ProcessState) ExitCode() int {
|
||||
return -1 // TODO
|
||||
}
|
||||
|
||||
type Process struct {
|
||||
Pid int
|
||||
}
|
||||
@@ -62,7 +49,3 @@ func (p *Process) Wait() (*ProcessState, error) {
|
||||
func (p *Process) Kill() error {
|
||||
return ErrNotImplemented
|
||||
}
|
||||
|
||||
func (p *Process) Signal(sig Signal) error {
|
||||
return ErrNotImplemented
|
||||
}
|
||||
|
||||
@@ -1,24 +0,0 @@
|
||||
package exec
|
||||
|
||||
import "os"
|
||||
|
||||
// An ExitError reports an unsuccessful exit by a command.
|
||||
type ExitError struct {
|
||||
*os.ProcessState
|
||||
|
||||
// Stderr holds a subset of the standard error output from the
|
||||
// Cmd.Output method if standard error was not otherwise being
|
||||
// collected.
|
||||
//
|
||||
// If the error output is long, Stderr may contain only a prefix
|
||||
// and suffix of the output, with the middle replaced with
|
||||
// text about the number of omitted bytes.
|
||||
//
|
||||
// Stderr is provided for debugging, for inclusion in error messages.
|
||||
// Users with other needs should redirect Cmd.Stderr as needed.
|
||||
Stderr []byte
|
||||
}
|
||||
|
||||
func (e *ExitError) Error() string {
|
||||
return e.ProcessState.String()
|
||||
}
|
||||
@@ -1,22 +0,0 @@
|
||||
// Copyright 2009 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.
|
||||
|
||||
package os
|
||||
|
||||
//go:build aix || darwin || dragonfly || freebsd || (js && wasm) || linux || netbsd || openbsd || solaris || windows
|
||||
// +build aix darwin dragonfly freebsd js,wasm linux netbsd openbsd solaris windows
|
||||
|
||||
import (
|
||||
"syscall"
|
||||
)
|
||||
|
||||
// The only signal values guaranteed to be present in the os package on all
|
||||
// systems are os.Interrupt (send the process an interrupt) and os.Kill (force
|
||||
// the process to exit). On Windows, sending os.Interrupt to a process with
|
||||
// os.Process.Signal is not implemented; it will return an error instead of
|
||||
// sending a signal.
|
||||
var (
|
||||
Interrupt Signal = syscall.SIGINT
|
||||
Kill Signal = syscall.SIGKILL
|
||||
)
|
||||
+1
-38
@@ -12,7 +12,6 @@ package os
|
||||
import (
|
||||
"errors"
|
||||
"io"
|
||||
"runtime"
|
||||
"syscall"
|
||||
)
|
||||
|
||||
@@ -180,19 +179,9 @@ func (f *File) SyscallConn() (syscall.RawConn, error) {
|
||||
return nil, ErrNotImplemented
|
||||
}
|
||||
|
||||
// fd is an internal interface that is used to try a type assertion in order to
|
||||
// call the Fd() method of the underlying file handle if it is implemented.
|
||||
type fd interface {
|
||||
Fd() uintptr
|
||||
}
|
||||
|
||||
// Fd returns the file handle referencing the open file.
|
||||
func (f *File) Fd() uintptr {
|
||||
handle, ok := f.handle.(fd)
|
||||
if ok {
|
||||
return handle.Fd()
|
||||
}
|
||||
return 0
|
||||
panic("unimplemented: os.file.Fd()")
|
||||
}
|
||||
|
||||
// Truncate is a stub, not yet implemented
|
||||
@@ -260,29 +249,3 @@ func Getwd() (string, error) {
|
||||
func TempDir() string {
|
||||
return tempDir()
|
||||
}
|
||||
|
||||
// UserHomeDir returns the current user's home directory.
|
||||
//
|
||||
// On Unix, including macOS, it returns the $HOME environment variable.
|
||||
// On Windows, it returns %USERPROFILE%.
|
||||
// On Plan 9, it returns the $home environment variable.
|
||||
func UserHomeDir() (string, error) {
|
||||
env, enverr := "HOME", "$HOME"
|
||||
switch runtime.GOOS {
|
||||
case "windows":
|
||||
env, enverr = "USERPROFILE", "%userprofile%"
|
||||
case "plan9":
|
||||
env, enverr = "home", "$home"
|
||||
}
|
||||
if v := Getenv(env); v != "" {
|
||||
return v, nil
|
||||
}
|
||||
// On some geese the home directory is not always defined.
|
||||
switch runtime.GOOS {
|
||||
case "android":
|
||||
return "/sdcard", nil
|
||||
case "ios":
|
||||
return "/", nil
|
||||
}
|
||||
return "", errors.New(enverr + " is not defined")
|
||||
}
|
||||
|
||||
@@ -26,6 +26,8 @@ var (
|
||||
Stderr = NewFile(uintptr(syscall.Stderr), "/dev/stderr")
|
||||
)
|
||||
|
||||
const DevNull = "/dev/null"
|
||||
|
||||
// isOS indicates whether we're running on a real operating system with
|
||||
// filesystem support.
|
||||
const isOS = true
|
||||
@@ -118,10 +120,6 @@ func (f unixFileHandle) Close() error {
|
||||
return handleSyscallError(syscall.Close(syscallFd(f)))
|
||||
}
|
||||
|
||||
func (f unixFileHandle) Fd() uintptr {
|
||||
return uintptr(f)
|
||||
}
|
||||
|
||||
// Chmod changes the mode of the named file to mode.
|
||||
// If the file is a symbolic link, it changes the mode of the link's target.
|
||||
// If there is an error, it will be of type *PathError.
|
||||
|
||||
@@ -4,9 +4,7 @@
|
||||
package os_test
|
||||
|
||||
import (
|
||||
"io"
|
||||
. "os"
|
||||
"runtime"
|
||||
"testing"
|
||||
)
|
||||
|
||||
@@ -70,47 +68,3 @@ func TestChdir(t *testing.T) {
|
||||
t.Errorf("Remove %s: %s", dir, err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestStandardFd(t *testing.T) {
|
||||
if runtime.GOOS == "windows" {
|
||||
t.Log("TODO: TestFd fails on Windows, skipping")
|
||||
return
|
||||
}
|
||||
if fd := Stdin.Fd(); fd != 0 {
|
||||
t.Errorf("Stdin.Fd() = %d, want 0", fd)
|
||||
}
|
||||
|
||||
if fd := Stdout.Fd(); fd != 1 {
|
||||
t.Errorf("Stdout.Fd() = %d, want 1", fd)
|
||||
}
|
||||
|
||||
if fd := Stderr.Fd(); fd != 2 {
|
||||
t.Errorf("Stderr.Fd() = %d, want 2", fd)
|
||||
}
|
||||
}
|
||||
|
||||
func TestFd(t *testing.T) {
|
||||
if runtime.GOOS == "windows" {
|
||||
t.Log("TODO: TestFd fails on Windows, skipping")
|
||||
return
|
||||
}
|
||||
f := newFile("TestFd.txt", t)
|
||||
defer Remove(f.Name())
|
||||
defer f.Close()
|
||||
|
||||
const data = "hello, world\n"
|
||||
io.WriteString(f, data)
|
||||
|
||||
fd := NewFile(f.Fd(), "as-fd")
|
||||
defer fd.Close()
|
||||
|
||||
b := make([]byte, 5)
|
||||
n, err := fd.ReadAt(b, 0)
|
||||
if n != 5 && err != nil {
|
||||
t.Errorf("Failed to read 5 bytes from file descriptor: %v", err)
|
||||
}
|
||||
|
||||
if string(b) != data[:5] {
|
||||
t.Errorf("File descriptor contents not equal to file contents.")
|
||||
}
|
||||
}
|
||||
|
||||
+2
-34
@@ -15,8 +15,6 @@ var (
|
||||
Stderr = NewFile(2, "/dev/stderr")
|
||||
)
|
||||
|
||||
const DevNull = "/dev/null"
|
||||
|
||||
// isOS indicates whether we're running on a real operating system with
|
||||
// filesystem support.
|
||||
const isOS = false
|
||||
@@ -38,26 +36,9 @@ func NewFile(fd uintptr, name string) *File {
|
||||
return &File{&file{stdioFileHandle(fd), name}}
|
||||
}
|
||||
|
||||
// Read reads up to len(b) bytes from machine.Serial.
|
||||
// It returns the number of bytes read and any error encountered.
|
||||
// Read is unsupported on this system.
|
||||
func (f stdioFileHandle) Read(b []byte) (n int, err error) {
|
||||
if len(b) == 0 {
|
||||
return 0, nil
|
||||
}
|
||||
|
||||
size := buffered()
|
||||
for size == 0 {
|
||||
gosched()
|
||||
size = buffered()
|
||||
}
|
||||
|
||||
if size > len(b) {
|
||||
size = len(b)
|
||||
}
|
||||
for i := 0; i < size; i++ {
|
||||
b[i] = getchar()
|
||||
}
|
||||
return size, nil
|
||||
return 0, ErrUnsupported
|
||||
}
|
||||
|
||||
func (f stdioFileHandle) ReadAt(b []byte, off int64) (n int, err error) {
|
||||
@@ -88,22 +69,9 @@ func (f stdioFileHandle) Seek(offset int64, whence int) (int64, error) {
|
||||
return -1, ErrUnsupported
|
||||
}
|
||||
|
||||
func (f stdioFileHandle) Fd() uintptr {
|
||||
return uintptr(f)
|
||||
}
|
||||
|
||||
//go:linkname putchar runtime.putchar
|
||||
func putchar(c byte)
|
||||
|
||||
//go:linkname getchar runtime.getchar
|
||||
func getchar() byte
|
||||
|
||||
//go:linkname buffered runtime.buffered
|
||||
func buffered() int
|
||||
|
||||
//go:linkname gosched runtime.Gosched
|
||||
func gosched() int
|
||||
|
||||
func Pipe() (r *File, w *File, err error) {
|
||||
return nil, nil, ErrNotImplemented
|
||||
}
|
||||
|
||||
@@ -1,9 +1,6 @@
|
||||
//go:build darwin || (linux && !baremetal)
|
||||
// +build darwin linux,!baremetal
|
||||
|
||||
// target wasi sets GOOS=linux and thus the +linux build tag,
|
||||
// even though it doesn't show up in "tinygo info target -wasi"
|
||||
|
||||
// Portions copyright 2009 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.
|
||||
@@ -15,8 +12,6 @@ import (
|
||||
"syscall"
|
||||
)
|
||||
|
||||
const DevNull = "/dev/null"
|
||||
|
||||
type syscallFd = int
|
||||
|
||||
// fixLongPath is a noop on non-Windows platforms.
|
||||
|
||||
@@ -13,8 +13,6 @@ import (
|
||||
"unicode/utf16"
|
||||
)
|
||||
|
||||
const DevNull = "NUL"
|
||||
|
||||
type syscallFd = syscall.Handle
|
||||
|
||||
// Symlink is a stub, it is not implemented.
|
||||
|
||||
@@ -253,21 +253,3 @@ func TestRenameFailed(t *testing.T) {
|
||||
t.Errorf("rename %q, %q: expected %T, got %T %v", from, to, new(LinkError), err, err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestUserHomeDir(t *testing.T) {
|
||||
dir, err := UserHomeDir()
|
||||
if dir == "" && err == nil {
|
||||
t.Fatal("UserHomeDir returned an empty string but no error")
|
||||
}
|
||||
if err != nil {
|
||||
t.Logf("UserHomeDir failed: %v", err)
|
||||
return
|
||||
}
|
||||
fi, err := Stat(dir)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if !fi.IsDir() {
|
||||
t.Fatalf("dir %s is not directory; type = %v", dir, fi.Mode())
|
||||
}
|
||||
}
|
||||
|
||||
+12
-17
@@ -18,7 +18,7 @@ import (
|
||||
// if set) and xxx contains the type kind number:
|
||||
// 0 (0001): Chan
|
||||
// 1 (0011): Interface
|
||||
// 2 (0101): Pointer
|
||||
// 2 (0101): Ptr
|
||||
// 3 (0111): Slice
|
||||
// 4 (1001): Array
|
||||
// 5 (1011): Func
|
||||
@@ -54,7 +54,7 @@ const (
|
||||
UnsafePointer
|
||||
Chan
|
||||
Interface
|
||||
Pointer
|
||||
Ptr
|
||||
Slice
|
||||
Array
|
||||
Func
|
||||
@@ -62,9 +62,6 @@ const (
|
||||
Struct
|
||||
)
|
||||
|
||||
// Ptr is the old name for the Pointer kind.
|
||||
const Ptr = Pointer
|
||||
|
||||
func (k Kind) String() string {
|
||||
switch k {
|
||||
case Bool:
|
||||
@@ -107,7 +104,7 @@ func (k Kind) String() string {
|
||||
return "chan"
|
||||
case Interface:
|
||||
return "interface"
|
||||
case Pointer:
|
||||
case Ptr:
|
||||
return "ptr"
|
||||
case Slice:
|
||||
return "slice"
|
||||
@@ -255,7 +252,7 @@ type Type interface {
|
||||
// Chan: ChanDir, Elem
|
||||
// Func: In, NumIn, Out, NumOut, IsVariadic.
|
||||
// Map: Key, Elem
|
||||
// Pointer: Elem
|
||||
// Ptr: Elem
|
||||
// Slice: Elem
|
||||
// Struct: Field, FieldByIndex, FieldByName, FieldByNameFunc, NumField
|
||||
|
||||
@@ -283,7 +280,7 @@ type Type interface {
|
||||
IsVariadic() bool
|
||||
|
||||
// Elem returns a type's element type.
|
||||
// It panics if the type's Kind is not Array, Chan, Map, Pointer, or Slice.
|
||||
// It panics if the type's Kind is not Array, Chan, Map, Ptr, or Slice.
|
||||
Elem() Type
|
||||
|
||||
// Field returns a struct type's i'th field.
|
||||
@@ -353,15 +350,13 @@ func TypeOf(i interface{}) Type {
|
||||
return ValueOf(i).typecode
|
||||
}
|
||||
|
||||
func PtrTo(t Type) Type { return PointerTo(t) }
|
||||
|
||||
func PointerTo(t Type) Type {
|
||||
if t.Kind() == Pointer {
|
||||
func PtrTo(t Type) Type {
|
||||
if t.Kind() == Ptr {
|
||||
panic("reflect: cannot make **T type")
|
||||
}
|
||||
ptrType := t.(rawType)<<5 | 5 // 0b0101 == 5
|
||||
if ptrType>>5 != t {
|
||||
panic("reflect: PointerTo type does not fit")
|
||||
panic("reflect: PtrTo type does not fit")
|
||||
}
|
||||
return ptrType
|
||||
}
|
||||
@@ -387,7 +382,7 @@ func (t rawType) Elem() Type {
|
||||
|
||||
func (t rawType) elem() rawType {
|
||||
switch t.Kind() {
|
||||
case Chan, Pointer, Slice:
|
||||
case Chan, Ptr, Slice:
|
||||
return t.stripPrefix()
|
||||
case Array:
|
||||
index := t.stripPrefix()
|
||||
@@ -571,7 +566,7 @@ func (t rawType) Size() uintptr {
|
||||
return 16
|
||||
case String:
|
||||
return unsafe.Sizeof("")
|
||||
case UnsafePointer, Chan, Map, Pointer:
|
||||
case UnsafePointer, Chan, Map, Ptr:
|
||||
return unsafe.Sizeof(uintptr(0))
|
||||
case Slice:
|
||||
return unsafe.Sizeof([]int{})
|
||||
@@ -620,7 +615,7 @@ func (t rawType) Align() int {
|
||||
return int(unsafe.Alignof(complex128(0)))
|
||||
case String:
|
||||
return int(unsafe.Alignof(""))
|
||||
case UnsafePointer, Chan, Map, Pointer:
|
||||
case UnsafePointer, Chan, Map, Ptr:
|
||||
return int(unsafe.Alignof(uintptr(0)))
|
||||
case Slice:
|
||||
return int(unsafe.Alignof([]int(nil)))
|
||||
@@ -686,7 +681,7 @@ func (t rawType) Comparable() bool {
|
||||
return true
|
||||
case Interface:
|
||||
return true
|
||||
case Pointer:
|
||||
case Ptr:
|
||||
return true
|
||||
case Slice:
|
||||
return false
|
||||
|
||||
@@ -861,11 +861,6 @@ func (v Value) FieldByIndex(index []int) Value {
|
||||
panic("unimplemented: (reflect.Value).FieldByIndex()")
|
||||
}
|
||||
|
||||
// FieldByIndexErr returns the nested field corresponding to index.
|
||||
func (v Value) FieldByIndexErr(index []int) (Value, error) {
|
||||
return Value{}, &ValueError{Method: "FieldByIndexErr"}
|
||||
}
|
||||
|
||||
func (v Value) FieldByName(name string) Value {
|
||||
panic("unimplemented: (reflect.Value).FieldByName()")
|
||||
}
|
||||
|
||||
@@ -1,56 +0,0 @@
|
||||
package runtime
|
||||
|
||||
// This file implements various core algorithms used in the runtime package and
|
||||
// standard library.
|
||||
|
||||
import "unsafe"
|
||||
|
||||
// This function is used by hash/maphash.
|
||||
func fastrand() uint32 {
|
||||
xorshift32State = xorshift32(xorshift32State)
|
||||
return xorshift32State
|
||||
}
|
||||
|
||||
var xorshift32State uint32 = 1
|
||||
|
||||
func xorshift32(x uint32) uint32 {
|
||||
// Algorithm "xor" from p. 4 of Marsaglia, "Xorshift RNGs".
|
||||
// Improved sequence based on
|
||||
// http://www.iro.umontreal.ca/~lecuyer/myftp/papers/xorshift.pdf
|
||||
x ^= x << 7
|
||||
x ^= x >> 1
|
||||
x ^= x << 9
|
||||
return x
|
||||
}
|
||||
|
||||
// This function is used by hash/maphash.
|
||||
func memhash(p unsafe.Pointer, seed, s uintptr) uintptr {
|
||||
if unsafe.Sizeof(uintptr(0)) > 4 {
|
||||
return seed ^ uintptr(hash64(p, s))
|
||||
}
|
||||
return seed ^ uintptr(hash32(p, s))
|
||||
}
|
||||
|
||||
// Get FNV-1a hash of the given memory buffer.
|
||||
//
|
||||
// https://en.wikipedia.org/wiki/Fowler%E2%80%93Noll%E2%80%93Vo_hash_function#FNV-1a_hash
|
||||
func hash32(ptr unsafe.Pointer, n uintptr) uint32 {
|
||||
var result uint32 = 2166136261 // FNV offset basis
|
||||
for i := uintptr(0); i < n; i++ {
|
||||
c := *(*uint8)(unsafe.Pointer(uintptr(ptr) + i))
|
||||
result ^= uint32(c) // XOR with byte
|
||||
result *= 16777619 // FNV prime
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
// Also a FNV-1a hash.
|
||||
func hash64(ptr unsafe.Pointer, n uintptr) uint64 {
|
||||
var result uint64 = 14695981039346656037 // FNV offset basis
|
||||
for i := uintptr(0); i < n; i++ {
|
||||
c := *(*uint8)(unsafe.Pointer(uintptr(ptr) + i))
|
||||
result ^= uint64(c) // XOR with byte
|
||||
result *= 1099511628211 // FNV prime
|
||||
}
|
||||
return result
|
||||
}
|
||||
@@ -1,20 +0,0 @@
|
||||
package runtime
|
||||
|
||||
// NumCPU returns the number of logical CPUs usable by the current process.
|
||||
//
|
||||
// The set of available CPUs is checked by querying the operating system
|
||||
// at process startup. Changes to operating system CPU allocation after
|
||||
// process startup are not reflected.
|
||||
func NumCPU() int {
|
||||
return 1
|
||||
}
|
||||
|
||||
// Stub for NumCgoCall, does not return the real value
|
||||
func NumCgoCall() int {
|
||||
return 0
|
||||
}
|
||||
|
||||
// Stub for NumGoroutine, does not return the real value
|
||||
func NumGoroutine() int {
|
||||
return 1
|
||||
}
|
||||
@@ -15,28 +15,3 @@ func SetMaxStack(n int) int {
|
||||
func Stack() []byte {
|
||||
return nil
|
||||
}
|
||||
|
||||
// ReadBuildInfo returns the build information embedded
|
||||
// in the running binary. The information is available only
|
||||
// in binaries built with module support.
|
||||
//
|
||||
// Not implemented.
|
||||
func ReadBuildInfo() (info *BuildInfo, ok bool) {
|
||||
return nil, false
|
||||
}
|
||||
|
||||
// BuildInfo represents the build information read from
|
||||
// the running binary.
|
||||
type BuildInfo struct {
|
||||
Path string // The main package path
|
||||
Main Module // The module containing the main package
|
||||
Deps []*Module // Module dependencies
|
||||
}
|
||||
|
||||
// Module represents a module.
|
||||
type Module struct {
|
||||
Path string // module path
|
||||
Version string // module version
|
||||
Sum string // checksum
|
||||
Replace *Module // replaced by this module
|
||||
}
|
||||
|
||||
@@ -3,15 +3,3 @@ package runtime
|
||||
func Callers(skip int, pc []uintptr) int {
|
||||
return 0
|
||||
}
|
||||
|
||||
// buildVersion is the Tinygo tree's version string at build time.
|
||||
//
|
||||
// This is set by the linker.
|
||||
var buildVersion string
|
||||
|
||||
// Version returns the Tinygo tree's version string.
|
||||
// It is the same as goenv.Version, or in case of a development build,
|
||||
// it will be the concatenation of goenv.Version and the git commit hash.
|
||||
func Version() string {
|
||||
return buildVersion
|
||||
}
|
||||
|
||||
@@ -32,9 +32,11 @@ func alloc(size uintptr, layout unsafe.Pointer) unsafe.Pointer {
|
||||
// Failed to make the heap bigger, so we must really be out of memory.
|
||||
runtimePanic("out of memory")
|
||||
}
|
||||
pointer := unsafe.Pointer(addr)
|
||||
memzero(pointer, size)
|
||||
return pointer
|
||||
for i := uintptr(0); i < uintptr(size); i += 4 {
|
||||
ptr := (*uint32)(unsafe.Pointer(addr + i))
|
||||
*ptr = 0
|
||||
}
|
||||
return unsafe.Pointer(addr)
|
||||
}
|
||||
|
||||
func realloc(ptr unsafe.Pointer, size uintptr) unsafe.Pointer {
|
||||
|
||||
+22
-9
@@ -37,6 +37,19 @@ type hashmapIterator struct {
|
||||
bucketIndex uint8
|
||||
}
|
||||
|
||||
// Get FNV-1a hash of this key.
|
||||
//
|
||||
// https://en.wikipedia.org/wiki/Fowler%E2%80%93Noll%E2%80%93Vo_hash_function#FNV-1a_hash
|
||||
func hashmapHash(ptr unsafe.Pointer, n uintptr) uint32 {
|
||||
var result uint32 = 2166136261 // FNV offset basis
|
||||
for i := uintptr(0); i < n; i++ {
|
||||
c := *(*uint8)(unsafe.Pointer(uintptr(ptr) + i))
|
||||
result ^= uint32(c) // XOR with byte
|
||||
result *= 16777619 // FNV prime
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
// Get the topmost 8 bits of the hash, without using a special value (like 0).
|
||||
func hashmapTopHash(hash uint32) uint8 {
|
||||
tophash := uint8(hash >> 24)
|
||||
@@ -295,7 +308,7 @@ func hashmapNext(m *hashmap, it *hashmapIterator, key, value unsafe.Pointer) boo
|
||||
|
||||
func hashmapBinarySet(m *hashmap, key, value unsafe.Pointer) {
|
||||
// TODO: detect nil map here and throw a better panic message?
|
||||
hash := hash32(key, uintptr(m.keySize))
|
||||
hash := hashmapHash(key, uintptr(m.keySize))
|
||||
hashmapSet(m, key, value, hash, memequal)
|
||||
}
|
||||
|
||||
@@ -304,7 +317,7 @@ func hashmapBinaryGet(m *hashmap, key, value unsafe.Pointer, valueSize uintptr)
|
||||
memzero(value, uintptr(valueSize))
|
||||
return false
|
||||
}
|
||||
hash := hash32(key, uintptr(m.keySize))
|
||||
hash := hashmapHash(key, uintptr(m.keySize))
|
||||
return hashmapGet(m, key, value, valueSize, hash, memequal)
|
||||
}
|
||||
|
||||
@@ -312,7 +325,7 @@ func hashmapBinaryDelete(m *hashmap, key unsafe.Pointer) {
|
||||
if m == nil {
|
||||
return
|
||||
}
|
||||
hash := hash32(key, uintptr(m.keySize))
|
||||
hash := hashmapHash(key, uintptr(m.keySize))
|
||||
hashmapDelete(m, key, hash, memequal)
|
||||
}
|
||||
|
||||
@@ -324,7 +337,7 @@ func hashmapStringEqual(x, y unsafe.Pointer, n uintptr) bool {
|
||||
|
||||
func hashmapStringHash(s string) uint32 {
|
||||
_s := (*_string)(unsafe.Pointer(&s))
|
||||
return hash32(unsafe.Pointer(_s.ptr), uintptr(_s.length))
|
||||
return hashmapHash(unsafe.Pointer(_s.ptr), uintptr(_s.length))
|
||||
}
|
||||
|
||||
func hashmapStringSet(m *hashmap, key string, value unsafe.Pointer) {
|
||||
@@ -357,7 +370,7 @@ func hashmapFloat32Hash(ptr unsafe.Pointer) uint32 {
|
||||
// convert -0 to 0 for hashing
|
||||
f = 0
|
||||
}
|
||||
return hash32(unsafe.Pointer(&f), 4)
|
||||
return hashmapHash(unsafe.Pointer(&f), 4)
|
||||
}
|
||||
|
||||
func hashmapFloat64Hash(ptr unsafe.Pointer) uint32 {
|
||||
@@ -366,7 +379,7 @@ func hashmapFloat64Hash(ptr unsafe.Pointer) uint32 {
|
||||
// convert -0 to 0 for hashing
|
||||
f = 0
|
||||
}
|
||||
return hash32(unsafe.Pointer(&f), 8)
|
||||
return hashmapHash(unsafe.Pointer(&f), 8)
|
||||
}
|
||||
|
||||
func hashmapInterfaceHash(itf interface{}) uint32 {
|
||||
@@ -384,9 +397,9 @@ func hashmapInterfaceHash(itf interface{}) uint32 {
|
||||
|
||||
switch x.RawType().Kind() {
|
||||
case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
|
||||
return hash32(ptr, x.RawType().Size())
|
||||
return hashmapHash(ptr, x.RawType().Size())
|
||||
case reflect.Bool, reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
|
||||
return hash32(ptr, x.RawType().Size())
|
||||
return hashmapHash(ptr, x.RawType().Size())
|
||||
case reflect.Float32:
|
||||
// It should be possible to just has the contents. However, NaN != NaN
|
||||
// so if you're using lots of NaNs as map keys (you shouldn't) then hash
|
||||
@@ -408,7 +421,7 @@ func hashmapInterfaceHash(itf interface{}) uint32 {
|
||||
// It might seem better to just return the pointer, but that won't
|
||||
// result in an evenly distributed hashmap. Instead, hash the pointer
|
||||
// like most other types.
|
||||
return hash32(ptr, x.RawType().Size())
|
||||
return hashmapHash(ptr, x.RawType().Size())
|
||||
case reflect.Array:
|
||||
var hash uint32
|
||||
for i := 0; i < x.Len(); i++ {
|
||||
|
||||
@@ -34,9 +34,9 @@ func (i Interrupt) Enable() error {
|
||||
// Set pulse interrupt type (rising edge detection)
|
||||
esp.INTERRUPT_CORE0.CPU_INT_TYPE.SetBits(1 << i.num)
|
||||
|
||||
// Set default threshold to defaultThreshold
|
||||
// Set default threshold to 5
|
||||
reg := (*volatile.Register32)(unsafe.Pointer((uintptr(unsafe.Pointer(&esp.INTERRUPT_CORE0.CPU_INT_PRI_0)) + uintptr(i.num)*4)))
|
||||
reg.Set(defaultThreshold)
|
||||
reg.Set(5)
|
||||
|
||||
// Reset interrupt before reenabling
|
||||
esp.INTERRUPT_CORE0.CPU_INT_CLEAR.SetBits(1 << i.num)
|
||||
@@ -47,118 +47,6 @@ func (i Interrupt) Enable() error {
|
||||
return nil
|
||||
}
|
||||
|
||||
// Adding pseudo function calls that is replaced by the compiler with the actual
|
||||
// functions registered through interrupt.New.
|
||||
//go:linkname callHandlers runtime/interrupt.callHandlers
|
||||
func callHandlers(num int)
|
||||
|
||||
const (
|
||||
IRQNUM_1 = 1 + iota
|
||||
IRQNUM_2
|
||||
IRQNUM_3
|
||||
IRQNUM_4
|
||||
IRQNUM_5
|
||||
IRQNUM_6
|
||||
IRQNUM_7
|
||||
IRQNUM_8
|
||||
IRQNUM_9
|
||||
IRQNUM_10
|
||||
IRQNUM_11
|
||||
IRQNUM_12
|
||||
IRQNUM_13
|
||||
IRQNUM_14
|
||||
IRQNUM_15
|
||||
IRQNUM_16
|
||||
IRQNUM_17
|
||||
IRQNUM_18
|
||||
IRQNUM_19
|
||||
IRQNUM_20
|
||||
IRQNUM_21
|
||||
IRQNUM_22
|
||||
IRQNUM_23
|
||||
IRQNUM_24
|
||||
IRQNUM_25
|
||||
IRQNUM_26
|
||||
IRQNUM_27
|
||||
IRQNUM_28
|
||||
IRQNUM_29
|
||||
IRQNUM_30
|
||||
IRQNUM_31
|
||||
)
|
||||
|
||||
const (
|
||||
defaultThreshold = 5
|
||||
disableThreshold = 10
|
||||
)
|
||||
|
||||
//go:inline
|
||||
func callHandler(n int) {
|
||||
switch n {
|
||||
case IRQNUM_1:
|
||||
callHandlers(IRQNUM_1)
|
||||
case IRQNUM_2:
|
||||
callHandlers(IRQNUM_2)
|
||||
case IRQNUM_3:
|
||||
callHandlers(IRQNUM_3)
|
||||
case IRQNUM_4:
|
||||
callHandlers(IRQNUM_4)
|
||||
case IRQNUM_5:
|
||||
callHandlers(IRQNUM_5)
|
||||
case IRQNUM_6:
|
||||
callHandlers(IRQNUM_6)
|
||||
case IRQNUM_7:
|
||||
callHandlers(IRQNUM_7)
|
||||
case IRQNUM_8:
|
||||
callHandlers(IRQNUM_8)
|
||||
case IRQNUM_9:
|
||||
callHandlers(IRQNUM_9)
|
||||
case IRQNUM_10:
|
||||
callHandlers(IRQNUM_10)
|
||||
case IRQNUM_11:
|
||||
callHandlers(IRQNUM_11)
|
||||
case IRQNUM_12:
|
||||
callHandlers(IRQNUM_12)
|
||||
case IRQNUM_13:
|
||||
callHandlers(IRQNUM_13)
|
||||
case IRQNUM_14:
|
||||
callHandlers(IRQNUM_14)
|
||||
case IRQNUM_15:
|
||||
callHandlers(IRQNUM_15)
|
||||
case IRQNUM_16:
|
||||
callHandlers(IRQNUM_16)
|
||||
case IRQNUM_17:
|
||||
callHandlers(IRQNUM_17)
|
||||
case IRQNUM_18:
|
||||
callHandlers(IRQNUM_18)
|
||||
case IRQNUM_19:
|
||||
callHandlers(IRQNUM_19)
|
||||
case IRQNUM_20:
|
||||
callHandlers(IRQNUM_20)
|
||||
case IRQNUM_21:
|
||||
callHandlers(IRQNUM_21)
|
||||
case IRQNUM_22:
|
||||
callHandlers(IRQNUM_22)
|
||||
case IRQNUM_23:
|
||||
callHandlers(IRQNUM_23)
|
||||
case IRQNUM_24:
|
||||
callHandlers(IRQNUM_24)
|
||||
case IRQNUM_25:
|
||||
callHandlers(IRQNUM_25)
|
||||
case IRQNUM_26:
|
||||
callHandlers(IRQNUM_26)
|
||||
case IRQNUM_27:
|
||||
callHandlers(IRQNUM_27)
|
||||
case IRQNUM_28:
|
||||
callHandlers(IRQNUM_28)
|
||||
case IRQNUM_29:
|
||||
callHandlers(IRQNUM_29)
|
||||
case IRQNUM_30:
|
||||
callHandlers(IRQNUM_30)
|
||||
case IRQNUM_31:
|
||||
callHandlers(IRQNUM_31)
|
||||
}
|
||||
}
|
||||
|
||||
//export handleInterrupt
|
||||
func handleInterrupt() {
|
||||
mcause := riscv.MCAUSE.Get()
|
||||
@@ -166,17 +54,12 @@ func handleInterrupt() {
|
||||
interruptNumber := uint32(mcause & 0x1f)
|
||||
|
||||
if !exception && interruptNumber > 0 {
|
||||
// save MSTATUS & MEPC, which could be overwritten by another CPU interrupt
|
||||
mstatus := riscv.MSTATUS.Get()
|
||||
// save mepc, which could be overwritten by another CPU interrupt
|
||||
mepc := riscv.MEPC.Get()
|
||||
// Useing threshold to temporary disable this interrupts.
|
||||
// FYI: using CPU interrupt enable bit make runtime to loose interrupts.
|
||||
reg := (*volatile.Register32)(unsafe.Pointer((uintptr(unsafe.Pointer(&esp.INTERRUPT_CORE0.CPU_INT_PRI_0)) + uintptr(interruptNumber)*4)))
|
||||
thresholdSave := reg.Get()
|
||||
reg.Set(disableThreshold)
|
||||
riscv.Asm("fence")
|
||||
|
||||
// disable interrupt
|
||||
interruptBit := uint32(1 << interruptNumber)
|
||||
esp.INTERRUPT_CORE0.CPU_INT_ENABLE.ClearBits(interruptBit)
|
||||
|
||||
// reset pending status interrupt
|
||||
if esp.INTERRUPT_CORE0.CPU_INT_TYPE.Get()&interruptBit != 0 {
|
||||
@@ -189,22 +72,23 @@ func handleInterrupt() {
|
||||
}
|
||||
|
||||
// enable CPU interrupts
|
||||
riscv.MSTATUS.SetBits(1 << 3)
|
||||
riscv.MSTATUS.SetBits(0x8)
|
||||
|
||||
// Call registered interrupt handler(s)
|
||||
callHandler(int(interruptNumber))
|
||||
esp.HandleInterrupt(int(interruptNumber))
|
||||
|
||||
// disable CPU interrupts
|
||||
riscv.MSTATUS.ClearBits(1 << 3)
|
||||
riscv.MSTATUS.ClearBits(0x8)
|
||||
|
||||
// restore interrupt threshold to enable interrupt again
|
||||
reg.Set(thresholdSave)
|
||||
riscv.Asm("fence")
|
||||
// mpie must be set to 1 to resume interrupts after 'MRET'
|
||||
riscv.MSTATUS.SetBits(0x80)
|
||||
|
||||
// restore MSTATUS & MEPC
|
||||
riscv.MSTATUS.Set(mstatus)
|
||||
// restore MEPC
|
||||
riscv.MEPC.Set(mepc)
|
||||
|
||||
// enable this interrupt
|
||||
esp.INTERRUPT_CORE0.CPU_INT_ENABLE.SetBits(interruptBit)
|
||||
|
||||
// do not enable CPU interrupts now
|
||||
// the 'MRET' in src/device/riscv/handleinterrupt.S will copies the state of MPIE back into MIE, and subsequently clears MPIE.
|
||||
// riscv.MSTATUS.SetBits(0x8)
|
||||
@@ -220,16 +104,6 @@ func handleException(mcause uintptr) {
|
||||
println("*** Exception: pc:", riscv.MEPC.Get())
|
||||
println("*** Exception: code:", uint32(mcause&0x1f))
|
||||
println("*** Exception: mcause:", mcause)
|
||||
switch uint32(mcause & 0x1f) {
|
||||
case 1:
|
||||
println("*** virtual addess:", riscv.MTVAL.Get())
|
||||
case 2:
|
||||
println("*** opcode:", riscv.MTVAL.Get())
|
||||
case 5:
|
||||
println("*** read address:", riscv.MTVAL.Get())
|
||||
case 7:
|
||||
println("*** write address:", riscv.MTVAL.Get())
|
||||
}
|
||||
for {
|
||||
riscv.Asm("wfi")
|
||||
}
|
||||
|
||||
@@ -14,16 +14,6 @@ func putchar(c byte) {
|
||||
// dummy, TODO
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
// dummy, TODO
|
||||
return 0
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
// dummy, TODO
|
||||
return 0
|
||||
}
|
||||
|
||||
//go:extern _sbss
|
||||
var _sbss [0]byte
|
||||
|
||||
|
||||
@@ -16,18 +16,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
// Sleep for a given period. The period is defined by the WDT peripheral, and is
|
||||
// on most chips (at least) 3 bits wide, in powers of two from 16ms to 2s
|
||||
// (0=16ms, 1=32ms, 2=64ms...). Note that the WDT is not very accurate: it can
|
||||
|
||||
@@ -30,27 +30,12 @@ func init() {
|
||||
|
||||
// connect to USB CDC interface
|
||||
machine.Serial.Configure(machine.UARTConfig{})
|
||||
if !machine.USB.Configured() {
|
||||
machine.USB.Configure(machine.UARTConfig{})
|
||||
}
|
||||
}
|
||||
|
||||
func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
func initClocks() {
|
||||
// Set 1 Flash Wait State for 48MHz, required for 3.3V operation according to SAMD21 Datasheet
|
||||
sam.NVMCTRL.CTRLB.SetBits(sam.NVMCTRL_CTRLB_RWS_HALF << sam.NVMCTRL_CTRLB_RWS_Pos)
|
||||
|
||||
@@ -30,27 +30,12 @@ func init() {
|
||||
|
||||
// connect to USB CDC interface
|
||||
machine.Serial.Configure(machine.UARTConfig{})
|
||||
if !machine.USB.Configured() {
|
||||
machine.USB.Configure(machine.UARTConfig{})
|
||||
}
|
||||
}
|
||||
|
||||
func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
func initClocks() {
|
||||
// set flash wait state
|
||||
sam.NVMCTRL.CTRLA.SetBits(0 << sam.NVMCTRL_CTRLA_RWS_Pos)
|
||||
|
||||
@@ -14,16 +14,6 @@ func putchar(c byte) {
|
||||
// UART is not supported.
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
// UART is not supported.
|
||||
return 0
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
// UART is not supported.
|
||||
return 0
|
||||
}
|
||||
|
||||
func sleepWDT(period uint8) {
|
||||
// TODO: use the watchdog timer instead of a busy loop.
|
||||
for i := 0x45; i != 0; i-- {
|
||||
|
||||
@@ -49,16 +49,6 @@ func putchar(c byte) {
|
||||
stdoutWrite.Set(uint8(c))
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
// dummy, TODO
|
||||
return 0
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
// dummy, TODO
|
||||
return 0
|
||||
}
|
||||
|
||||
func waitForEvents() {
|
||||
arm.Asm("wfe")
|
||||
}
|
||||
|
||||
@@ -15,18 +15,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
// Initialize .bss: zero-initialized global variables.
|
||||
// The .data section has already been loaded by the ROM bootloader.
|
||||
func clearbss() {
|
||||
|
||||
@@ -18,18 +18,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
// Write to the internal control bus (using I2C?).
|
||||
// Signature found here:
|
||||
// https://github.com/espressif/ESP8266_RTOS_SDK/blob/14171de0/components/esp8266/include/esp8266/rom_functions.h#L54
|
||||
|
||||
@@ -99,18 +99,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
var timerWakeup volatile.Register8
|
||||
|
||||
func ticks() timeUnit {
|
||||
|
||||
@@ -111,18 +111,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
var timerWakeup volatile.Register8
|
||||
|
||||
func ticks() timeUnit {
|
||||
|
||||
@@ -126,18 +126,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.UART1.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.UART1.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.UART1.Buffered()
|
||||
}
|
||||
|
||||
func exit(code int) {
|
||||
abort()
|
||||
}
|
||||
|
||||
@@ -66,18 +66,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
func sleepTicks(d timeUnit) {
|
||||
for d != 0 {
|
||||
ticks := uint32(d) & 0x7fffff // 23 bits (to be on the safe side)
|
||||
|
||||
@@ -231,16 +231,6 @@ func putchar(c byte) {
|
||||
machine.PutcharUART(machine.UART0, c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
// dummy, TODO
|
||||
return 0
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
// dummy, TODO
|
||||
return 0
|
||||
}
|
||||
|
||||
func exit(code int) {
|
||||
abort()
|
||||
}
|
||||
|
||||
@@ -45,18 +45,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
// machineInit is provided by package machine.
|
||||
func machineInit()
|
||||
|
||||
|
||||
@@ -20,18 +20,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
// initCLK sets clock to 72MHz using HSE 8MHz crystal w/ PLL X 9 (8MHz x 9 = 72MHz).
|
||||
func initCLK() {
|
||||
stm32.FLASH.ACR.SetBits(stm32.FLASH_ACR_LATENCY_WS2) // Two wait states, per datasheet
|
||||
|
||||
@@ -21,18 +21,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
func initCLK() {
|
||||
// Reset clock registers
|
||||
// Set HSION
|
||||
|
||||
@@ -163,15 +163,3 @@ func initCOM() {
|
||||
func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
@@ -38,18 +38,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
func initCLK() {
|
||||
// PWR_CLK_ENABLE
|
||||
stm32.RCC.APB1ENR.SetBits(stm32.RCC_APB1ENR_PWREN)
|
||||
|
||||
@@ -16,18 +16,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
func initCLK() {
|
||||
// Set Power Regulator to enable max performance (1.8V)
|
||||
stm32.PWR.CR.ReplaceBits(1<<stm32.PWR_CR_VOS_Pos, stm32.PWR_CR_VOS_Msk, 0)
|
||||
|
||||
@@ -47,18 +47,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
func initCLK() {
|
||||
// PWR_CLK_ENABLE
|
||||
stm32.RCC.APB1ENR1.SetBits(stm32.RCC_APB1ENR1_PWREN)
|
||||
|
||||
@@ -39,18 +39,6 @@ func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
func initCLK() {
|
||||
|
||||
// PWR_CLK_ENABLE
|
||||
|
||||
@@ -102,15 +102,3 @@ func initCLK() {
|
||||
func putchar(c byte) {
|
||||
machine.Serial.WriteByte(c)
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
for machine.Serial.Buffered() == 0 {
|
||||
Gosched()
|
||||
}
|
||||
v, _ := machine.Serial.ReadByte()
|
||||
return v
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
return machine.Serial.Buffered()
|
||||
}
|
||||
|
||||
@@ -55,16 +55,6 @@ func putchar(c byte) {
|
||||
stdoutWrite.Set(uint8(c))
|
||||
}
|
||||
|
||||
func getchar() byte {
|
||||
// dummy, TODO
|
||||
return 0
|
||||
}
|
||||
|
||||
func buffered() int {
|
||||
// dummy, TODO
|
||||
return 0
|
||||
}
|
||||
|
||||
func abort() {
|
||||
exit(1)
|
||||
}
|
||||
|
||||
@@ -1,23 +0,0 @@
|
||||
// Copyright 2014 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.
|
||||
|
||||
//go:build darwin || linux
|
||||
// +build darwin linux
|
||||
|
||||
package syscall_test
|
||||
|
||||
import (
|
||||
"syscall"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestMmap(t *testing.T) {
|
||||
b, err := syscall.Mmap(-1, 0, syscall.Getpagesize(), syscall.PROT_NONE, syscall.MAP_ANON|syscall.MAP_PRIVATE)
|
||||
if err != nil {
|
||||
t.Fatalf("Mmap: %v", err)
|
||||
}
|
||||
if err := syscall.Munmap(b); err != nil {
|
||||
t.Fatalf("Munmap: %v", err)
|
||||
}
|
||||
}
|
||||
@@ -226,14 +226,6 @@ func Mmap(fd int, offset int64, length int, prot int, flags int) (data []byte, e
|
||||
return (*[1 << 30]byte)(addr)[:length:length], nil
|
||||
}
|
||||
|
||||
func Munmap(b []byte) (err error) {
|
||||
errCode := libc_munmap(unsafe.Pointer(&b[0]), uintptr(len(b)))
|
||||
if errCode != 0 {
|
||||
err = getErrno()
|
||||
}
|
||||
return err
|
||||
}
|
||||
|
||||
func Mprotect(b []byte, prot int) (err error) {
|
||||
errCode := libc_mprotect(unsafe.Pointer(&b[0]), uintptr(len(b)), int32(prot))
|
||||
if errCode != 0 {
|
||||
@@ -242,19 +234,7 @@ func Mprotect(b []byte, prot int) (err error) {
|
||||
return
|
||||
}
|
||||
|
||||
func Getpagesize() int {
|
||||
return int(libc_getpagesize())
|
||||
}
|
||||
|
||||
func Environ() []string {
|
||||
|
||||
// This function combines all the environment into a single allocation.
|
||||
// While this optimizes for memory usage and garbage collector
|
||||
// overhead, it does run the risk of potentially pinning a "large"
|
||||
// allocation if a user holds onto a single environment variable or
|
||||
// value. Having each variable be its own allocation would make the
|
||||
// trade-off in the other direction.
|
||||
|
||||
// calculate total memory required
|
||||
var length uintptr
|
||||
var vars int
|
||||
@@ -355,18 +335,10 @@ func libc_dup(fd int32) int32
|
||||
//export mmap
|
||||
func libc_mmap(addr unsafe.Pointer, length uintptr, prot, flags, fd int32, offset uintptr) unsafe.Pointer
|
||||
|
||||
// int munmap(void *addr, size_t length);
|
||||
//export munmap
|
||||
func libc_munmap(addr unsafe.Pointer, length uintptr) int32
|
||||
|
||||
// int mprotect(void *addr, size_t len, int prot);
|
||||
//export mprotect
|
||||
func libc_mprotect(addr unsafe.Pointer, len uintptr, prot int32) int32
|
||||
|
||||
// int getpagesize();
|
||||
//export getpagesize
|
||||
func libc_getpagesize() int32
|
||||
|
||||
// int chdir(const char *pathname, mode_t mode);
|
||||
//export chdir
|
||||
func libc_chdir(pathname *byte) int32
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
package syscall
|
||||
|
||||
import (
|
||||
"internal/itoa"
|
||||
"unsafe"
|
||||
)
|
||||
|
||||
@@ -83,20 +82,6 @@ const (
|
||||
SIGTERM Signal = 0xf
|
||||
)
|
||||
|
||||
func (s Signal) Signal() {}
|
||||
|
||||
func (s Signal) String() string {
|
||||
if 0 <= s && int(s) < len(signals) {
|
||||
str := signals[s]
|
||||
if str != "" {
|
||||
return str
|
||||
}
|
||||
}
|
||||
return "signal " + itoa.Itoa(int(s))
|
||||
}
|
||||
|
||||
var signals = [...]string{}
|
||||
|
||||
const (
|
||||
Stdin = 0
|
||||
Stdout = 1
|
||||
|
||||
@@ -3,10 +3,6 @@
|
||||
|
||||
package syscall
|
||||
|
||||
import (
|
||||
"internal/itoa"
|
||||
)
|
||||
|
||||
// A Signal is a number describing a process signal.
|
||||
// It implements the os.Signal interface.
|
||||
type Signal int
|
||||
@@ -21,20 +17,6 @@ const (
|
||||
SIGTERM
|
||||
)
|
||||
|
||||
func (s Signal) Signal() {}
|
||||
|
||||
func (s Signal) String() string {
|
||||
if 0 <= s && int(s) < len(signals) {
|
||||
str := signals[s]
|
||||
if str != "" {
|
||||
return str
|
||||
}
|
||||
}
|
||||
return "signal " + itoa.Itoa(int(s))
|
||||
}
|
||||
|
||||
var signals = [...]string{}
|
||||
|
||||
// File system
|
||||
|
||||
const (
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
package syscall
|
||||
|
||||
import (
|
||||
"internal/itoa"
|
||||
"unsafe"
|
||||
)
|
||||
|
||||
@@ -13,28 +12,14 @@ import (
|
||||
type Signal int
|
||||
|
||||
const (
|
||||
SIGCHLD Signal = 16
|
||||
SIGINT Signal = 2
|
||||
SIGKILL Signal = 9
|
||||
SIGTRAP Signal = 5
|
||||
SIGQUIT Signal = 3
|
||||
SIGTERM Signal = 15
|
||||
SIGCHLD = 16
|
||||
SIGINT = 2
|
||||
SIGKILL = 9
|
||||
SIGTRAP = 5
|
||||
SIGQUIT = 3
|
||||
SIGTERM = 15
|
||||
)
|
||||
|
||||
func (s Signal) Signal() {}
|
||||
|
||||
func (s Signal) String() string {
|
||||
if 0 <= s && int(s) < len(signals) {
|
||||
str := signals[s]
|
||||
if str != "" {
|
||||
return str
|
||||
}
|
||||
}
|
||||
return "signal " + itoa.Itoa(int(s))
|
||||
}
|
||||
|
||||
var signals = [...]string{}
|
||||
|
||||
const (
|
||||
Stdin = 0
|
||||
Stdout = 1
|
||||
@@ -59,19 +44,6 @@ const (
|
||||
O_SYNC = __WASI_FDFLAGS_SYNC
|
||||
|
||||
O_CLOEXEC = 0
|
||||
|
||||
// ../../lib/wasi-libc/sysroot/include/sys/mman.h
|
||||
MAP_FILE = 0
|
||||
MAP_SHARED = 0x01
|
||||
MAP_PRIVATE = 0x02
|
||||
MAP_ANON = 0x20
|
||||
MAP_ANONYMOUS = MAP_ANON
|
||||
|
||||
// ../../lib/wasi-libc/sysroot/include/sys/mman.h
|
||||
PROT_NONE = 0
|
||||
PROT_READ = 1
|
||||
PROT_WRITE = 2
|
||||
PROT_EXEC = 4
|
||||
)
|
||||
|
||||
//go:extern errno
|
||||
|
||||
@@ -3,10 +3,6 @@
|
||||
|
||||
package syscall
|
||||
|
||||
import (
|
||||
"internal/itoa"
|
||||
)
|
||||
|
||||
// Most code here has been copied from the Go sources:
|
||||
// https://github.com/golang/go/blob/go1.12/src/syscall/syscall_js.go
|
||||
// It has the following copyright note:
|
||||
@@ -27,28 +23,8 @@ const (
|
||||
SIGTRAP
|
||||
SIGQUIT
|
||||
SIGTERM
|
||||
SIGILL
|
||||
SIGABRT
|
||||
SIGBUS
|
||||
SIGFPE
|
||||
SIGSEGV
|
||||
SIGPIPE
|
||||
)
|
||||
|
||||
func (s Signal) Signal() {}
|
||||
|
||||
func (s Signal) String() string {
|
||||
if 0 <= s && int(s) < len(signals) {
|
||||
str := signals[s]
|
||||
if str != "" {
|
||||
return str
|
||||
}
|
||||
}
|
||||
return "signal " + itoa.Itoa(int(s))
|
||||
}
|
||||
|
||||
var signals = [...]string{}
|
||||
|
||||
// File system
|
||||
|
||||
const (
|
||||
@@ -72,22 +48,6 @@ const (
|
||||
O_CLOEXEC = 0
|
||||
)
|
||||
|
||||
// Dummy values to allow compiling tests
|
||||
// Dummy source: https://opensource.apple.com/source/xnu/xnu-7195.81.3/bsd/sys/mman.h.auto.html
|
||||
const (
|
||||
PROT_NONE = 0x00 // no permissions
|
||||
PROT_READ = 0x01 // pages can be read
|
||||
PROT_WRITE = 0x02 // pages can be written
|
||||
PROT_EXEC = 0x04 // pages can be executed
|
||||
|
||||
MAP_SHARED = 0x0001 // share changes
|
||||
MAP_PRIVATE = 0x0002 // changes are private
|
||||
|
||||
MAP_FILE = 0x0000 // map from file (default)
|
||||
MAP_ANON = 0x1000 // allocated from memory, swap space
|
||||
MAP_ANONYMOUS = MAP_ANON
|
||||
)
|
||||
|
||||
func runtime_envs() []string
|
||||
|
||||
func Getenv(key string) (value string, found bool) {
|
||||
@@ -190,14 +150,6 @@ func Wait4(pid int, wstatus *WaitStatus, options int, rusage *Rusage) (wpid int,
|
||||
return 0, ENOSYS
|
||||
}
|
||||
|
||||
func Mmap(fd int, offset int64, length int, prot int, flags int) (data []byte, err error) {
|
||||
return nil, ENOSYS
|
||||
}
|
||||
|
||||
func Munmap(b []byte) (err error) {
|
||||
return ENOSYS
|
||||
}
|
||||
|
||||
type Timeval struct {
|
||||
Sec int64
|
||||
Usec int64
|
||||
|
||||
@@ -1,10 +0,0 @@
|
||||
// Copyright 2016 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.
|
||||
//
|
||||
//go:build baremetal
|
||||
// +build baremetal
|
||||
|
||||
package testing
|
||||
|
||||
const isBaremetal = true
|
||||
@@ -1,10 +0,0 @@
|
||||
// Copyright 2016 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.
|
||||
//
|
||||
//go:build !baremetal
|
||||
// +build !baremetal
|
||||
|
||||
package testing
|
||||
|
||||
const isBaremetal = false
|
||||
@@ -26,11 +26,6 @@ type matcher struct {
|
||||
var matchMutex sync.Mutex
|
||||
|
||||
func newMatcher(matchString func(pat, str string) (bool, error), patterns, name string) *matcher {
|
||||
if isBaremetal {
|
||||
// Probably not enough ram to load regexp, substitute something simpler.
|
||||
matchString = fakeMatchString
|
||||
}
|
||||
|
||||
var filter []string
|
||||
if patterns != "" {
|
||||
filter = splitRegexp(patterns)
|
||||
@@ -171,14 +166,3 @@ func isSpace(r rune) bool {
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
// A fake regexp matcher.
|
||||
// Inflexible, but saves 50KB of flash and 50KB of RAM per -size full,
|
||||
// and lets tests pass on cortex-m.
|
||||
func fakeMatchString(pat, str string) (bool, error) {
|
||||
if pat == ".*" {
|
||||
return true, nil
|
||||
}
|
||||
matched := strings.Contains(str, pat)
|
||||
return matched, nil
|
||||
}
|
||||
|
||||
+1
-32
@@ -205,10 +205,6 @@ func (fi *frameInfo) exec(bytecode []byte) ([]frameInfoLine, error) {
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
case 3: // DW_CFA_restore
|
||||
// Restore a register. Used after an outlined function call.
|
||||
// It should be possible to ignore this.
|
||||
// TODO: check that this is not the stack pointer.
|
||||
case 0:
|
||||
switch lowBits {
|
||||
case 0: // DW_CFA_nop
|
||||
@@ -222,22 +218,7 @@ func (fi *frameInfo) exec(bytecode []byte) ([]frameInfoLine, error) {
|
||||
}
|
||||
fi.loc += uint64(offset) * fi.cie.codeAlignmentFactor
|
||||
entries = append(entries, fi.newLine())
|
||||
case 0x03: // DW_CFA_advance_loc2
|
||||
var offset uint16
|
||||
err := binary.Read(r, binary.LittleEndian, &offset)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
fi.loc += uint64(offset) * fi.cie.codeAlignmentFactor
|
||||
entries = append(entries, fi.newLine())
|
||||
case 0x04: // DW_CFA_advance_loc4
|
||||
var offset uint32
|
||||
err := binary.Read(r, binary.LittleEndian, &offset)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
fi.loc += uint64(offset) * fi.cie.codeAlignmentFactor
|
||||
entries = append(entries, fi.newLine())
|
||||
// TODO: DW_CFA_advance_loc2 etc
|
||||
case 0x05: // DW_CFA_offset_extended
|
||||
// Semantics are the same as DW_CFA_offset, but the encoding is
|
||||
// different. Ignore it just like DW_CFA_offset.
|
||||
@@ -258,18 +239,6 @@ func (fi *frameInfo) exec(bytecode []byte) ([]frameInfoLine, error) {
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
case 0x09: // DW_CFA_register
|
||||
// Copies a register. Emitted by the machine outliner, for example.
|
||||
// It should be possible to ignore this.
|
||||
// TODO: check that the stack pointer is not affected.
|
||||
_, err := readULEB128(r)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
_, err = readULEB128(r)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
case 0x0c: // DW_CFA_def_cfa
|
||||
register, err := readULEB128(r)
|
||||
if err != nil {
|
||||
|
||||
@@ -1,5 +0,0 @@
|
||||
{
|
||||
"inherits": ["esp32c3"],
|
||||
"build-tags": ["esp32c312f", "esp32c3", "esp"]
|
||||
}
|
||||
|
||||
@@ -11,6 +11,7 @@
|
||||
"ldflags": [
|
||||
"--allow-undefined",
|
||||
"--stack-first",
|
||||
"--export-dynamic",
|
||||
"--no-demangle"
|
||||
],
|
||||
"emulator": ["wasmtime"],
|
||||
|
||||
@@ -424,7 +424,7 @@
|
||||
|
||||
const dst = loadSlice(dest_addr, dest_len);
|
||||
const src = loadValue(source_addr);
|
||||
if (!(src instanceof Uint8Array || src instanceof Uint8ClampedArray)) {
|
||||
if (!(src instanceof Uint8Array)) {
|
||||
mem().setUint8(returned_status_addr, 0); // Return "not ok" status
|
||||
return;
|
||||
}
|
||||
@@ -443,7 +443,7 @@
|
||||
|
||||
const dst = loadValue(dest_addr);
|
||||
const src = loadSlice(source_addr, source_len);
|
||||
if (!(dst instanceof Uint8Array || dst instanceof Uint8ClampedArray)) {
|
||||
if (!(dst instanceof Uint8Array)) {
|
||||
mem().setUint8(returned_status_addr, 0); // Return "not ok" status
|
||||
return;
|
||||
}
|
||||
|
||||
Vendored
-13
@@ -170,19 +170,6 @@ func main() {
|
||||
assertSize(reflect.TypeOf(new(int)).Size() == unsafe.Sizeof(new(int)), "*int")
|
||||
assertSize(reflect.TypeOf(zeroFunc).Size() == unsafe.Sizeof(zeroFunc), "func()")
|
||||
|
||||
// Test that offset is correctly calculated.
|
||||
// This doesn't just test reflect but also (indirectly) that unsafe.Alignof
|
||||
// works correctly.
|
||||
s := struct {
|
||||
small1 byte
|
||||
big1 int64
|
||||
small2 byte
|
||||
big2 int64
|
||||
}{}
|
||||
st := reflect.TypeOf(s)
|
||||
println("offset for int64 matches:", st.Field(1).Offset-st.Field(0).Offset == uintptr(unsafe.Pointer(&s.big1))-uintptr(unsafe.Pointer(&s.small1)))
|
||||
println("offset for complex128 matches:", st.Field(3).Offset-st.Field(2).Offset == uintptr(unsafe.Pointer(&s.big2))-uintptr(unsafe.Pointer(&s.small2)))
|
||||
|
||||
// SetBool
|
||||
rv := reflect.ValueOf(new(bool)).Elem()
|
||||
rv.SetBool(true)
|
||||
|
||||
Vendored
-2
@@ -401,8 +401,6 @@ float32 4 32
|
||||
float64 8 64
|
||||
complex64 8 64
|
||||
complex128 16 128
|
||||
offset for int64 matches: true
|
||||
offset for complex128 matches: true
|
||||
type assertion succeeded for unreferenced type
|
||||
|
||||
struct tags
|
||||
|
||||
Vendored
+9
-9
@@ -6,7 +6,6 @@ import (
|
||||
"errors"
|
||||
"flag"
|
||||
"io"
|
||||
"strings"
|
||||
"testing"
|
||||
)
|
||||
|
||||
@@ -33,7 +32,7 @@ func TestAllLowercase(t *testing.T) {
|
||||
"alpha",
|
||||
"BETA",
|
||||
"gamma",
|
||||
"BELTA",
|
||||
"DELTA",
|
||||
}
|
||||
|
||||
for _, name := range names {
|
||||
@@ -57,22 +56,23 @@ var benchmarks = []testing.InternalBenchmark{}
|
||||
|
||||
var examples = []testing.InternalExample{}
|
||||
|
||||
// A fake regexp matcher.
|
||||
// A fake regexp matcher that can only handle two patterns.
|
||||
// Inflexible, but saves 50KB of flash and 50KB of RAM per -size full,
|
||||
// and lets tests pass on cortex-m.
|
||||
// Must match the one in src/testing/match.go that is substituted on bare-metal platforms,
|
||||
// or "make test" will fail there.
|
||||
// and lets tests pass on cortex-m3.
|
||||
func fakeMatchString(pat, str string) (bool, error) {
|
||||
if pat == ".*" {
|
||||
return true, nil
|
||||
}
|
||||
matched := strings.Contains(str, pat)
|
||||
return matched, nil
|
||||
if pat == "[BD]" {
|
||||
return (str[0] == 'B' || str[0] == 'D'), nil
|
||||
}
|
||||
println("BUG: fakeMatchString does not grok", pat)
|
||||
return false, nil
|
||||
}
|
||||
|
||||
func main() {
|
||||
testing.Init()
|
||||
flag.Set("test.run", ".*/B")
|
||||
flag.Set("test.run", ".*/[BD]")
|
||||
m := testing.MainStart(matchStringOnly(fakeMatchString /*regexp.MatchString*/), tests, benchmarks, examples)
|
||||
|
||||
exitcode := m.Run()
|
||||
|
||||
Vendored
+2
-2
@@ -15,7 +15,7 @@
|
||||
--- FAIL: TestAllLowercase (0.00s)
|
||||
--- FAIL: TestAllLowercase/BETA (0.00s)
|
||||
expected lowercase name, got BETA
|
||||
--- FAIL: TestAllLowercase/BELTA (0.00s)
|
||||
expected lowercase name, got BELTA
|
||||
--- FAIL: TestAllLowercase/DELTA (0.00s)
|
||||
expected lowercase name, got DELTA
|
||||
FAIL
|
||||
exitcode: 1
|
||||
|
||||
@@ -151,7 +151,6 @@ func Optimize(mod llvm.Module, config *compileopts.Config, optLevel, sizeLevel i
|
||||
funcPasses.FinalizeFunc()
|
||||
|
||||
// Run module passes.
|
||||
// TODO: somehow set the PrepareForThinLTO flag in the pass manager builder.
|
||||
modPasses := llvm.NewPassManager()
|
||||
defer modPasses.Dispose()
|
||||
builder.Populate(modPasses)
|
||||
|
||||
+1
-25
@@ -11,9 +11,8 @@ import (
|
||||
// modified after linking.
|
||||
func CreateStackSizeLoads(mod llvm.Module, config *compileopts.Config) []string {
|
||||
functionMap := map[llvm.Value][]llvm.Value{}
|
||||
var functions []llvm.Value // ptrtoint values of functions
|
||||
var functions []llvm.Value
|
||||
var functionNames []string
|
||||
var functionValues []llvm.Value // direct references to functions
|
||||
for _, use := range getUses(mod.NamedFunction("internal/task.getGoroutineStackSize")) {
|
||||
if use.FirstUse().IsNil() {
|
||||
// Apparently this stack size isn't used.
|
||||
@@ -24,7 +23,6 @@ func CreateStackSizeLoads(mod llvm.Module, config *compileopts.Config) []string
|
||||
if _, ok := functionMap[ptrtoint]; !ok {
|
||||
functions = append(functions, ptrtoint)
|
||||
functionNames = append(functionNames, ptrtoint.Operand(0).Name())
|
||||
functionValues = append(functionValues, ptrtoint.Operand(0))
|
||||
}
|
||||
functionMap[ptrtoint] = append(functionMap[ptrtoint], use)
|
||||
}
|
||||
@@ -46,9 +44,6 @@ func CreateStackSizeLoads(mod llvm.Module, config *compileopts.Config) []string
|
||||
}
|
||||
stackSizesGlobal.SetInitializer(llvm.ConstArray(functions[0].Type(), defaultStackSizes))
|
||||
|
||||
// Add all relevant values to llvm.used (for LTO).
|
||||
appendToUsedGlobals(mod, append([]llvm.Value{stackSizesGlobal}, functionValues...)...)
|
||||
|
||||
// Replace the calls with loads from the new global with stack sizes.
|
||||
irbuilder := mod.Context().NewBuilder()
|
||||
defer irbuilder.Dispose()
|
||||
@@ -67,22 +62,3 @@ func CreateStackSizeLoads(mod llvm.Module, config *compileopts.Config) []string
|
||||
|
||||
return functionNames
|
||||
}
|
||||
|
||||
// Append the given values to the llvm.used array. The values can be any pointer
|
||||
// type, they will be bitcast to i8*.
|
||||
func appendToUsedGlobals(mod llvm.Module, values ...llvm.Value) {
|
||||
if !mod.NamedGlobal("llvm.used").IsNil() {
|
||||
// Sanity check. TODO: we don't emit such a global at the moment, but
|
||||
// when we do we should append to it instead.
|
||||
panic("todo: append to existing llvm.used")
|
||||
}
|
||||
i8ptrType := llvm.PointerType(mod.Context().Int8Type(), 0)
|
||||
var castValues []llvm.Value
|
||||
for _, value := range values {
|
||||
castValues = append(castValues, llvm.ConstBitCast(value, i8ptrType))
|
||||
}
|
||||
usedInitializer := llvm.ConstArray(i8ptrType, castValues)
|
||||
used := llvm.AddGlobal(mod, usedInitializer.Type(), "llvm.used")
|
||||
used.SetInitializer(usedInitializer)
|
||||
used.SetLinkage(llvm.AppendingLinkage)
|
||||
}
|
||||
|
||||
Vendored
-1
@@ -2,7 +2,6 @@ target datalayout = "e-m:e-p:32:32-i64:64-v128:64:128-a:0:32-n32-S64"
|
||||
target triple = "armv7m-none-eabi"
|
||||
|
||||
@"internal/task.stackSizes" = global [1 x i32] [i32 1024], section ".tinygo_stacksizes"
|
||||
@llvm.used = appending global [2 x i8*] [i8* bitcast ([1 x i32]* @"internal/task.stackSizes" to i8*), i8* bitcast (void (i8*)* @"runtime.run$1$gowrapper" to i8*)]
|
||||
|
||||
declare i32 @"internal/task.getGoroutineStackSize"(i32, i8*, i8*)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user