1616package phases
1717
1818import (
19+ "bytes"
20+ "io"
1921 "strings"
2022
2123 "github.com/arduino/arduino-cli/arduino/builder"
2224 "github.com/arduino/arduino-cli/arduino/builder/utils"
2325 f "github.com/arduino/arduino-cli/internal/algorithms"
24- "github.com/arduino/arduino-cli/legacy/builder/constants"
25- "github.com/arduino/arduino-cli/legacy/builder/types"
2626 "github.com/arduino/go-paths-helper"
2727 "github.com/arduino/go-properties-orderedmap"
2828 "github.com/pkg/errors"
2929)
3030
31- type Linker struct {}
32-
33- func (s * Linker ) Run (ctx * types.Context ) error {
34- if ctx .OnlyUpdateCompilationDatabase {
35- if ctx .Verbose {
36- ctx .Info (tr ("Skip linking of final executable." ))
31+ func Linker (
32+ onlyUpdateCompilationDatabase , verbose bool ,
33+ sketchObjectFiles , librariesObjectFiles , coreObjectsFiles paths.PathList ,
34+ coreArchiveFilePath , buildPath * paths.Path ,
35+ buildProperties * properties.Map ,
36+ stdoutWriter , stderrWriter io.Writer ,
37+ warningsLevel string ,
38+ ) ([]byte , error ) {
39+ verboseInfo := & bytes.Buffer {}
40+ if onlyUpdateCompilationDatabase {
41+ if verbose {
42+ verboseInfo .WriteString (tr ("Skip linking of final executable." ))
3743 }
38- return nil
44+ return verboseInfo . Bytes (), nil
3945 }
4046
41- objectFilesSketch := ctx . SketchObjectFiles
42- objectFilesLibraries := ctx . LibrariesObjectFiles
43- objectFilesCore := ctx . CoreObjectsFiles
47+ objectFilesSketch := sketchObjectFiles
48+ objectFilesLibraries := librariesObjectFiles
49+ objectFilesCore := coreObjectsFiles
4450
4551 objectFiles := paths .NewPathList ()
4652 objectFiles .AddAll (objectFilesSketch )
4753 objectFiles .AddAll (objectFilesLibraries )
4854 objectFiles .AddAll (objectFilesCore )
4955
50- coreArchiveFilePath := ctx .CoreArchiveFilePath
51- buildPath := ctx .BuildPath
5256 coreDotARelPath , err := buildPath .RelTo (coreArchiveFilePath )
5357 if err != nil {
54- return errors .WithStack (err )
58+ return nil , errors .WithStack (err )
5559 }
5660
57- buildProperties := ctx .BuildProperties
58-
59- err = link (ctx , objectFiles , coreDotARelPath , coreArchiveFilePath , buildProperties )
61+ verboseInfoOut , err := link (
62+ objectFiles , coreDotARelPath , coreArchiveFilePath , buildProperties ,
63+ verbose , stdoutWriter , stderrWriter , warningsLevel ,
64+ )
65+ verboseInfo .Write (verboseInfoOut )
6066 if err != nil {
61- return errors .WithStack (err )
67+ return verboseInfo . Bytes (), errors .WithStack (err )
6268 }
6369
64- return nil
70+ return verboseInfo . Bytes (), nil
6571}
6672
67- func link (ctx * types.Context , objectFiles paths.PathList , coreDotARelPath * paths.Path , coreArchiveFilePath * paths.Path , buildProperties * properties.Map ) error {
73+ func link (
74+ objectFiles paths.PathList , coreDotARelPath * paths.Path , coreArchiveFilePath * paths.Path , buildProperties * properties.Map ,
75+ verbose bool ,
76+ stdoutWriter , stderrWriter io.Writer ,
77+ warningsLevel string ,
78+ ) ([]byte , error ) {
79+ verboseBuffer := & bytes.Buffer {}
80+ wrapWithDoubleQuotes := func (value string ) string { return "\" " + value + "\" " }
6881 objectFileList := strings .Join (f .Map (objectFiles .AsStrings (), wrapWithDoubleQuotes ), " " )
6982
7083 // If command line length is too big (> 30000 chars), try to collect the object files into archives
@@ -95,14 +108,14 @@ func link(ctx *types.Context, objectFiles paths.PathList, coreDotARelPath *paths
95108
96109 command , err := utils .PrepareCommandForRecipe (properties , builder .RecipeARPattern , false )
97110 if err != nil {
98- return errors .WithStack (err )
111+ return nil , errors .WithStack (err )
99112 }
100113
101- if verboseInfo , _ , _ , err := utils .ExecCommand (ctx . Verbose , ctx . Stdout , ctx . Stderr , command , utils .ShowIfVerbose /* stdout */ , utils .Show /* stderr */ ); err != nil {
102- if ctx . Verbose {
103- ctx . Info (string (verboseInfo ))
114+ if verboseInfo , _ , _ , err := utils .ExecCommand (verbose , stdoutWriter , stderrWriter , command , utils .ShowIfVerbose /* stdout */ , utils .Show /* stderr */ ); err != nil {
115+ if verbose {
116+ verboseBuffer . WriteString (string (verboseInfo ))
104117 }
105- return errors .WithStack (err )
118+ return verboseBuffer . Bytes (), errors .WithStack (err )
106119 }
107120 }
108121
@@ -111,24 +124,20 @@ func link(ctx *types.Context, objectFiles paths.PathList, coreDotARelPath *paths
111124 }
112125
113126 properties := buildProperties .Clone ()
114- properties .Set (constants . BUILD_PROPERTIES_COMPILER_C_ELF_FLAGS , properties .Get (constants . BUILD_PROPERTIES_COMPILER_C_ELF_FLAGS ))
115- properties .Set (builder .BuildPropertiesCompilerWarningFlags , properties .Get (builder .BuildPropertiesCompilerWarningFlags + "." + ctx . WarningsLevel ))
127+ properties .Set ("compiler.c.elf.flags" , properties .Get ("compiler.c.elf.flags" ))
128+ properties .Set (builder .BuildPropertiesCompilerWarningFlags , properties .Get (builder .BuildPropertiesCompilerWarningFlags + "." + warningsLevel ))
116129 properties .Set (builder .BuildPropertiesArchiveFile , coreDotARelPath .String ())
117130 properties .Set (builder .BuildPropertiesArchiveFilePath , coreArchiveFilePath .String ())
118131 properties .Set ("object_files" , objectFileList )
119132
120- command , err := utils .PrepareCommandForRecipe (properties , constants . RECIPE_C_COMBINE_PATTERN , false )
133+ command , err := utils .PrepareCommandForRecipe (properties , "recipe.c.combine.pattern" , false )
121134 if err != nil {
122- return err
135+ return verboseBuffer . Bytes (), err
123136 }
124137
125- verboseInfo , _ , _ , err := utils .ExecCommand (ctx . Verbose , ctx . Stdout , ctx . Stderr , command , utils .ShowIfVerbose /* stdout */ , utils .Show /* stderr */ )
126- if ctx . Verbose {
127- ctx . Info (string (verboseInfo ))
138+ verboseInfo , _ , _ , err := utils .ExecCommand (verbose , stdoutWriter , stderrWriter , command , utils .ShowIfVerbose /* stdout */ , utils .Show /* stderr */ )
139+ if verbose {
140+ verboseBuffer . WriteString (string (verboseInfo ))
128141 }
129- return err
130- }
131-
132- func wrapWithDoubleQuotes (value string ) string {
133- return "\" " + value + "\" "
142+ return verboseBuffer .Bytes (), err
134143}
0 commit comments