@@ -33,6 +33,7 @@ import (
3333 "os/exec"
3434 "path"
3535 "path/filepath"
36+ "regexp"
3637 "runtime"
3738 "strings"
3839 "time"
@@ -41,7 +42,6 @@ import (
4142
4243 "github.com/arduino/arduino-create-agent/utilities"
4344 "github.com/blang/semver"
44- "github.com/xrash/smetrics"
4545)
4646
4747type system struct {
@@ -64,15 +64,21 @@ type index struct {
6464 } `json:"packages"`
6565}
6666
67- var systems = map [string ]string {
68- "linuxamd64" : "x86_64-linux-gnu" ,
69- "linux386" : "i686-linux-gnu" ,
70- "darwinamd64" : "i686-apple-darwin" ,
71- "darwinarm64" : "arm64-apple-darwin" ,
72- "windows386" : "i686-mingw32" ,
73- "windowsamd64" : "x86_64-mingw32" ,
74- "linuxarm" : "arm-linux-gnueabihf" ,
75- }
67+ // Source: https://github.com/arduino/arduino-cli/blob/master/arduino/cores/tools.go#L129-L142
68+ var (
69+ regexpLinuxArm = regexp .MustCompile ("arm.*-linux-gnueabihf" )
70+ regexpLinuxArm64 = regexp .MustCompile ("(aarch64|arm64)-linux-gnu" )
71+ regexpLinux64 = regexp .MustCompile ("x86_64-.*linux-gnu" )
72+ regexpLinux32 = regexp .MustCompile ("i[3456]86-.*linux-gnu" )
73+ regexpWindows32 = regexp .MustCompile ("i[3456]86-.*(mingw32|cygwin)" )
74+ regexpWindows64 = regexp .MustCompile ("(amd64|x86_64)-.*(mingw32|cygwin)" )
75+ regexpMac64 = regexp .MustCompile ("x86_64-apple-darwin.*" )
76+ regexpMac32 = regexp .MustCompile ("i[3456]86-apple-darwin.*" )
77+ regexpMacArm64 = regexp .MustCompile ("arm64-apple-darwin.*" )
78+ regexpFreeBSDArm = regexp .MustCompile ("arm.*-freebsd[0-9]*" )
79+ regexpFreeBSD32 = regexp .MustCompile ("i?[3456]86-freebsd[0-9]*" )
80+ regexpFreeBSD64 = regexp .MustCompile ("amd64-freebsd[0-9]*" )
81+ )
7682
7783// public vars to allow override in the tests
7884var (
@@ -299,6 +305,64 @@ func (t *Tools) Download(pack, name, version, behaviour string) error {
299305 return t .writeMap ()
300306}
301307
308+ // Source: https://github.com/arduino/arduino-cli/blob/master/arduino/cores/tools.go#L144-L176
309+ func (s * system ) isExactMatchWith (osName , osArch string ) bool {
310+ if s .Host == "all" {
311+ return true
312+ }
313+
314+ switch osName + "," + osArch {
315+ case "linux,arm" , "linux,armbe" :
316+ return regexpLinuxArm .MatchString (s .Host )
317+ case "linux,arm64" :
318+ return regexpLinuxArm64 .MatchString (s .Host )
319+ case "linux,amd64" :
320+ return regexpLinux64 .MatchString (s .Host )
321+ case "linux,386" :
322+ return regexpLinux32 .MatchString (s .Host )
323+ case "windows,386" :
324+ return regexpWindows32 .MatchString (s .Host )
325+ case "windows,amd64" :
326+ return regexpWindows64 .MatchString (s .Host )
327+ case "darwin,arm64" :
328+ return regexpMacArm64 .MatchString (s .Host )
329+ case "darwin,amd64" :
330+ return regexpMac64 .MatchString (s .Host )
331+ case "darwin,386" :
332+ return regexpMac32 .MatchString (s .Host )
333+ case "freebsd,arm" :
334+ return regexpFreeBSDArm .MatchString (s .Host )
335+ case "freebsd,386" :
336+ return regexpFreeBSD32 .MatchString (s .Host )
337+ case "freebsd,amd64" :
338+ return regexpFreeBSD64 .MatchString (s .Host )
339+ }
340+ return false
341+ }
342+
343+ // Source: https://github.com/arduino/arduino-cli/blob/master/arduino/cores/tools.go#L178-L198
344+ func (s * system ) isCompatibleWith (osName , osArch string ) (bool , int ) {
345+ if s .isExactMatchWith (osName , osArch ) {
346+ return true , 1000
347+ }
348+
349+ switch osName + "," + osArch {
350+ case "windows,amd64" :
351+ return regexpWindows32 .MatchString (s .Host ), 10
352+ case "darwin,amd64" :
353+ return regexpMac32 .MatchString (s .Host ), 10
354+ case "darwin,arm64" :
355+ // Compatibility guaranteed through Rosetta emulation
356+ if regexpMac64 .MatchString (s .Host ) {
357+ // Prefer amd64 version if available
358+ return true , 20
359+ }
360+ return regexpMac32 .MatchString (s .Host ), 10
361+ }
362+
363+ return false , 0
364+ }
365+
302366func findTool (pack , name , version string , data index ) (tool , system ) {
303367 var correctTool tool
304368 correctTool .Version = "0.0"
@@ -325,11 +389,10 @@ func findTool(pack, name, version string, data index) (tool, system) {
325389
326390 // Find the url based on system
327391 var correctSystem system
328- maxSimilarity := 0.7
392+ maxSimilarity := - 1
329393
330394 for _ , s := range correctTool .Systems {
331- similarity := smetrics .Jaro (s .Host , systems [OS + Arch ])
332- if similarity > maxSimilarity {
395+ if comp , similarity := s .isCompatibleWith (OS , Arch ); comp && similarity > maxSimilarity {
333396 correctSystem = s
334397 maxSimilarity = similarity
335398 }
0 commit comments