diff --git a/legacy/builder/builder.go b/legacy/builder/builder.go index 195338d641c..e9aafb0b73c 100644 --- a/legacy/builder/builder.go +++ b/legacy/builder/builder.go @@ -99,7 +99,7 @@ func (s *Builder) Run(ctx *types.Context) error { &RecipeByPrefixSuffixRunner{Prefix: constants.HOOKS_POSTBUILD, Suffix: constants.HOOKS_PATTERN_SUFFIX}, } - mainErr := runCommands(ctx, commands, true) + mainErr := runCommands(ctx, commands) commands = []types.Command{ &PrintUsedAndNotUsedLibraries{SketchError: mainErr != nil}, @@ -110,7 +110,7 @@ func (s *Builder) Run(ctx *types.Context) error { &phases.Sizer{SketchError: mainErr != nil}, } - otherErr := runCommands(ctx, commands, false) + otherErr := runCommands(ctx, commands) if mainErr != nil { return mainErr @@ -128,7 +128,7 @@ func (s *PreprocessSketch) Run(ctx *types.Context) error { } else { commands = append(commands, &ContainerAddPrototypes{}) } - return runCommands(ctx, commands, true) + return runCommands(ctx, commands) } type Preprocess struct{} @@ -158,7 +158,7 @@ func (s *Preprocess) Run(ctx *types.Context) error { &PreprocessSketch{}, } - if err := runCommands(ctx, commands, true); err != nil { + if err := runCommands(ctx, commands); err != nil { return err } @@ -180,22 +180,21 @@ func (s *ParseHardwareAndDumpBuildProperties) Run(ctx *types.Context) error { &DumpBuildProperties{}, } - return runCommands(ctx, commands, true) + return runCommands(ctx, commands) } -func runCommands(ctx *types.Context, commands []types.Command, progressEnabled bool) error { - - ctx.Progress.PrintEnabled = progressEnabled - ctx.Progress.Progress = 0 +func runCommands(ctx *types.Context, commands []types.Command) error { + ctx.Progress.AddSubSteps(len(commands)) + defer ctx.Progress.RemoveSubSteps() for _, command := range commands { PrintRingNameIfDebug(ctx, command) - ctx.Progress.Steps = 100.0 / float64(len(commands)) - builder_utils.PrintProgressIfProgressEnabledAndMachineLogger(ctx) err := command.Run(ctx) if err != nil { return errors.WithStack(err) } + ctx.Progress.CompleteStep() + builder_utils.PrintProgressIfProgressEnabledAndMachineLogger(ctx) } return nil } diff --git a/legacy/builder/builder_utils/utils.go b/legacy/builder/builder_utils/utils.go index 5e96c815541..0c6e991762f 100644 --- a/legacy/builder/builder_utils/utils.go +++ b/legacy/builder/builder_utils/utils.go @@ -41,8 +41,7 @@ func PrintProgressIfProgressEnabledAndMachineLogger(ctx *types.Context) { log := ctx.GetLogger() if log.Name() == "machine" { - log.Println(constants.LOG_LEVEL_INFO, constants.MSG_PROGRESS, strconv.FormatFloat(ctx.Progress.Progress, 'f', 2, 32)) - ctx.Progress.Progress += ctx.Progress.Steps + log.Println(constants.LOG_LEVEL_INFO, constants.MSG_PROGRESS, strconv.FormatFloat(float64(ctx.Progress.Progress), 'f', 2, 32)) } } @@ -69,18 +68,35 @@ func CompileFilesRecursive(ctx *types.Context, sourcePath *paths.Path, buildPath } func CompileFiles(ctx *types.Context, sourcePath *paths.Path, recurse bool, buildPath *paths.Path, buildProperties *properties.Map, includes []string) (paths.PathList, error) { - sObjectFiles, err := compileFilesWithExtensionWithRecipe(ctx, sourcePath, recurse, buildPath, buildProperties, includes, ".S", constants.RECIPE_S_PATTERN) + sSources, err := findFilesInFolder(sourcePath, ".S", recurse) if err != nil { return nil, errors.WithStack(err) } - cObjectFiles, err := compileFilesWithExtensionWithRecipe(ctx, sourcePath, recurse, buildPath, buildProperties, includes, ".c", constants.RECIPE_C_PATTERN) + cSources, err := findFilesInFolder(sourcePath, ".c", recurse) if err != nil { return nil, errors.WithStack(err) } - cppObjectFiles, err := compileFilesWithExtensionWithRecipe(ctx, sourcePath, recurse, buildPath, buildProperties, includes, ".cpp", constants.RECIPE_CPP_PATTERN) + cppSources, err := findFilesInFolder(sourcePath, ".cpp", recurse) if err != nil { return nil, errors.WithStack(err) } + + ctx.Progress.AddSubSteps(len(sSources) + len(cSources) + len(cppSources)) + defer ctx.Progress.RemoveSubSteps() + + sObjectFiles, err := compileFilesWithRecipe(ctx, sourcePath, sSources, buildPath, buildProperties, includes, constants.RECIPE_S_PATTERN) + if err != nil { + return nil, errors.WithStack(err) + } + cObjectFiles, err := compileFilesWithRecipe(ctx, sourcePath, cSources, buildPath, buildProperties, includes, constants.RECIPE_C_PATTERN) + if err != nil { + return nil, errors.WithStack(err) + } + cppObjectFiles, err := compileFilesWithRecipe(ctx, sourcePath, cppSources, buildPath, buildProperties, includes, constants.RECIPE_CPP_PATTERN) + if err != nil { + return nil, errors.WithStack(err) + } + objectFiles := paths.NewPathList() objectFiles.AddAll(sObjectFiles) objectFiles.AddAll(cObjectFiles) @@ -88,14 +104,6 @@ func CompileFiles(ctx *types.Context, sourcePath *paths.Path, recurse bool, buil return objectFiles, nil } -func compileFilesWithExtensionWithRecipe(ctx *types.Context, sourcePath *paths.Path, recurse bool, buildPath *paths.Path, buildProperties *properties.Map, includes []string, extension string, recipe string) (paths.PathList, error) { - sources, err := findFilesInFolder(sourcePath, extension, recurse) - if err != nil { - return nil, errors.WithStack(err) - } - return compileFilesWithRecipe(ctx, sourcePath, sources, buildPath, buildProperties, includes, recipe) -} - func findFilesInFolder(sourcePath *paths.Path, extension string, recurse bool) (paths.PathList, error) { files, err := utils.ReadDirFiltered(sourcePath.String(), utils.FilterFilesWithExtensions(extension)) if err != nil { @@ -164,11 +172,8 @@ func compileFilesWithRecipe(ctx *types.Context, sourcePath *paths.Path, sources var errorsList []error var errorsMux sync.Mutex - ctx.Progress.Steps = ctx.Progress.Steps / float64(len(sources)) - queue := make(chan *paths.Path) job := func(source *paths.Path) { - PrintProgressIfProgressEnabledAndMachineLogger(ctx) objectFile, err := compileFileWithRecipe(ctx, sourcePath, source, buildPath, buildProperties, includes, recipe) if err != nil { errorsMux.Lock() @@ -206,6 +211,9 @@ func compileFilesWithRecipe(ctx *types.Context, sourcePath *paths.Path, sources break } queue <- source + + ctx.Progress.CompleteStep() + PrintProgressIfProgressEnabledAndMachineLogger(ctx) } close(queue) wg.Wait() diff --git a/legacy/builder/container_setup.go b/legacy/builder/container_setup.go index 2561b60c732..e562e0853b3 100644 --- a/legacy/builder/container_setup.go +++ b/legacy/builder/container_setup.go @@ -28,6 +28,10 @@ import ( type ContainerSetupHardwareToolsLibsSketchAndProps struct{} func (s *ContainerSetupHardwareToolsLibsSketchAndProps) Run(ctx *types.Context) error { + // total number of steps in this container: 14 + ctx.Progress.AddSubSteps(14) + defer ctx.Progress.RemoveSubSteps() + commands := []types.Command{ &AddAdditionalEntriesToContext{}, &FailIfBuildPathEqualsSketchPath{}, @@ -40,15 +44,14 @@ func (s *ContainerSetupHardwareToolsLibsSketchAndProps) Run(ctx *types.Context) &LibrariesLoader{}, } - ctx.Progress.Steps = ctx.Progress.Steps / float64(len(commands)) - for _, command := range commands { - builder_utils.PrintProgressIfProgressEnabledAndMachineLogger(ctx) PrintRingNameIfDebug(ctx, command) err := command.Run(ctx) if err != nil { return errors.WithStack(err) } + ctx.Progress.CompleteStep() + builder_utils.PrintProgressIfProgressEnabledAndMachineLogger(ctx) } if ctx.SketchLocation != nil { @@ -69,6 +72,8 @@ func (s *ContainerSetupHardwareToolsLibsSketchAndProps) Run(ctx *types.Context) ctx.SketchLocation = paths.New(sketch.MainFile.Path) ctx.Sketch = types.SketchToLegacy(sketch) } + ctx.Progress.CompleteStep() + builder_utils.PrintProgressIfProgressEnabledAndMachineLogger(ctx) commands = []types.Command{ &SetupBuildProperties{}, @@ -77,15 +82,14 @@ func (s *ContainerSetupHardwareToolsLibsSketchAndProps) Run(ctx *types.Context) &AddMissingBuildPropertiesFromParentPlatformTxtFiles{}, } - ctx.Progress.Steps = ctx.Progress.Steps / float64(len(commands)) - for _, command := range commands { - builder_utils.PrintProgressIfProgressEnabledAndMachineLogger(ctx) PrintRingNameIfDebug(ctx, command) err := command.Run(ctx) if err != nil { return errors.WithStack(err) } + ctx.Progress.CompleteStep() + builder_utils.PrintProgressIfProgressEnabledAndMachineLogger(ctx) } return nil diff --git a/legacy/builder/phases/libraries_builder.go b/legacy/builder/phases/libraries_builder.go index 28f39ca429b..355bbda430e 100644 --- a/legacy/builder/phases/libraries_builder.go +++ b/legacy/builder/phases/libraries_builder.go @@ -143,6 +143,9 @@ func fixLDFLAGforPrecompiledLibraries(ctx *types.Context, libs libraries.List) e } func compileLibraries(ctx *types.Context, libraries libraries.List, buildPath *paths.Path, buildProperties *properties.Map, includes []string) (paths.PathList, error) { + ctx.Progress.AddSubSteps(len(libraries)) + defer ctx.Progress.RemoveSubSteps() + objectFiles := paths.NewPathList() for _, library := range libraries { libraryObjectFiles, err := compileLibrary(ctx, library, buildPath, buildProperties, includes) @@ -150,6 +153,9 @@ func compileLibraries(ctx *types.Context, libraries libraries.List, buildPath *p return nil, errors.WithStack(err) } objectFiles = append(objectFiles, libraryObjectFiles...) + + ctx.Progress.CompleteStep() + builder_utils.PrintProgressIfProgressEnabledAndMachineLogger(ctx) } return objectFiles, nil diff --git a/legacy/builder/types/context.go b/legacy/builder/types/context.go index 50b3935ef79..bcd24047550 100644 --- a/legacy/builder/types/context.go +++ b/legacy/builder/types/context.go @@ -1,3 +1,18 @@ +// This file is part of arduino-cli. +// +// Copyright 2020 ARDUINO SA (http://www.arduino.cc/) +// +// This software is released under the GNU General Public License version 3, +// which covers the main part of arduino-cli. +// The terms of this license can be found at: +// https://www.gnu.org/licenses/gpl-3.0.en.html +// +// You can be released from the requirements of the above licenses by purchasing +// a commercial license. Buying such a license is mandatory if you want to +// modify or otherwise use the software for commercial activities involving the +// Arduino software without disclosing the source code of your own applications. +// To purchase a commercial license, send an email to license@arduino.cc. + package types import ( @@ -16,8 +31,31 @@ import ( type ProgressStruct struct { PrintEnabled bool - Steps float64 - Progress float64 + Progress float32 + StepAmount float32 + Parent *ProgressStruct +} + +func (p *ProgressStruct) AddSubSteps(steps int) { + p.Parent = &ProgressStruct{ + Progress: p.Progress, + StepAmount: p.StepAmount, + Parent: p.Parent, + } + if p.StepAmount == 0.0 { + p.StepAmount = 100.0 + } + p.StepAmount /= float32(steps) +} + +func (p *ProgressStruct) RemoveSubSteps() { + p.Progress = p.Parent.Progress + p.StepAmount = p.Parent.StepAmount + p.Parent = p.Parent.Parent +} + +func (p *ProgressStruct) CompleteStep() { + p.Progress += p.StepAmount } // Context structure diff --git a/legacy/builder/types/progress_test.go b/legacy/builder/types/progress_test.go new file mode 100644 index 00000000000..2d367acf898 --- /dev/null +++ b/legacy/builder/types/progress_test.go @@ -0,0 +1,67 @@ +// This file is part of arduino-cli. +// +// Copyright 2020 ARDUINO SA (http://www.arduino.cc/) +// +// This software is released under the GNU General Public License version 3, +// which covers the main part of arduino-cli. +// The terms of this license can be found at: +// https://www.gnu.org/licenses/gpl-3.0.en.html +// +// You can be released from the requirements of the above licenses by purchasing +// a commercial license. Buying such a license is mandatory if you want to +// modify or otherwise use the software for commercial activities involving the +// Arduino software without disclosing the source code of your own applications. +// To purchase a commercial license, send an email to license@arduino.cc. + +package types + +import ( + "fmt" + "testing" + + "github.com/stretchr/testify/require" +) + +func TestProgress(t *testing.T) { + p := &ProgressStruct{} + p.AddSubSteps(3) + require.Equal(t, float32(0.0), p.Progress) + require.InEpsilon(t, 33.33333, p.StepAmount, 0.00001) + fmt.Printf("%+v\n", p) + { + p.CompleteStep() + require.InEpsilon(t, 33.33333, p.Progress, 0.00001) + fmt.Printf("%+v\n", p) + + p.AddSubSteps(4) + require.InEpsilon(t, 33.33333, p.Progress, 0.00001) + require.InEpsilon(t, 8.33333, p.StepAmount, 0.00001) + fmt.Printf("%+v\n", p) + { + p.CompleteStep() + require.InEpsilon(t, 41.66666, p.Progress, 0.00001) + fmt.Printf("%+v\n", p) + + p.CompleteStep() + require.InEpsilon(t, 50.0, p.Progress, 0.00001) + fmt.Printf("%+v\n", p) + + p.AddSubSteps(0) // zero steps + fmt.Printf("%+v\n", p) + { + // p.CompleteStep() invalid here + } + p.RemoveSubSteps() + } + p.RemoveSubSteps() + require.InEpsilon(t, 33.33333, p.Progress, 0.00001) + fmt.Printf("%+v\n", p) + + p.CompleteStep() + require.InEpsilon(t, 66.66666, p.Progress, 0.00001) + fmt.Printf("%+v\n", p) + } + p.RemoveSubSteps() + require.Equal(t, float32(0.0), p.Progress) + require.Equal(t, float32(0.0), p.StepAmount) +}