blob: 33281ee39a5164a9424a3f5ef5aa1caf1819e02e [file] [log] [blame]
Darin Petkova4a8a8c2010-07-15 22:21:12 -07001// Copyright (c) 2010 The Chromium OS Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "update_engine/omaha_request_params.h"
6
7#include <errno.h>
8#include <fcntl.h>
9#include <sys/utsname.h>
10
11#include <map>
12#include <string>
13
14#include "base/string_util.h"
15#include "update_engine/simple_key_value_store.h"
16#include "update_engine/utils.h"
17
18using std::map;
19using std::string;
20
21namespace {
22const string OmahaIdPath() {
23 return string(chromeos_update_engine::utils::kStatefulPartition) +
24 "/etc/omaha_id";
25}
26} // namespace {}
27
28namespace chromeos_update_engine {
29
Darin Petkov5a7f5652010-07-22 21:40:09 -070030const char* const OmahaRequestParams::kAppId(
31 "{87efface-864d-49a5-9bb3-4b050a7c227a}");
32const char* const OmahaRequestParams::kOsPlatform("Chrome OS");
33const char* const OmahaRequestParams::kOsVersion("Indy");
34const char* const OmahaRequestParams::kUpdateUrl(
35 "https://tools.google.com/service/update2");
36
37bool OmahaRequestDeviceParams::Init(const std::string& in_app_version,
38 const std::string& in_update_url) {
Darin Petkova4a8a8c2010-07-15 22:21:12 -070039 TEST_AND_RETURN_FALSE(GetMachineId(&machine_id));
40 user_id = machine_id;
41 os_platform = OmahaRequestParams::kOsPlatform;
42 os_version = OmahaRequestParams::kOsVersion;
Darin Petkov5a7f5652010-07-22 21:40:09 -070043 app_version = in_app_version.empty() ?
44 GetLsbValue("CHROMEOS_RELEASE_VERSION", "") : in_app_version;
Darin Petkova4a8a8c2010-07-15 22:21:12 -070045 os_sp = app_version + "_" + GetMachineType();
46 os_board = GetLsbValue("CHROMEOS_RELEASE_BOARD", "");
47 app_id = OmahaRequestParams::kAppId;
48 app_lang = "en-US";
49 app_track = GetLsbValue("CHROMEOS_RELEASE_TRACK", "");
Andrew de los Reyes3f0303a2010-07-15 22:35:35 -070050 struct stat stbuf;
Darin Petkov5a7f5652010-07-22 21:40:09 -070051
Andrew de los Reyes3f0303a2010-07-15 22:35:35 -070052 // Deltas are only okay if the /.nodelta file does not exist.
53 // If we don't know (i.e. stat() returns some unexpected error),
54 // then err on the side of caution and say deltas are not okay
55 delta_okay = (stat((root_ + "/.nodelta").c_str(), &stbuf) < 0) &&
56 (errno == ENOENT);
57
Darin Petkov5a7f5652010-07-22 21:40:09 -070058 update_url = in_update_url.empty() ?
59 GetLsbValue("CHROMEOS_AUSERVER", OmahaRequestParams::kUpdateUrl) :
60 in_update_url;
Darin Petkova4a8a8c2010-07-15 22:21:12 -070061 return true;
62}
63
64namespace {
65const size_t kGuidDataByteLength = 128 / 8;
66const string::size_type kGuidStringLength = 38;
67// Formats 16 bytes (128 bits) of data as a GUID:
68// "{XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX}" where X is a hex digit
69string GuidFromData(const unsigned char data[kGuidDataByteLength]) {
70 return StringPrintf(
71 "{%02X%02X%02X%02X-%02X%02X-%02X%02X-%02X%02X-%02X%02X%02X%02X%02X%02X}",
72 data[0], data[1], data[2], data[3], data[4], data[5], data[6], data[7],
73 data[8], data[9], data[10], data[11], data[12], data[13], data[14],
74 data[15]);
75}
76}
77
78// Returns true on success.
79bool OmahaRequestDeviceParams::GetMachineId(std::string* out_id) const {
80 // Checks if we have an existing Machine ID.
81 const string omaha_id_path = root_ + OmahaIdPath();
82
83 if (utils::ReadFileToString(omaha_id_path, out_id) &&
84 out_id->size() == kGuidStringLength) {
85 return true;
86 }
87
88 // Creates a new ID.
89 int rand_fd = open("/dev/urandom", O_RDONLY, 0);
90 TEST_AND_RETURN_FALSE_ERRNO(rand_fd >= 0);
91 ScopedFdCloser rand_fd_closer(&rand_fd);
92 unsigned char buf[kGuidDataByteLength];
93 size_t bytes_read = 0;
94 while (bytes_read < sizeof(buf)) {
95 ssize_t rc = read(rand_fd, buf + bytes_read, sizeof(buf) - bytes_read);
96 TEST_AND_RETURN_FALSE_ERRNO(rc > 0);
97 bytes_read += rc;
98 }
99 string guid = GuidFromData(buf);
100 TEST_AND_RETURN_FALSE(
101 utils::WriteFile(omaha_id_path.c_str(), guid.data(), guid.size()));
102 *out_id = guid;
103 return true;
104}
105
106string OmahaRequestDeviceParams::GetLsbValue(
107 const string& key, const string& default_value) const {
108 string files[] = {string(utils::kStatefulPartition) + "/etc/lsb-release",
109 "/etc/lsb-release"};
110 for (unsigned int i = 0; i < arraysize(files); ++i) {
111 // TODO(adlr): make sure files checked are owned as root (and all
112 // their parents are recursively, too).
113 string file_data;
114 if (!utils::ReadFileToString(root_ + files[i], &file_data))
115 continue;
116
117 map<string, string> data = simple_key_value_store::ParseString(file_data);
118 if (utils::MapContainsKey(data, key))
119 return data[key];
120 }
121 // not found
122 return default_value;
123}
124
125string OmahaRequestDeviceParams::GetMachineType() const {
126 struct utsname buf;
127 string ret;
128 if (uname(&buf) == 0)
129 ret = buf.machine;
130 return ret;
131}
132
133} // namespace chromeos_update_engine