Commit 15b0fe85 authored by Hugo Moreau's avatar Hugo Moreau
Browse files

Dependencies: Commenting statements to keep

 * main.go,
   transform/dependencies_rework.go : Modified.
parent bf16e8e7
Pipeline #28376 passed with stage
in 2 minutes and 24 seconds
......@@ -510,7 +510,7 @@ func handleBlackboxBlocks(src []byte, variables map[string]bool) {
meta := transform.NewMeta(fset, info)
transform.ApplyAll(node, meta, []transform.Transform{
&transform.DependenciesRework{NVariables: variables},
&transform.Debug{}, // only for debuging a special transformation
// &transform.Debug{}, // only for debuging a special transformation
})
}
......
package transform
import (
"bytes"
"fmt"
"go/ast"
"go/printer"
"regexp"
"strconv"
)
......@@ -10,17 +13,20 @@ type DependenciesRework struct {
GlobalVar []*ast.Object
Func map[*ast.Object]*FuncInfosBis
NVariables map[string]bool
file *ast.File
}
type VarInfos struct {
ReadStmt map[*[]StmtNumber]bool
WriteStmt map[*[]StmtNumber]bool
VarDep map[*ast.Object]bool
Required bool
}
type FuncInfosBis struct {
Parameters []*ast.Field
Variables map[*ast.Object]*VarInfos
RequiredSt map[*[]StmtNumber]bool
}
type StmtNumber struct {
......@@ -35,6 +41,7 @@ func (t *DependenciesRework) init(file *ast.File) {
t.GlobalVar = append(t.GlobalVar, val)
}
}
t.file = file
}
func (t *DependenciesRework) handleFuncDecl(funcDecl *ast.FuncDecl) {
......@@ -45,6 +52,7 @@ func (t *DependenciesRework) handleFuncDecl(funcDecl *ast.FuncDecl) {
currentFunc := &FuncInfosBis{
Parameters: funcDecl.Type.Params.List,
Variables: make(map[*ast.Object]*VarInfos),
RequiredSt: make(map[*[]StmtNumber]bool),
}
for key, value := range funcDecl.Body.List {
currentFunc.handleStmt([]StmtNumber{StmtNumber{key, false}}, false, value)
......@@ -63,16 +71,18 @@ func (infos *FuncInfosBis) addReadAndWrite(number []StmtNumber, read, write []*a
}
}
infos.Variables[value].ReadStmt[&number] = true
for _, dep := range read {
if dep != value {
infos.Variables[value].VarDep[dep] = true
/*
for _, dep := range read {
if dep != value {
infos.Variables[value].VarDep[dep] = true
}
}
}
for _, dep := range write {
if dep != value {
infos.Variables[value].VarDep[dep] = true
for _, dep := range write {
if dep != value {
infos.Variables[value].VarDep[dep] = true
}
}
}
*/
}
for _, value := range write {
if _, ok := infos.Variables[value]; !ok {
......@@ -178,6 +188,13 @@ func detectVar(stmt ast.Node) []*ast.Object {
return variables
}
func (t *DependenciesRework) insertCommentBefore(meta *Meta, node ast.Node, comment string) {
c := &ast.Comment{Text: "// " + comment, Slash: node.Pos() - 1}
cg := &ast.CommentGroup{List: []*ast.Comment{c}}
meta.fset.File(node.End()).AddLine(int(node.End()) + 2)
t.file.Comments = append(t.file.Comments, cg)
}
// Pre traversal applies the transformation.
func (t *DependenciesRework) Pre(meta *Meta, v *Visitor) bool {
c := v.Cursor()
......@@ -190,38 +207,145 @@ func (t *DependenciesRework) Pre(meta *Meta, v *Visitor) bool {
return true
}
func sameStmtNumber(a, b []StmtNumber) bool {
if len(a) != len(b) {
return false
}
for i, v := range a {
if v != b[i] {
return false
}
}
return true
}
func (infos *FuncInfosBis) isRequired(a []StmtNumber) bool {
for key, _ := range infos.RequiredSt {
if sameStmtNumber(*key, a) {
return true
}
}
return false
}
func (t *DependenciesRework) postFuncDecl(meta *Meta, funcDecl *ast.FuncDecl) {
currentFunc := t.Func[funcDecl.Name.Obj]
for key, value := range funcDecl.Body.List {
currentFunc.postStmt(t, meta, []StmtNumber{StmtNumber{key, false}}, false, value)
}
}
func (infos *FuncInfosBis) postStmt(t *DependenciesRework, meta *Meta, number []StmtNumber, if_or_else bool, stmt ast.Node) {
if stmt == nil {
return
}
if infos.isRequired(number) {
t.insertCommentBefore(meta, stmt, "REQUIRED")
}
switch stmt := stmt.(type) {
case *ast.BlockStmt:
for key, value := range stmt.List {
infos.postStmt(t, meta, append(number, StmtNumber{key, if_or_else}), false, value)
}
return
case *ast.ForStmt:
infos.postStmt(t, meta, number, false, stmt.Body)
return
case *ast.IfStmt:
infos.postStmt(t, meta, number, false, stmt.Body)
infos.postStmt(t, meta, number, true, stmt.Else)
return
default:
return
}
}
// Post traversal applies the transformation.
func (t *DependenciesRework) Post(meta *Meta, v *Visitor) bool {
c := v.Cursor()
switch c.Node().(type) {
switch node := c.Node().(type) {
case *ast.File:
for key, _ := range t.NVariables {
fmt.Println(key)
}
for _, v := range t.GlobalVar {
fmt.Println(v)
}
for key, value := range t.Func {
fmt.Println(key)
for k, val := range value.Variables {
fmt.Println("\t", k)
fmt.Println("\t READ STMTS")
for statements, _ := range val.ReadStmt {
fmt.Println("\t\t", StmtNumberString(statements))
t.TakeRequiredVariables()
for _, val := range node.Decls {
switch val := val.(type) {
case *ast.FuncDecl:
t.postFuncDecl(meta, val)
}
}
var output []byte
buf := bytes.NewBuffer(output)
if err := printer.Fprint(buf, meta.fset, c.Node()); err != nil {
panic(err)
}
fmt.Println(buf)
}
return true
}
type wantedVar struct {
Package, Func, Name string
}
func (t *DependenciesRework) TakeRequiredVariables() {
variables := t.TakeVariables()
for name, info := range t.Func {
for k, v := range info.Variables {
for _, val := range variables {
if val.Name == k.Name {
if val.Func == name.Name {
info.RequiredRec(v)
} else if val.Func == "" {
for _, v2 := range t.GlobalVar {
if v2.Name == val.Name {
info.RequiredRec(v)
}
}
}
}
fmt.Println("\t WRITE STMTS")
for statements, _ := range val.WriteStmt {
fmt.Println("\t\t", StmtNumberString(statements))
}
}
}
}
func (info *FuncInfosBis) RequiredRec(variable *VarInfos) {
req := variable.Required
variable.Required = true
for key, _ := range variable.WriteStmt {
info.RequiredSt[key] = true
}
if !req {
for v, _ := range variable.VarDep {
info.RequiredRec(info.Variables[v])
}
}
}
func (t *DependenciesRework) TakeVariables() []wantedVar {
r := regexp.MustCompile("_")
res := []wantedVar{}
for key, _ := range t.NVariables {
packAndFunc := r.Split(key, 2)
if len(packAndFunc) == 2 {
funcAndName := r.Split(packAndFunc[1], 2)
if len(funcAndName) == 2 {
multi := false
for k, _ := range t.Func {
if k.Name == funcAndName[0] {
multi = true
break
}
}
fmt.Println("\t VARIABLES DEPENDENCIES")
for variables, _ := range val.VarDep {
fmt.Println("\t\t", variables)
if multi {
res = append(res, wantedVar{packAndFunc[0], funcAndName[0], funcAndName[1]})
} else {
res = append(res, wantedVar{packAndFunc[0], "", packAndFunc[1]})
}
println()
} else {
res = append(res, wantedVar{packAndFunc[0], "", packAndFunc[1]})
}
}
}
return true
return res
}
func StmtNumberString(stmtsNmb *[]StmtNumber) string {
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment