-
Notifications
You must be signed in to change notification settings - Fork 47
/
raw_ostree.go
157 lines (128 loc) · 4.56 KB
/
raw_ostree.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
package manifest
import (
"fmt"
"github.com/osbuild/images/pkg/artifact"
"github.com/osbuild/images/pkg/osbuild"
"github.com/osbuild/images/pkg/platform"
)
// A RawOSTreeImage represents a raw ostree image file which can be booted in a
// hypervisor. It is created from an existing OSTreeDeployment.
type RawOSTreeImage struct {
Base
treePipeline *OSTreeDeployment
filename string
platform platform.Platform
}
func (p RawOSTreeImage) Filename() string {
return p.filename
}
func (p *RawOSTreeImage) SetFilename(filename string) {
p.filename = filename
}
func NewRawOStreeImage(buildPipeline Build, treePipeline *OSTreeDeployment, platform platform.Platform) *RawOSTreeImage {
p := &RawOSTreeImage{
Base: NewBase("image", buildPipeline),
treePipeline: treePipeline,
filename: "disk.img",
platform: platform,
}
buildPipeline.addDependent(p)
return p
}
func (p *RawOSTreeImage) getBuildPackages(Distro) []string {
packages := p.platform.GetBuildPackages()
packages = append(packages, p.platform.GetPackages()...)
packages = append(packages, p.treePipeline.PartitionTable.GetBuildPackages()...)
packages = append(packages,
"rpm-ostree",
// these should be defined on the platform
"dracut-config-generic",
"efibootmgr",
)
return packages
}
func (p *RawOSTreeImage) serialize() osbuild.Pipeline {
pipeline := p.Base.serialize()
pt := p.treePipeline.PartitionTable
if pt == nil {
panic("no partition table in live image")
}
for _, stage := range osbuild.GenImagePrepareStages(pt, p.Filename(), osbuild.PTSfdisk) {
pipeline.AddStage(stage)
}
inputName := "root-tree"
treeCopyOptions, treeCopyDevices, treeCopyMounts := osbuild.GenCopyFSTreeOptions(inputName, p.treePipeline.Name(), p.Filename(), pt)
treeCopyInputs := osbuild.NewPipelineTreeInputs(inputName, p.treePipeline.Name())
pipeline.AddStage(osbuild.NewCopyStage(treeCopyOptions, treeCopyInputs, treeCopyDevices, treeCopyMounts))
bootFiles := p.platform.GetBootFiles()
if len(bootFiles) > 0 {
// we ignore the bootcopyoptions as they contain a full tree copy instead we make our own, we *do* still want all the other
// information such as mountpoints and devices
_, bootCopyDevices, bootCopyMounts := osbuild.GenCopyFSTreeOptions(inputName, p.treePipeline.Name(), p.Filename(), pt)
bootCopyOptions := &osbuild.CopyStageOptions{}
commit := p.treePipeline.ostreeSpec
commitChecksum := commit.Checksum
bootCopyInputs := osbuild.OSTreeCheckoutInputs{
"ostree-tree": *osbuild.NewOSTreeCheckoutInput("org.osbuild.source", commitChecksum),
}
// Find the FS root mount name to use as the destination root
// for the target when copying the boot files.
var fsRootMntName string
for _, mnt := range bootCopyMounts {
if mnt.Target == "/" {
fsRootMntName = mnt.Name
break
}
}
if fsRootMntName == "" {
panic("no mount found for the filesystem root")
}
for _, paths := range bootFiles {
bootCopyOptions.Paths = append(bootCopyOptions.Paths, osbuild.CopyStagePath{
From: fmt.Sprintf("input://ostree-tree/%s%s", commitChecksum, paths[0]),
To: fmt.Sprintf("mount://%s%s", fsRootMntName, paths[1]),
})
}
pipeline.AddStage(osbuild.NewCopyStage(bootCopyOptions, bootCopyInputs, bootCopyDevices, bootCopyMounts))
}
for _, stage := range osbuild.GenImageFinishStages(pt, p.Filename()) {
pipeline.AddStage(stage)
}
if p.treePipeline.UseBootupd {
p.addBootupdStage(&pipeline)
} else {
p.maybeAddGrubInstStage(&pipeline)
}
return pipeline
}
func (p *RawOSTreeImage) addBootupdStage(pipeline *osbuild.Pipeline) {
pt := p.treePipeline.PartitionTable
treeBootupdDevices, treeBootupdMounts := osbuild.GenBootupdDevicesMounts(p.Filename(), pt)
opts := &osbuild.BootupdStageOptions{
Deployment: &osbuild.OSTreeDeployment{
OSName: p.treePipeline.osName,
Ref: p.treePipeline.ref,
},
StaticConfigs: true,
}
if legacyBios := p.treePipeline.platform.GetBIOSPlatform(); legacyBios != "" {
opts.Bios = &osbuild.BootupdStageOptionsBios{
Device: "disk",
}
}
bootupd, err := osbuild.NewBootupdStage(opts, treeBootupdDevices, treeBootupdMounts)
if err != nil {
panic(err)
}
pipeline.AddStage(bootupd)
}
func (p *RawOSTreeImage) maybeAddGrubInstStage(pipeline *osbuild.Pipeline) {
pt := p.treePipeline.PartitionTable
if grubLegacy := p.treePipeline.platform.GetBIOSPlatform(); grubLegacy != "" {
pipeline.AddStage(osbuild.NewGrub2InstStage(osbuild.NewGrub2InstStageOption(p.Filename(), pt, grubLegacy)))
}
}
func (p *RawOSTreeImage) Export() *artifact.Artifact {
p.Base.export = true
return artifact.New(p.Name(), p.Filename(), nil)
}