@@ -528,8 +528,8 @@ type manifestParseContext struct {
528
528
529
529
prepareLibs []* prepareLibsEntry
530
530
531
- mtx * sync.Mutex
532
- libsByLoc * libByLocMap
531
+ mtx * sync.Mutex
532
+ libsByName * libByNameMap
533
533
}
534
534
535
535
// readManifestWithLibs reads manifest from the provided dir, "expands" all
@@ -568,8 +568,8 @@ func readManifestWithLibs(
568
568
569
569
cbs : cbs ,
570
570
571
- mtx : & sync.Mutex {},
572
- libsByLoc : newLibByLocMap (),
571
+ mtx : & sync.Mutex {},
572
+ libsByName : newLibByNameMap (),
573
573
}
574
574
575
575
manifest , mtime , err := readManifestWithLibs2 (dir , pc )
@@ -909,14 +909,14 @@ func prepareLib(
909
909
return
910
910
}
911
911
912
- ls := pc .libsByLoc .AddOrFetchAndLock (m .Location )
912
+ ls := pc .libsByName .AddOrFetchAndLock (m .Name )
913
913
defer ls .mtx .Unlock ()
914
914
if ls .Lib != nil {
915
915
prepareLibReencounter (parentNodeName , manifest , pc , ls .Lib , m )
916
916
return
917
917
}
918
918
919
- ourutil .Freportf (pc .logWriter , "Reading lib at %q..." , m .Location )
919
+ ourutil .Freportf (pc .logWriter , "Reading lib %q at %q..." , m . Name , m .Location )
920
920
921
921
libLocalDir , err := pc .cbs .ComponentProvider .GetLibLocalPath (
922
922
m , pc .rootAppDir , pc .appManifest .LibsVersion , manifest .Platform ,
@@ -947,22 +947,73 @@ func prepareLib(
947
947
return
948
948
}
949
949
950
- // The library can explicitly set its name in its manifest. Also its
951
- // name can be explicitly set in the referring manifest. Either
952
- // separately is fine. None is fine too (the name defaults to the
953
- // location basename). However if both are used, treat a mismatch as an
954
- // error (building without one of the two names in place is guaranteed
955
- // to fail, and is likely with both too).
950
+ // The name of a library can be explicitly set in its manifest and/or in the
951
+ // referring manifest. Barring that, the name defaults to the location
952
+ // basename.
953
+ //
954
+ // The library code is hardwired to the right name via at least its
955
+ // mgos_*_init() symbol. The code using the library may also be via, e.g.,
956
+ // HAVE_* variables.
957
+ //
958
+ // The building process uses the library name for library deduplication and
959
+ // overriding.
960
+ //
961
+ // The location being `.../foo', the library name in use is:
962
+ //
963
+ // (#) lib mos.yml ref mos.yml name in use
964
+ // --------------------------------------
965
+ // (1) (none) (none) foo
966
+ // (2) (none) foo foo
967
+ // (3) (none) bar bar
968
+ // (4) foo (none) foo
969
+ // (5) foo foo foo
970
+ // (6) foo bar (ERROR)
971
+ // (7) bar (none) (ERROR)
972
+ // (8) bar foo (ERROR)
973
+ // (9) bar bar bar
974
+ //
975
+ // Rationales per (#) case:
976
+ // - (1) The most typical use case.
977
+ // - (2, 4, 5) Effectively no new information atop the location basename.
978
+ // - (3) The handy use case of, e.g., .../foo-test1, .../foo-test2 copies
979
+ // adjacent to one another and/or the original .../foo.
980
+ // - (6) If `foo' were correct here, the same problem as in (7) would apply.
981
+ // If `bar' were correct, then `foo' in lib mos.yml would produce erroneous
982
+ // results via any automation/content generation applied to individual
983
+ // libraries outside their usages.
984
+ // - (7) The name set via the library manifest must be replicated in the
985
+ // referring manifest. Otherwise, if this library is overridden while this
986
+ // particular location isn't accessible from the building environment,
987
+ // library deduplication/overriding by name can't obviate the need to read
988
+ // the inaccessible manifest.
989
+ // - (8) This is (6) with the names swapped around.
990
+ // - (9) A location-independently named library. E.g., Github repositories
991
+ // .../mgos-foo, .../mgos-bar with libraries next to repositories unrelated
992
+ // to Mongoose OS.
993
+ //
994
+ // At this point, libRefName == `ref mos.yml' name above; libManifest.name ==
995
+ // `lib mos.yml' name; m.Name == libRefName || library location basename.
996
+ // After validation, m.Name will be the library `name to use' above.
956
997
if libManifest .Name != "" {
957
- if libRefName != "" && libRefName != libManifest .Name {
998
+ if libRefName != "" && libRefName != libManifest .Name { // (6, 8) above
958
999
lpres <- libPrepareResult {
959
1000
err : fmt .Errorf ("Library %q at %q is referred to as %q from %q" ,
960
1001
libManifest .Name , m .Location ,
961
1002
libRefName , manifest .Origin ),
962
1003
}
963
1004
return
964
1005
}
965
- m .Name = libManifest .Name
1006
+ if libRefName == "" && m .Name != libManifest .Name { // (7) above
1007
+ lpres <- libPrepareResult {
1008
+ err : fmt .Errorf ("Library %q at %q must be referred to as %q from %q" ,
1009
+ libManifest .Name , m .Location ,
1010
+ libManifest .Name , manifest .Origin ),
1011
+ }
1012
+ return
1013
+ }
1014
+ }
1015
+ if libRefName != "" && m .Name != libRefName { // (3, 9) above
1016
+ m .Name = libRefName
966
1017
}
967
1018
name , err := m .GetName ()
968
1019
if err != nil {
0 commit comments