blob: 0a63d9294c0c1d1961eec78d9b2213b07685eecb [file] [log] [blame]
Alexander Hansen1ba6e1c2024-11-26 11:16:44 +01001#include "spi_device_code_updater.hpp"
2
3#include <phosphor-logging/lg2.hpp>
4#include <sdbusplus/asio/connection.hpp>
5#include <sdbusplus/asio/object_server.hpp>
6#include <sdbusplus/async.hpp>
7#include <sdbusplus/server.hpp>
8
9#include <fstream>
10#include <iostream>
11
12// implementing the design
13// https://github.com/openbmc/docs/blob/377ed14df4913010752ee2faff994a50e12a6316/designs/code-update.md
14
15// NOLINTNEXTLINE
16sdbusplus::async::task<> startManualUpdate(sdbusplus::async::context& ctx,
17 SPIDeviceCodeUpdater& spidcu,
18 const std::string& imageFilename)
19{
20 if (spidcu.devices.empty())
21 {
22 lg2::error("no device available for manual update");
23 co_return;
24 }
25
26 const std::unique_ptr<Device>& device = *spidcu.devices.begin();
27
28 std::ifstream file(imageFilename, std::ios::binary | std::ios::ate);
29
30 if (!file.good())
31 {
32 lg2::error("error opening file {FILENAME}", "FILENAME", imageFilename);
33 co_return;
34 }
35
36 std::streamsize size = file.tellg();
37 file.seekg(0, std::ios::beg);
38
39 auto buffer = std::make_unique<uint8_t[]>(size);
40
41 if (!file.read(reinterpret_cast<char*>(buffer.get()), size))
42 {
43 throw std::runtime_error("Error reading file: " + imageFilename);
44 }
45
46 // TODO: find the proper object path here
47 auto sap =
48 std::make_unique<SoftwareActivationProgress>(ctx, "/dummyActivation");
49
50 co_await device->updateDevice(buffer.get(), size, sap);
51
52 co_return;
53}
54
55// NOLINTNEXTLINE
56sdbusplus::async::task<> start(sdbusplus::async::context& ctx,
57 SPIDeviceCodeUpdater& spidcu, bool manual,
58 const std::string& imageFilename)
59{
60 std::vector<std::string> configIntfs = {
61 "xyz.openbmc_project.Configuration." + configTypeSPIDevice};
62
63 co_await spidcu.getInitialConfiguration(configIntfs);
64
65 if (manual)
66 {
67 co_await startManualUpdate(ctx, spidcu, imageFilename);
68 }
69
70 co_return;
71}
72
73void printHelpText()
74{
75 std::cout << "--help : print help" << std::endl;
76 std::cout << "--manual : start a manual update" << std::endl;
77 std::cout << "--image <filename> : filename for manual update"
78 << std::endl;
79}
80
81int main(int argc, char* argv[])
82{
83 // getting a really unspecific error from clang-tidy here
84 // about an uninitialized / garbage branch. Happy to discuss.
85
86 // NOLINTBEGIN
87
88 sdbusplus::async::context ctx;
89
90 bool manualUpdate = false;
91 bool printHelp = false;
92 bool dryRun = false;
93 bool debug = false;
94 std::string imageFilename = "";
95
96 for (int i = 1; i < argc; i++)
97 {
98 std::string arg = std::string(argv[i]);
99 if (arg == "--manual")
100 {
101 manualUpdate = true;
102 }
103 if (arg == "--image" && i < argc - 1)
104 {
105 imageFilename = std::string(argv[i + 1]);
106 i++;
107 }
108 if (arg == "--help")
109 {
110 printHelp = true;
111 }
112 if (arg == "--dryrun")
113 {
114 dryRun = true;
115 }
116 if (arg == "-debug")
117 {
118 debug = true;
119 }
120 }
121
122 if (printHelp)
123 {
124 printHelpText();
125 }
126
127 SPIDeviceCodeUpdater spidcu(ctx, dryRun, debug);
128
129 ctx.spawn(start(ctx, spidcu, manualUpdate, imageFilename));
130
131 ctx.run();
132
133 // NOLINTEND
134
135 return 0;
136}