blob: f37818ed824a9e8687d2898b7f8155f4feba1c82 [file] [log] [blame]
[email protected]efd2c3f2014-03-11 09:57:251// Copyright 2014 The Chromium Authors. All rights reserved.
[email protected]4202867482010-08-27 19:28:252// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
[email protected]efd2c3f2014-03-11 09:57:255#include "content/public/common/user_agent.h"
6
avia9aa7a82015-12-25 03:06:317#include <stdint.h>
8
Melissa Galonsky15417f92018-08-10 16:03:359#include "base/feature_list.h"
[email protected]efd2c3f2014-03-11 09:57:2510#include "base/logging.h"
11#include "base/strings/string_util.h"
12#include "base/strings/stringprintf.h"
Sebastien Marchand75a7cdf2018-11-13 23:47:0313#include "base/system/sys_info.h"
[email protected]efd2c3f2014-03-11 09:57:2514#include "build/build_config.h"
tfarinac2103c42015-10-27 21:37:3415#include "build/util/webkit_version.h"
[email protected]4202867482010-08-27 19:28:2516
[email protected]b4e3e8d52011-03-05 01:16:2817#if defined(OS_WIN)
18#include "base/win/windows_version.h"
Fabrice de Gans-Riberi91fa35052018-05-07 19:33:4819#elif (defined(OS_POSIX) && !defined(OS_MACOSX)) || defined(OS_FUCHSIA)
20#include <sys/utsname.h>
[email protected]b4e3e8d52011-03-05 01:16:2821#endif
22
[email protected]efd2c3f2014-03-11 09:57:2523namespace content {
24
Lei Zhang6c119132018-11-15 01:44:3325namespace {
26
Melissa Galonsky15417f92018-08-10 16:03:3527#if defined(OS_ANDROID)
28const base::Feature kAndroidUserAgentStringContainsBuildId{
29 "AndroidUserAgentStringContainsBuildId", base::FEATURE_DISABLED_BY_DEFAULT};
30#endif // defined(OS_ANDROID)
31
Lei Zhang6c119132018-11-15 01:44:3332std::string GetUserAgentPlatform() {
33 return
34#if defined(OS_WIN)
35 "";
36#elif defined(OS_MACOSX)
37 "Macintosh; ";
38#elif defined(USE_X11) || defined(USE_OZONE)
39 "X11; "; // strange, but that's what Firefox uses
40#elif defined(OS_ANDROID)
41 "Linux; ";
42#elif defined(OS_POSIX) || defined(OS_FUCHSIA)
43 "Unknown; ";
44#endif
45}
46
47} // namespace
48
[email protected]4202867482010-08-27 19:28:2549std::string GetWebKitVersion() {
[email protected]5193d5372011-01-22 00:41:5250 return base::StringPrintf("%d.%d (%s)",
51 WEBKIT_VERSION_MAJOR,
52 WEBKIT_VERSION_MINOR,
53 WEBKIT_SVN_REVISION);
54}
55
56std::string GetWebKitRevision() {
57 return WEBKIT_SVN_REVISION;
[email protected]4202867482010-08-27 19:28:2558}
59
Melissa Galonsky15417f92018-08-10 16:03:3560std::string BuildOSCpuInfo(bool include_android_build_number) {
[email protected]4202867482010-08-27 19:28:2561 std::string os_cpu;
62
[email protected]abef4b332012-08-21 23:55:5263#if defined(OS_WIN) || defined(OS_MACOSX) || defined(OS_CHROMEOS) ||\
64 defined(OS_ANDROID)
avia9aa7a82015-12-25 03:06:3165 int32_t os_major_version = 0;
66 int32_t os_minor_version = 0;
67 int32_t os_bugfix_version = 0;
[email protected]4202867482010-08-27 19:28:2568 base::SysInfo::OperatingSystemVersionNumbers(&os_major_version,
69 &os_minor_version,
70 &os_bugfix_version);
71#endif
[email protected]abef4b332012-08-21 23:55:5272
[email protected]b4e3e8d52011-03-05 01:16:2873#if defined(OS_WIN)
74 std::string architecture_token;
[email protected]f481221192011-04-07 22:15:3475 base::win::OSInfo* os_info = base::win::OSInfo::GetInstance();
76 if (os_info->wow64_status() == base::win::OSInfo::WOW64_ENABLED) {
[email protected]b4e3e8d52011-03-05 01:16:2877 architecture_token = "; WOW64";
78 } else {
[email protected]f481221192011-04-07 22:15:3479 base::win::OSInfo::WindowsArchitecture windows_architecture =
Lei Zhang10d9e1562019-03-14 18:46:0280 os_info->GetArchitecture();
[email protected]f481221192011-04-07 22:15:3481 if (windows_architecture == base::win::OSInfo::X64_ARCHITECTURE)
[email protected]b4e3e8d52011-03-05 01:16:2882 architecture_token = "; Win64; x64";
[email protected]f481221192011-04-07 22:15:3483 else if (windows_architecture == base::win::OSInfo::IA64_ARCHITECTURE)
[email protected]b4e3e8d52011-03-05 01:16:2884 architecture_token = "; Win64; IA64";
85 }
Fabrice de Gans-Riberi91fa35052018-05-07 19:33:4886#elif defined(OS_ANDROID)
Bo Liu4f2b4e142017-05-26 21:41:5187 std::string android_version_str = base::SysInfo::OperatingSystemVersion();
Lei Zhang4b6ba9f2018-09-05 04:58:4888 std::string android_info_str = GetAndroidOSInfo(include_android_build_number);
Fabrice de Gans-Riberi91fa35052018-05-07 19:33:4889#elif (defined(OS_POSIX) && !defined(OS_MACOSX)) || defined(OS_FUCHSIA)
90 // Should work on any Posix system.
91 struct utsname unixinfo;
92 uname(&unixinfo);
93
94 std::string cputype;
95 // special case for biarch systems
96 if (strcmp(unixinfo.machine, "x86_64") == 0 &&
97 sizeof(void*) == sizeof(int32_t)) { // NOLINT
98 cputype.assign("i686 (x86_64)");
99 } else {
100 cputype.assign(unixinfo.machine);
101 }
[email protected]abef4b332012-08-21 23:55:52102#endif
103
[email protected]a77fa2dc2010-11-15 12:11:11104 base::StringAppendF(
[email protected]4202867482010-08-27 19:28:25105 &os_cpu,
106#if defined(OS_WIN)
robliaoab2b82e82016-12-16 03:10:50107 "Windows NT %d.%d%s",
108 os_major_version,
109 os_minor_version,
[email protected]b4e3e8d52011-03-05 01:16:28110 architecture_token.c_str()
[email protected]4202867482010-08-27 19:28:25111#elif defined(OS_MACOSX)
112 "Intel Mac OS X %d_%d_%d",
113 os_major_version,
114 os_minor_version,
115 os_bugfix_version
116#elif defined(OS_CHROMEOS)
[email protected]71de8192011-03-16 15:11:16117 "CrOS "
[email protected]71de8192011-03-16 15:11:16118 "%s %d.%d.%d",
[email protected]3c2952a2011-03-03 19:49:47119 cputype.c_str(), // e.g. i686
[email protected]4202867482010-08-27 19:28:25120 os_major_version,
121 os_minor_version,
122 os_bugfix_version
[email protected]d0924cb32012-06-19 16:56:09123#elif defined(OS_ANDROID)
[email protected]8720e50e2012-09-20 10:43:58124 "Android %s%s",
125 android_version_str.c_str(),
[email protected]abef4b332012-08-21 23:55:52126 android_info_str.c_str()
Fabrice de Gans-Riberi91fa35052018-05-07 19:33:48127#elif defined(OS_POSIX) || defined(OS_FUCHSIA)
128 "%s %s",
129 unixinfo.sysname, // e.g. Linux
130 cputype.c_str() // e.g. i686
[email protected]4202867482010-08-27 19:28:25131#endif
132 ); // NOLINT
133
134 return os_cpu;
135}
136
John Delaneyac24e572019-04-30 19:47:02137base::StringPiece GetFrozenUserAgent(bool mobile) {
138#if defined(OS_ANDROID)
139 return mobile ? frozen_user_agent_strings::kAndroidMobile
140 : frozen_user_agent_strings::kAndroid;
141#endif
142 return frozen_user_agent_strings::kDesktop;
143}
144
gsenntone98c5bb42015-03-30 19:22:57145std::string BuildUserAgentFromProduct(const std::string& product) {
[email protected]3e807c42012-08-28 23:25:58146 std::string os_info;
Lei Zhang6c119132018-11-15 01:44:33147 base::StringAppendF(&os_info, "%s%s", GetUserAgentPlatform().c_str(),
Melissa Galonsky15417f92018-08-10 16:03:35148 BuildOSCpuInfo(false).c_str());
gsenntone98c5bb42015-03-30 19:22:57149 return BuildUserAgentFromOSAndProduct(os_info, product);
150}
151
Melissa Galonsky15417f92018-08-10 16:03:35152#if defined(OS_ANDROID)
gsenntone98c5bb42015-03-30 19:22:57153std::string BuildUserAgentFromProductAndExtraOSInfo(
154 const std::string& product,
Melissa Galonsky15417f92018-08-10 16:03:35155 const std::string& extra_os_info,
Lei Zhang4b6ba9f2018-09-05 04:58:48156 bool include_android_build_number) {
gsenntone98c5bb42015-03-30 19:22:57157 std::string os_info;
Lei Zhang6c119132018-11-15 01:44:33158 base::StringAppendF(&os_info, "%s%s%s", GetUserAgentPlatform().c_str(),
Melissa Galonsky15417f92018-08-10 16:03:35159 BuildOSCpuInfo(include_android_build_number).c_str(),
160 extra_os_info.c_str());
[email protected]3e807c42012-08-28 23:25:58161 return BuildUserAgentFromOSAndProduct(os_info, product);
162}
Lei Zhang4b6ba9f2018-09-05 04:58:48163
164std::string GetAndroidOSInfo(bool include_android_build_number) {
165 std::string android_info_str;
166
167 // Send information about the device.
168 bool semicolon_inserted = false;
169 std::string android_build_codename = base::SysInfo::GetAndroidBuildCodename();
170 std::string android_device_name = base::SysInfo::HardwareModelName();
171 if (!android_device_name.empty() && "REL" == android_build_codename) {
172 android_info_str += "; " + android_device_name;
173 semicolon_inserted = true;
174 }
175
176 // Append the build ID.
177 if (base::FeatureList::IsEnabled(kAndroidUserAgentStringContainsBuildId) ||
178 include_android_build_number) {
179 std::string android_build_id = base::SysInfo::GetAndroidBuildID();
180 if (!android_build_id.empty()) {
181 if (!semicolon_inserted)
182 android_info_str += ";";
183 android_info_str += " Build/" + android_build_id;
184 }
185 }
186
187 return android_info_str;
188}
189#endif // defined(OS_ANDROID)
[email protected]d7196e32011-06-16 22:35:50190
[email protected]3e807c42012-08-28 23:25:58191std::string BuildUserAgentFromOSAndProduct(const std::string& os_info,
192 const std::string& product) {
193 // Derived from Safari's UA string.
[email protected]d7196e32011-06-16 22:35:50194 // This is done to expose our product name in a manner that is maximally
195 // compatible with Safari, we hope!!
[email protected]3e807c42012-08-28 23:25:58196 std::string user_agent;
[email protected]a77fa2dc2010-11-15 12:11:11197 base::StringAppendF(
[email protected]d7196e32011-06-16 22:35:50198 &user_agent,
[email protected]3e807c42012-08-28 23:25:58199 "Mozilla/5.0 (%s) AppleWebKit/%d.%d (KHTML, like Gecko) %s Safari/%d.%d",
200 os_info.c_str(),
[email protected]4202867482010-08-27 19:28:25201 WEBKIT_VERSION_MAJOR,
202 WEBKIT_VERSION_MINOR,
203 product.c_str(),
204 WEBKIT_VERSION_MAJOR,
205 WEBKIT_VERSION_MINOR);
[email protected]d7196e32011-06-16 22:35:50206 return user_agent;
[email protected]4202867482010-08-27 19:28:25207}
208
[email protected]efd2c3f2014-03-11 09:57:25209} // namespace content