flowey_lib_hvlite/_jobs/
check_openvmm_hcl_size.rs1use crate::artifact_openhcl_igvm_from_recipe_extras;
7use crate::build_openhcl_igvm_from_recipe;
8use crate::build_openhcl_igvm_from_recipe::OpenhclIgvmRecipe;
9use crate::build_openvmm_hcl;
10use crate::build_openvmm_hcl::OpenvmmHclBuildParams;
11use crate::build_openvmm_hcl::OpenvmmHclBuildProfile::OpenvmmHclShip;
12use crate::common::CommonArch;
13use crate::common::CommonTriple;
14use flowey::node::prelude::*;
15use flowey_lib_common::download_gh_artifact;
16use flowey_lib_common::gh_workflow_id;
17use flowey_lib_common::git_merge_commit;
18
19flowey_request! {
20 pub struct Request {
21 pub target: CommonTriple,
22 pub done: WriteVar<SideEffect>,
23 pub pipeline_name: String,
24 pub job_name: String,
25 }
26}
27
28new_simple_flow_node!(struct Node);
29
30impl SimpleFlowNode for Node {
31 type Request = Request;
32
33 fn imports(ctx: &mut ImportCtx<'_>) {
34 ctx.import::<crate::build_xtask::Node>();
35 ctx.import::<crate::git_checkout_openvmm_repo::Node>();
36 ctx.import::<download_gh_artifact::Node>();
37 ctx.import::<git_merge_commit::Node>();
38 ctx.import::<gh_workflow_id::Node>();
39 ctx.import::<build_openhcl_igvm_from_recipe::Node>();
40 ctx.import::<build_openvmm_hcl::Node>();
41 ctx.import::<artifact_openhcl_igvm_from_recipe_extras::publish::Node>();
42 }
43
44 fn process_request(request: Self::Request, ctx: &mut NodeCtx<'_>) -> anyhow::Result<()> {
45 let Request {
46 target,
47 done,
48 pipeline_name,
49 job_name,
50 } = request;
51
52 let xtask_target = CommonTriple::Common {
53 arch: ctx.arch().try_into()?,
54 platform: ctx.platform().try_into()?,
55 };
56
57 let xtask = ctx.reqv(|v| crate::build_xtask::Request {
58 target: xtask_target,
59 xtask: v,
60 });
61 let openvmm_repo_path = ctx.reqv(crate::git_checkout_openvmm_repo::req::GetRepoDir);
62
63 let recipe = match target.common_arch().unwrap() {
64 CommonArch::X86_64 => OpenhclIgvmRecipe::X64,
65 CommonArch::Aarch64 => OpenhclIgvmRecipe::Aarch64,
66 }
67 .recipe_details(true);
68
69 let built_openvmm_hcl = ctx.reqv(|v| build_openvmm_hcl::Request {
70 build_params: OpenvmmHclBuildParams {
71 target: target.clone(),
72 profile: OpenvmmHclShip,
73 features: recipe.openvmm_hcl_features,
74 no_split_dbg_info: false,
75 max_trace_level: recipe.max_trace_level,
76 },
77 openvmm_hcl_output: v,
78 });
79
80 let file_name = match target.common_arch().unwrap() {
81 CommonArch::X86_64 => "x64-openhcl-baseline",
82 CommonArch::Aarch64 => "aarch64-openhcl-baseline",
83 };
84
85 let merge_commit = ctx.reqv(|v| git_merge_commit::Request {
86 repo_path: openvmm_repo_path.clone(),
87 merge_commit: v,
88 base_branch: "main".into(),
89 });
90
91 let merge_run = ctx.reqv(|v| {
92 gh_workflow_id::Request::WithStatusAndJob(gh_workflow_id::QueryWithStatusAndJob {
93 params: gh_workflow_id::WorkflowQueryParams {
94 github_commit_hash: merge_commit,
95 repo_path: openvmm_repo_path.clone(),
96 pipeline_name,
97 gh_workflow: v,
98 },
99 gh_run_status: gh_workflow_id::GhRunStatus::Completed,
100 gh_run_job_name: job_name,
101 })
102 });
103
104 let run_id = merge_run.map(ctx, |r| r.id);
105 let merge_head_artifact = ctx.reqv(|old_openhcl| download_gh_artifact::Request {
106 repo_owner: "microsoft".into(),
107 repo_name: "openvmm".into(),
108 file_name: file_name.into(),
109 path: old_openhcl,
110 run_id,
111 });
112
113 let publish_artifact = if ctx.backend() == FlowBackend::Github {
119 let dir = ctx.emit_rust_stepv("collect openvmm_hcl files for analysis", |ctx| {
120 let built_openvmm_hcl = built_openvmm_hcl.clone().claim(ctx);
121 move |rt| {
122 let built_openvmm_hcl = rt.read(built_openvmm_hcl);
123 let path = Path::new("artifact");
124 fs_err::create_dir_all(path)?;
125 fs_err::copy(built_openvmm_hcl.bin, path.join("openvmm_hcl"))?;
126 if let Some(dbg) = built_openvmm_hcl.dbg {
127 fs_err::copy(dbg, path.join("openvmm_hcl.dbg"))?;
128 }
129 Ok(path
130 .absolute()?
131 .into_os_string()
132 .into_string()
133 .ok()
134 .unwrap())
135 }
136 });
137 let name = format!(
138 "{}_openvmm_hcl_for_size_analysis",
139 target.common_arch().unwrap().as_arch()
140 );
141 Some(
142 ctx.emit_gh_step(
143 "publish openvmm_hcl for analysis",
144 "actions/upload-artifact@v7",
145 )
146 .with("name", name)
147 .with("path", dir)
148 .finish(ctx),
149 )
150 } else {
151 None
152 };
153
154 let comparison = ctx.emit_rust_step("binary size comparison", |ctx| {
155 let _publish_artifact = publish_artifact.claim(ctx);
157 let xtask = xtask.claim(ctx);
158 let openvmm_repo_path = openvmm_repo_path.claim(ctx);
159 let old_openhcl = merge_head_artifact.claim(ctx);
160 let new_openhcl = built_openvmm_hcl.claim(ctx);
161 let merge_run = merge_run.claim(ctx);
162
163 move |rt| {
164 let xtask = match rt.read(xtask) {
165 crate::build_xtask::XtaskOutput::LinuxBin { bin, .. } => bin,
166 crate::build_xtask::XtaskOutput::WindowsBin { exe, .. } => exe,
167 };
168
169 let old_openhcl = rt.read(old_openhcl);
170 let new_openhcl = rt.read(new_openhcl);
171 let merge_run = rt.read(merge_run);
172
173 let old_path = old_openhcl.join(file_name).join("openhcl");
174 let new_path = new_openhcl.bin;
175
176 println!(
177 "comparing HEAD to merge commit {} and workflow {}",
178 merge_run.commit, merge_run.id
179 );
180
181 let path = rt.read(openvmm_repo_path);
182 rt.sh.change_dir(path);
183 flowey::shell_cmd!(
184 rt,
185 "{xtask} verify-size --original {old_path} --new {new_path}"
186 )
187 .run()?;
188
189 Ok(())
190 }
191 });
192
193 ctx.emit_side_effect_step(vec![comparison], [done]);
194
195 Ok(())
196 }
197}