Skip to content

Commit f836ac2

Browse files
move CompileFiles in the builder struct
1 parent 991004d commit f836ac2

File tree

5 files changed

+193
-276
lines changed

5 files changed

+193
-276
lines changed

Diff for: arduino/builder/compilation.go

+165
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,165 @@
1+
package builder
2+
3+
import (
4+
"fmt"
5+
"runtime"
6+
"strings"
7+
"sync"
8+
9+
"github.com/arduino/arduino-cli/arduino/builder/internal/utils"
10+
"github.com/arduino/arduino-cli/arduino/globals"
11+
"github.com/arduino/go-paths-helper"
12+
"github.com/pkg/errors"
13+
)
14+
15+
func (b *Builder) compileFiles(
16+
sourceDir *paths.Path,
17+
buildPath *paths.Path,
18+
recurse bool,
19+
includes []string,
20+
) (paths.PathList, error) {
21+
validExtensions := []string{}
22+
for ext := range globals.SourceFilesValidExtensions {
23+
validExtensions = append(validExtensions, ext)
24+
}
25+
26+
sources, err := utils.FindFilesInFolder(sourceDir, recurse, validExtensions...)
27+
if err != nil {
28+
return nil, err
29+
}
30+
31+
b.Progress.AddSubSteps(len(sources))
32+
defer b.Progress.RemoveSubSteps()
33+
34+
objectFiles := paths.NewPathList()
35+
var objectFilesMux sync.Mutex
36+
if len(sources) == 0 {
37+
return objectFiles, nil
38+
}
39+
var errorsList []error
40+
var errorsMux sync.Mutex
41+
42+
queue := make(chan *paths.Path)
43+
job := func(source *paths.Path) {
44+
recipe := fmt.Sprintf("recipe%s.o.pattern", source.Ext())
45+
if !b.buildProperties.ContainsKey(recipe) {
46+
recipe = fmt.Sprintf("recipe%s.o.pattern", globals.SourceFilesValidExtensions[source.Ext()])
47+
}
48+
objectFile, err := b.compileFileWithRecipe(sourceDir, source, buildPath, includes, recipe)
49+
if err != nil {
50+
errorsMux.Lock()
51+
errorsList = append(errorsList, err)
52+
errorsMux.Unlock()
53+
} else {
54+
objectFilesMux.Lock()
55+
objectFiles.Add(objectFile)
56+
objectFilesMux.Unlock()
57+
}
58+
}
59+
60+
// Spawn jobs runners
61+
var wg sync.WaitGroup
62+
if b.jobs == 0 {
63+
b.jobs = runtime.NumCPU()
64+
}
65+
for i := 0; i < b.jobs; i++ {
66+
wg.Add(1)
67+
go func() {
68+
for source := range queue {
69+
job(source)
70+
}
71+
wg.Done()
72+
}()
73+
}
74+
75+
// Feed jobs until error or done
76+
for _, source := range sources {
77+
errorsMux.Lock()
78+
gotError := len(errorsList) > 0
79+
errorsMux.Unlock()
80+
if gotError {
81+
break
82+
}
83+
queue <- source
84+
85+
b.Progress.CompleteStep()
86+
b.Progress.PushProgress()
87+
}
88+
close(queue)
89+
wg.Wait()
90+
if len(errorsList) > 0 {
91+
// output the first error
92+
return nil, errors.WithStack(errorsList[0])
93+
}
94+
objectFiles.Sort()
95+
return objectFiles, nil
96+
}
97+
98+
// CompileFilesRecursive fixdoc
99+
func (b *Builder) compileFileWithRecipe(
100+
sourcePath *paths.Path,
101+
source *paths.Path,
102+
buildPath *paths.Path,
103+
includes []string,
104+
recipe string,
105+
) (*paths.Path, error) {
106+
properties := b.buildProperties.Clone()
107+
properties.Set("compiler.warning_flags", properties.Get("compiler.warning_flags."+b.logger.WarningsLevel()))
108+
properties.Set("includes", strings.Join(includes, " "))
109+
properties.SetPath("source_file", source)
110+
relativeSource, err := sourcePath.RelTo(source)
111+
if err != nil {
112+
return nil, errors.WithStack(err)
113+
}
114+
depsFile := buildPath.Join(relativeSource.String() + ".d")
115+
objectFile := buildPath.Join(relativeSource.String() + ".o")
116+
117+
properties.SetPath("object_file", objectFile)
118+
err = objectFile.Parent().MkdirAll()
119+
if err != nil {
120+
return nil, errors.WithStack(err)
121+
}
122+
123+
objIsUpToDate, err := utils.ObjFileIsUpToDate(source, objectFile, depsFile)
124+
if err != nil {
125+
return nil, errors.WithStack(err)
126+
}
127+
128+
command, err := utils.PrepareCommandForRecipe(properties, recipe, false)
129+
if err != nil {
130+
return nil, errors.WithStack(err)
131+
}
132+
if b.compilationDatabase != nil {
133+
b.compilationDatabase.Add(source, command)
134+
}
135+
if !objIsUpToDate && !b.onlyUpdateCompilationDatabase {
136+
// Since this compile could be multithreaded, we first capture the command output
137+
info, stdout, stderr, err := utils.ExecCommand(
138+
b.logger.Verbose(),
139+
b.logger.Stdout(),
140+
b.logger.Stderr(),
141+
command,
142+
utils.Capture,
143+
utils.Capture,
144+
)
145+
// and transfer all at once at the end...
146+
if b.logger.Verbose() {
147+
b.logger.Info(string(info))
148+
b.logger.WriteStdout(stdout)
149+
}
150+
b.logger.WriteStderr(stderr)
151+
152+
// ...and then return the error
153+
if err != nil {
154+
return nil, errors.WithStack(err)
155+
}
156+
} else if b.logger.Verbose() {
157+
if objIsUpToDate {
158+
b.logger.Info(tr("Using previously compiled file: %[1]s", objectFile))
159+
} else {
160+
b.logger.Info(tr("Skipping compile of: %[1]s", objectFile))
161+
}
162+
}
163+
164+
return objectFile, nil
165+
}

Diff for: arduino/builder/core.go

+8-14
Original file line numberDiff line numberDiff line change
@@ -71,13 +71,10 @@ func (b *Builder) compileCore() (*paths.Path, paths.PathList, error) {
7171
var err error
7272
variantObjectFiles := paths.NewPathList()
7373
if variantFolder != nil && variantFolder.IsDir() {
74-
variantObjectFiles, err = utils.CompileFilesRecursive(
75-
variantFolder, b.coreBuildPath, b.buildProperties, includes,
76-
b.onlyUpdateCompilationDatabase,
77-
b.compilationDatabase,
78-
b.jobs,
79-
b.logger,
80-
b.Progress,
74+
variantObjectFiles, err = b.compileFiles(
75+
variantFolder, b.coreBuildPath,
76+
true, /** recursive **/
77+
includes,
8178
)
8279
if err != nil {
8380
return nil, nil, errors.WithStack(err)
@@ -122,13 +119,10 @@ func (b *Builder) compileCore() (*paths.Path, paths.PathList, error) {
122119
}
123120
}
124121

125-
coreObjectFiles, err := utils.CompileFilesRecursive(
126-
coreFolder, b.coreBuildPath, b.buildProperties, includes,
127-
b.onlyUpdateCompilationDatabase,
128-
b.compilationDatabase,
129-
b.jobs,
130-
b.logger,
131-
b.Progress,
122+
coreObjectFiles, err := b.compileFiles(
123+
coreFolder, b.coreBuildPath,
124+
true, /** recursive **/
125+
includes,
132126
)
133127
if err != nil {
134128
return nil, nil, errors.WithStack(err)

0 commit comments

Comments
 (0)