treewide: introduce osbase package and move things around

All except localregistry moved from metropolis/pkg to osbase,
localregistry moved to metropolis/test as its only used there anyway.

Change-Id: If1a4bf377364bef0ac23169e1b90379c71b06d72
Reviewed-on: https://review.monogon.dev/c/monogon/+/3079
Tested-by: Jenkins CI
Reviewed-by: Serge Bazanski <serge@monogon.tech>
diff --git a/osbase/kmod/meta.go b/osbase/kmod/meta.go
new file mode 100644
index 0000000..c005a7c
--- /dev/null
+++ b/osbase/kmod/meta.go
@@ -0,0 +1,50 @@
+package kmod
+
+import (
+	"fmt"
+	"log"
+
+	kmodpb "source.monogon.dev/osbase/kmod/spec"
+)
+
+// MakeMetaFromModuleInfo is a more flexible alternative to MakeMeta. It only
+// relies on ModuleInfo structures, additional processing can be done outside of
+// this function. It does however require that for dynamically-loaded modules
+// the "path" key is set to the path of the .ko file relative to the module
+// root.
+func MakeMetaFromModuleInfo(modinfos []ModuleInfo) (*kmodpb.Meta, error) {
+	modIndices := make(map[string]uint32)
+	modInfoMap := make(map[string]ModuleInfo)
+	var meta kmodpb.Meta
+	meta.ModuleDeviceMatches = &kmodpb.RadixNode{
+		Type: kmodpb.RadixNode_ROOT,
+	}
+	var i uint32
+	for _, m := range modinfos {
+		meta.Modules = append(meta.Modules, &kmodpb.Module{
+			Name: m.Name(),
+			Path: m.Get("path"),
+		})
+		for _, p := range m.Aliases() {
+			if m.Get("path") == "" {
+				// Ignore built-in modaliases as they do not need to be loaded.
+				continue
+			}
+			if err := AddPattern(meta.ModuleDeviceMatches, p, i); err != nil {
+				return nil, fmt.Errorf("failed adding device match %q: %w", p, err)
+			}
+		}
+		modIndices[m.Name()] = i
+		modInfoMap[m.Name()] = m
+		i++
+	}
+	for _, m := range meta.Modules {
+		for _, dep := range modInfoMap[m.Name].GetDependencies() {
+			if _, ok := modIndices[dep]; !ok {
+				log.Printf("Unknown dependency %q for module %q", modInfoMap[m.Name].GetDependencies(), m.Name)
+			}
+			m.Depends = append(m.Depends, modIndices[dep])
+		}
+	}
+	return &meta, nil
+}