@ -18,17 +18,19 @@ func isDirective(text string) bool {
return strings . HasPrefix ( text , "//go:" ) || strings . HasPrefix ( text , "// +build" )
return strings . HasPrefix ( text , "//go:" ) || strings . HasPrefix ( text , "// +build" )
}
}
var printBuf1 , printBuf2 bytes . Buffer
// printFile prints a Go file to a buffer, while also removing non-directive
// printFile prints a Go file to a buffer, while also removing non-directive
// comments and adding extra compiler directives to obfuscate position
// comments and adding extra compiler directives to obfuscate position
// information.
// information.
func printFile ( file1 * ast . File ) ( [ ] byte , error ) {
func printFile ( file1 * ast . File ) ( [ ] byte , error ) {
printConfig := printer . Config { Mode : printer . RawFormat }
printConfig := printer . Config { Mode : printer . RawFormat }
var buf1 bytes . Buffer
printBuf1 . Reset ( )
if err := printConfig . Fprint ( & b uf1, fset , file1 ) ; err != nil {
if err := printConfig . Fprint ( & printB uf1, fset , file1 ) ; err != nil {
return nil , err
return nil , err
}
}
src := b uf1. Bytes ( )
src := printB uf1. Bytes ( )
if ! curPkg . ToObfuscate {
if ! curPkg . ToObfuscate {
// TODO(mvdan): make transformCompile handle untouched
// TODO(mvdan): make transformCompile handle untouched
@ -59,16 +61,6 @@ func printFile(file1 *ast.File) ([]byte, error) {
return nil , fmt . Errorf ( "re-parse error: %w" , err )
return nil , fmt . Errorf ( "re-parse error: %w" , err )
}
}
// Keep the compiler directives, and change position info.
type commentToAdd struct {
offset int
text string
}
var toAdd [ ] commentToAdd
addComment := func ( offset int , text string ) {
toAdd = append ( toAdd , commentToAdd { offset , text } )
}
// Remove any comments by making them whitespace.
// Remove any comments by making them whitespace.
// Keep directives, as they affect the build.
// Keep directives, as they affect the build.
// This is superior to removing the comments before printing,
// This is superior to removing the comments before printing,
@ -94,6 +86,12 @@ func printFile(file1 *ast.File) ([]byte, error) {
return true
return true
} )
} )
// Keep the compiler directives, and change position info.
type commentToAdd struct {
offset int
text string
}
var toAdd [ ] commentToAdd
i := 0
i := 0
ast . Inspect ( file2 , func ( node ast . Node ) bool {
ast . Inspect ( file2 , func ( node ast . Node ) bool {
node , ok := node . ( * ast . CallExpr )
node , ok := node . ( * ast . CallExpr )
@ -108,12 +106,14 @@ func printFile(file1 *ast.File) ([]byte, error) {
newName = hashWith ( curPkg . GarbleActionID , origPos ) + ".go"
newName = hashWith ( curPkg . GarbleActionID , origPos ) + ".go"
// log.Printf("%q hashed with %x to %q", origPos, curPkg.GarbleActionID, newName)
// log.Printf("%q hashed with %x to %q", origPos, curPkg.GarbleActionID, newName)
}
}
newPos := fmt . Sprintf ( "%s:1" , newName )
pos := fset . Position ( node . Pos ( ) )
pos := fset . Position ( node . Pos ( ) )
// We use the "/*text*/" form, since we can use multiple of them
// We use the "/*text*/" form, since we can use multiple of them
// on a single line, and they don't require extra newlines.
// on a single line, and they don't require extra newlines.
addComment ( pos . Offset , "/*line " + newPos + "*/" )
toAdd = append ( toAdd , commentToAdd {
offset : pos . Offset ,
text : fmt . Sprintf ( "/*line %s:1*/" , newName ) ,
} )
return true
return true
} )
} )
@ -123,16 +123,16 @@ func printFile(file1 *ast.File) ([]byte, error) {
} )
} )
copied := 0
copied := 0
var buf2 bytes . Buffer
printBuf2 . Reset ( )
// Make sure the entire file gets a zero filename by default,
// Make sure the entire file gets a zero filename by default,
// in case we miss any positions below.
// in case we miss any positions below.
// We use a //-style comment, because there might be build tags.
// We use a //-style comment, because there might be build tags.
// addComment is for /*-style comments, so add it to b uf2 directly.
// toAdd is for /*-style comments, so add it to printB uf2 directly.
b uf2. WriteString ( "//line :1\n" )
printB uf2. WriteString ( "//line :1\n" )
for _ , comment := range toAdd {
for _ , comment := range toAdd {
b uf2. Write ( src [ copied : comment . offset ] )
printB uf2. Write ( src [ copied : comment . offset ] )
copied = comment . offset
copied = comment . offset
// We assume that all comments are of the form "/*text*/".
// We assume that all comments are of the form "/*text*/".
@ -140,10 +140,10 @@ func printFile(file1 *ast.File) ([]byte, error) {
// Otherwise, we could change the syntax of the program.
// Otherwise, we could change the syntax of the program.
// Inserting "/*text*/" in "a/b" // must be "a/ /*text*/ b",
// Inserting "/*text*/" in "a/b" // must be "a/ /*text*/ b",
// as "a//*text*/b" is tokenized as a "//" comment.
// as "a//*text*/b" is tokenized as a "//" comment.
b uf2. WriteByte ( ' ' )
printB uf2. WriteByte ( ' ' )
b uf2. WriteString ( comment . text )
printB uf2. WriteString ( comment . text )
b uf2. WriteByte ( ' ' )
printB uf2. WriteByte ( ' ' )
}
}
b uf2. Write ( src [ copied : ] )
printB uf2. Write ( src [ copied : ] )
return b uf2. Bytes ( ) , nil
return printB uf2. Bytes ( ) , nil
}
}