-
Notifications
You must be signed in to change notification settings - Fork 569
Support embed
package.
#1145
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Closed
Closed
Support embed
package.
#1145
Changes from all commits
Commits
Show all changes
26 commits
Select commit
Hold shift + click to select a range
61801ed
compiler/natives/src: add embed
visualfc b0db6f5
compiler/natives: go generate
visualfc 522585d
build: check and generate embed file for build/test
visualfc 561171d
build: BuildFiles support check embed file for build/run
visualfc 7dd9288
tests/testdata/legacy_syscall: fix go:build
visualfc 2a8f084
goembed v0.2.3
visualfc 092a24b
checkEmbed: check load file error
visualfc 4316b6d
build: move checkEmbed to BuildPackage
visualfc b4fad18
build: checkEmbed unknown type check error
visualfc 7c483c8
build: embedFiles
visualfc aec0b57
compiler/natives/src: prealloc embed
visualfc 7cb07f3
build: embedFiles rewrite ast for go:embed vars
visualfc f4c2418
compiler/natives/src: add embed/internal/embedtest
visualfc 0c19332
build: BuildFiles ctx.ReadDir prealloc
visualfc 625d4cc
build: joinEmbedPatternPos
visualfc 1e0f65a
goembed v0.2.5
visualfc a80e720
goembed v0.2.7
visualfc 2a6f9de
goembed v0.2.8
visualfc fd891b2
goembed v0.3.0 go:embed check multiple file error if kind not EmbedFiles
visualfc ffe4555
goembed v0.3.1
visualfc c5140d5
build: embedFiles check goembed.EmbedMaybeAlias
visualfc b612190
x
visualfc a9d764a
goembed v0.3.2
visualfc b799041
Merge remote-tracking branch 'upstream/master' into embed
visualfc 8fb8e58
goembed v0.3.3
visualfc c552a3d
remove compiler/natives/src/embed/internal/embedtest
visualfc File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,4 +1,3 @@ | ||
embed/internal/embedtest | ||
encoding/xml | ||
go/build | ||
go/internal/srcimporter | ||
|
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,175 @@ | ||
package build | ||
|
||
import ( | ||
"bytes" | ||
"fmt" | ||
"go/ast" | ||
"go/parser" | ||
"go/token" | ||
"strconv" | ||
|
||
"github.com/visualfc/goembed" | ||
) | ||
|
||
func buildIdent(name string) string { | ||
return fmt.Sprintf("__gopherjs_embed_%x__", name) | ||
} | ||
|
||
var embed_head = `package %v | ||
|
||
import ( | ||
"embed" | ||
_ "unsafe" | ||
) | ||
|
||
//go:linkname __gopherjs_embed_buildFS__ embed.buildFS | ||
func __gopherjs_embed_buildFS__(list []struct { | ||
name string | ||
data string | ||
hash [16]byte | ||
}) (f embed.FS) | ||
` | ||
|
||
// embedFiles generates an additional source file, which initializes all variables in the package with a go:embed directive. | ||
func embedFiles(pkg *PackageData, fset *token.FileSet, files []*ast.File) (*ast.File, error) { | ||
if len(pkg.EmbedPatternPos) == 0 { | ||
return nil, nil | ||
} | ||
|
||
ems, err := goembed.CheckEmbed(pkg.EmbedPatternPos, fset, files) | ||
if err != nil { | ||
return nil, err | ||
nevkontakte marked this conversation as resolved.
Show resolved
Hide resolved
|
||
} | ||
|
||
r := goembed.NewResolve() | ||
for _, em := range ems { | ||
fs, err := r.Load(pkg.Dir, fset, em) | ||
if err != nil { | ||
return nil, err | ||
} | ||
switch em.Kind { | ||
case goembed.EmbedMaybeAlias: | ||
// value = Type(data) | ||
// valid alias string or []byte type used by types.check | ||
em.Spec.Values = []ast.Expr{ | ||
&ast.CallExpr{ | ||
Fun: em.Spec.Type, | ||
Args: []ast.Expr{ | ||
&ast.Ident{Name: buildIdent(fs[0].Name), | ||
NamePos: em.Spec.Names[0].NamePos}, | ||
}, | ||
}} | ||
case goembed.EmbedBytes: | ||
// value = []byte(data) | ||
em.Spec.Values = []ast.Expr{ | ||
&ast.CallExpr{ | ||
Fun: em.Spec.Type, | ||
Args: []ast.Expr{ast.NewIdent(buildIdent(fs[0].Name))}, | ||
}} | ||
case goembed.EmbedString: | ||
// value = data | ||
em.Spec.Values = []ast.Expr{ast.NewIdent(buildIdent(fs[0].Name))} | ||
case goembed.EmbedFiles: | ||
// value = __gopherjs_embed_buildFS__([]struct{name string; data string; hash [16]byte}{...}) | ||
fs = goembed.BuildFS(fs) | ||
elts := make([]ast.Expr, len(fs)) | ||
for i, f := range fs { | ||
if len(f.Data) == 0 { | ||
elts[i] = &ast.CompositeLit{ | ||
Elts: []ast.Expr{ | ||
&ast.BasicLit{Kind: token.STRING, Value: strconv.Quote(f.Name)}, | ||
&ast.BasicLit{Kind: token.STRING, Value: `""`}, | ||
&ast.CompositeLit{ | ||
Type: &ast.ArrayType{ | ||
Len: &ast.BasicLit{Kind: token.INT, Value: "16"}, | ||
Elt: ast.NewIdent("byte"), | ||
}, | ||
}, | ||
}, | ||
} | ||
} else { | ||
var hash [16]ast.Expr | ||
for j, v := range f.Hash { | ||
hash[j] = &ast.BasicLit{Kind: token.INT, Value: strconv.Itoa(int(v))} | ||
} | ||
elts[i] = &ast.CompositeLit{ | ||
Elts: []ast.Expr{ | ||
&ast.BasicLit{Kind: token.STRING, Value: strconv.Quote(f.Name)}, | ||
ast.NewIdent(buildIdent(f.Name)), | ||
&ast.CompositeLit{ | ||
Type: &ast.ArrayType{ | ||
Len: &ast.BasicLit{Kind: token.INT, Value: "16"}, | ||
Elt: ast.NewIdent("byte"), | ||
}, | ||
Elts: hash[:], | ||
}, | ||
}, | ||
} | ||
} | ||
} | ||
call := &ast.CallExpr{ | ||
Fun: ast.NewIdent("__gopherjs_embed_buildFS__"), | ||
Args: []ast.Expr{ | ||
&ast.CompositeLit{ | ||
Type: &ast.ArrayType{ | ||
Elt: &ast.StructType{ | ||
Fields: &ast.FieldList{ | ||
List: []*ast.Field{ | ||
&ast.Field{ | ||
Names: []*ast.Ident{ast.NewIdent("name")}, | ||
Type: ast.NewIdent("string"), | ||
}, | ||
&ast.Field{ | ||
Names: []*ast.Ident{ast.NewIdent("data")}, | ||
Type: ast.NewIdent("string"), | ||
}, | ||
&ast.Field{ | ||
Names: []*ast.Ident{ast.NewIdent("hash")}, | ||
Type: &ast.ArrayType{ | ||
Len: &ast.BasicLit{Kind: token.INT, Value: "16"}, | ||
Elt: ast.NewIdent("byte"), | ||
}, | ||
}, | ||
}, | ||
}, | ||
}, | ||
}, | ||
Elts: elts, | ||
}, | ||
}, | ||
} | ||
em.Spec.Values = []ast.Expr{call} | ||
} | ||
} | ||
|
||
var buf bytes.Buffer | ||
fmt.Fprintf(&buf, embed_head, pkg.Name) | ||
buf.WriteString("\nconst (\n") | ||
for _, f := range r.Files() { | ||
if len(f.Data) == 0 { | ||
fmt.Fprintf(&buf, "\t%v = \"\"\n", buildIdent(f.Name)) | ||
} else { | ||
fmt.Fprintf(&buf, "\t%v = \"%v\"\n", buildIdent(f.Name), goembed.BytesToHex(f.Data)) | ||
} | ||
} | ||
buf.WriteString(")\n\n") | ||
f, err := parser.ParseFile(fset, "js_embed.go", buf.String(), parser.ParseComments) | ||
if err != nil { | ||
return nil, err | ||
} | ||
return f, nil | ||
} | ||
|
||
func joinEmbedPatternPos(m1, m2 map[string][]token.Position) map[string][]token.Position { | ||
if len(m1) == 0 && len(m2) == 0 { | ||
return nil | ||
} | ||
m := make(map[string][]token.Position) | ||
for k, v := range m1 { | ||
m[k] = v | ||
} | ||
for k, v := range m2 { | ||
m[k] = append(m[k], v...) | ||
} | ||
return m | ||
} |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.