1 // Copyright 2016 The Chromium 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 "remoting/host/host_attributes.h"
6 
7 #include <string>
8 #include <type_traits>
9 #include <vector>
10 
11 #include "base/atomicops.h"
12 #include "base/check_op.h"
13 #include "base/stl_util.h"
14 #include "base/strings/string_piece.h"
15 #include "base/strings/string_util.h"
16 #include "build/branding_buildflags.h"
17 #include "build/build_config.h"
18 
19 #if defined(OS_WIN)
20 #include "base/win/windows_version.h"
21 #include "media/base/win/mf_initializer.h"
22 #include "media/gpu/windows/media_foundation_video_encode_accelerator_win.h"
23 #include "remoting/host/win/evaluate_3d_display_mode.h"
24 #include "remoting/host/win/evaluate_d3d.h"
25 #endif
26 
27 namespace remoting {
28 
29 namespace {
30 
31 static constexpr char kSeparator[] = ",";
32 
33 struct Attribute {
34   const char* name;
35   bool(* get_value_func)();
36 };
37 
IsDebug()38 inline constexpr bool IsDebug() {
39 #if defined(NDEBUG)
40   return false;
41 #else
42   return true;
43 #endif
44 }
45 
IsChromeBranded()46 inline constexpr bool IsChromeBranded() {
47 #if BUILDFLAG(GOOGLE_CHROME_BRANDING)
48   return true;
49 #elif BUILDFLAG(CHROMIUM_BRANDING)
50   return false;
51 #else
52   #error Only Chrome and Chromium brands are supported.
53 #endif
54 }
55 
IsChromiumBranded()56 inline constexpr bool IsChromiumBranded() {
57   return !IsChromeBranded();
58 }
59 
IsOfficialBuild()60 inline constexpr bool IsOfficialBuild() {
61 #if defined(OFFICIAL_BUILD)
62   return true;
63 #else
64   return false;
65 #endif
66 }
67 
IsNonOfficialBuild()68 inline constexpr bool IsNonOfficialBuild() {
69   return !IsOfficialBuild();
70 }
71 
72 // By using base::size() macro in base/macros.h, it's illegal to have empty
73 // arrays.
74 //
75 // error: no matching function for call to 'ArraySizeHelper'
76 // note: candidate template ignored: substitution failure
77 // [with T = const remoting::StaticAttribute, N = 0]:
78 // zero-length arrays are not permitted in C++.
79 //
80 // So we need IsDebug() function, and "Debug-Build" Attribute.
81 
82 static constexpr Attribute kAttributes[] = {
83   { "Debug-Build", &IsDebug },
84   { "ChromeBrand", &IsChromeBranded },
85   { "ChromiumBrand", &IsChromiumBranded },
86   { "OfficialBuild", &IsOfficialBuild },
87   { "NonOfficialBuild", &IsNonOfficialBuild },
88 };
89 
90 }  // namespace
91 
92 static_assert(std::is_pod<Attribute>::value, "Attribute should be POD.");
93 
GetHostAttributes()94 std::string GetHostAttributes() {
95   std::vector<std::string> result;
96   for (const auto& attribute : kAttributes) {
97     DCHECK_EQ(std::string(attribute.name).find(kSeparator), std::string::npos);
98     if (attribute.get_value_func()) {
99       result.push_back(attribute.name);
100     }
101   }
102 #if defined(OS_WIN)
103   {
104     GetD3DCapabilities(&result);
105 
106     auto version = base::win::GetVersion();
107     if (version >= base::win::Version::WIN8) {
108       result.push_back("Win8+");
109     }
110     if (version >= base::win::Version::WIN8_1) {
111       result.push_back("Win81+");
112     }
113     if (version >= base::win::Version::WIN10) {
114       result.push_back("Win10+");
115     }
116   }
117 
118   if (media::MediaFoundationVideoEncodeAccelerator
119       ::PreSandboxInitialization() &&
120       media::InitializeMediaFoundation()) {
121     result.push_back("HWEncoder");
122   }
123 #elif defined(OS_LINUX) || defined(OS_CHROMEOS) || defined(OS_BSD)
124   result.push_back("HWEncoder");
125 #endif
126 
127   return base::JoinString(result, kSeparator);
128 }
129 
130 }  // namespace remoting
131