Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(17)

Side by Side Diff: base/metrics/field_trial.cc

Issue 2633203002: Enable field trial shared memory segment on Android. (Closed)
Patch Set: Add #error Unsupported OS. Created 3 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « base/metrics/field_trial.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "base/metrics/field_trial.h" 5 #include "base/metrics/field_trial.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <utility> 8 #include <utility>
9 9
10 #include "base/base_switches.h" 10 #include "base/base_switches.h"
11 #include "base/build_time.h" 11 #include "base/build_time.h"
12 #include "base/command_line.h" 12 #include "base/command_line.h"
13 #include "base/logging.h" 13 #include "base/logging.h"
14 #include "base/metrics/field_trial_param_associator.h" 14 #include "base/metrics/field_trial_param_associator.h"
15 #include "base/process/memory.h" 15 #include "base/process/memory.h"
16 #include "base/rand_util.h" 16 #include "base/rand_util.h"
17 #include "base/strings/string_number_conversions.h" 17 #include "base/strings/string_number_conversions.h"
18 #include "base/strings/string_util.h" 18 #include "base/strings/string_util.h"
19 #include "base/strings/stringprintf.h" 19 #include "base/strings/stringprintf.h"
20 #include "base/strings/utf_string_conversions.h" 20 #include "base/strings/utf_string_conversions.h"
21 21
22 // On systems that use the zygote process to spawn child processes, we must 22 // On POSIX, the fd is shared using the mapping in GlobalDescriptors.
23 // retrieve the correct fd using the mapping in GlobalDescriptors. 23 #if defined(OS_POSIX) && !defined(OS_NACL)
24 #if defined(OS_POSIX) && !defined(OS_NACL) && !defined(OS_MACOSX) && \
25 !defined(OS_ANDROID)
26 #define POSIX_WITH_ZYGOTE 1
27 #endif
28
29 #if defined(POSIX_WITH_ZYGOTE) || defined(OS_MACOSX)
30 #include "base/posix/global_descriptors.h" 24 #include "base/posix/global_descriptors.h"
31 #endif 25 #endif
32 26
33 namespace base { 27 namespace base {
34 28
35 namespace { 29 namespace {
36 30
37 // Define a separator character to use when creating a persistent form of an 31 // Define a separator character to use when creating a persistent form of an
38 // instance. This is intended for use as a command line argument, passed to a 32 // instance. This is intended for use as a command line argument, passed to a
39 // second process to mimic our state (i.e., provide the same group name). 33 // second process to mimic our state (i.e., provide the same group name).
(...skipping 16 matching lines...) Expand all
56 // Constants for the field trial allocator. 50 // Constants for the field trial allocator.
57 const char kAllocatorName[] = "FieldTrialAllocator"; 51 const char kAllocatorName[] = "FieldTrialAllocator";
58 52
59 // We allocate 128 KiB to hold all the field trial data. This should be enough, 53 // We allocate 128 KiB to hold all the field trial data. This should be enough,
60 // as most people use 3 - 25 KiB for field trials (as of 11/25/2016). 54 // as most people use 3 - 25 KiB for field trials (as of 11/25/2016).
61 // This also doesn't allocate all 128 KiB at once -- the pages only get mapped 55 // This also doesn't allocate all 128 KiB at once -- the pages only get mapped
62 // to physical memory when they are touched. If the size of the allocated field 56 // to physical memory when they are touched. If the size of the allocated field
63 // trials does get larger than 128 KiB, then we will drop some field trials in 57 // trials does get larger than 128 KiB, then we will drop some field trials in
64 // child processes, leading to an inconsistent view between browser and child 58 // child processes, leading to an inconsistent view between browser and child
65 // processes and possibly causing crashes (see crbug.com/661617). 59 // processes and possibly causing crashes (see crbug.com/661617).
66 #if !defined(OS_NACL)
67 const size_t kFieldTrialAllocationSize = 128 << 10; // 128 KiB 60 const size_t kFieldTrialAllocationSize = 128 << 10; // 128 KiB
68 #endif
69 61
70 // Writes out string1 and then string2 to pickle. 62 // Writes out string1 and then string2 to pickle.
71 bool WriteStringPair(Pickle* pickle, 63 bool WriteStringPair(Pickle* pickle,
72 const StringPiece& string1, 64 const StringPiece& string1,
73 const StringPiece& string2) { 65 const StringPiece& string2) {
74 if (!pickle->WriteString(string1)) 66 if (!pickle->WriteString(string1))
75 return false; 67 return false;
76 if (!pickle->WriteString(string2)) 68 if (!pickle->WriteString(string2))
77 return false; 69 return false;
78 return true; 70 return true;
(...skipping 132 matching lines...) Expand 10 before | Expand all | Expand 10 after
211 HANDLE src = allocator->shared_memory()->handle().GetHandle(); 203 HANDLE src = allocator->shared_memory()->handle().GetHandle();
212 ProcessHandle process = GetCurrentProcess(); 204 ProcessHandle process = GetCurrentProcess();
213 DWORD access = SECTION_MAP_READ | SECTION_QUERY; 205 DWORD access = SECTION_MAP_READ | SECTION_QUERY;
214 HANDLE dst; 206 HANDLE dst;
215 if (!::DuplicateHandle(process, src, process, &dst, access, true, 0)) 207 if (!::DuplicateHandle(process, src, process, &dst, access, true, 0))
216 return kInvalidPlatformFile; 208 return kInvalidPlatformFile;
217 return dst; 209 return dst;
218 } 210 }
219 #endif 211 #endif
220 212
221 #if defined(POSIX_WITH_ZYGOTE) || defined(OS_MACOSX) 213 #if defined(OS_POSIX) && !defined(OS_NACL)
222 int CreateReadOnlyHandle(FieldTrialList::FieldTrialAllocator* allocator) { 214 int CreateReadOnlyHandle(FieldTrialList::FieldTrialAllocator* allocator) {
223 SharedMemoryHandle new_handle; 215 SharedMemoryHandle new_handle;
224 allocator->shared_memory()->ShareReadOnlyToProcess(GetCurrentProcessHandle(), 216 allocator->shared_memory()->ShareReadOnlyToProcess(GetCurrentProcessHandle(),
225 &new_handle); 217 &new_handle);
226 return SharedMemory::GetFdFromSharedMemoryHandle(new_handle); 218 return SharedMemory::GetFdFromSharedMemoryHandle(new_handle);
227 } 219 }
228 #endif 220 #endif
229 221
222 void OnOutOfMemory(size_t size) {
223 #if defined(OS_NACL)
224 NOTREACHED();
225 #else
226 TerminateBecauseOutOfMemory(size);
227 #endif
228 }
229
230 } // namespace 230 } // namespace
231 231
232 // statics 232 // statics
233 const int FieldTrial::kNotFinalized = -1; 233 const int FieldTrial::kNotFinalized = -1;
234 const int FieldTrial::kDefaultGroupNumber = 0; 234 const int FieldTrial::kDefaultGroupNumber = 0;
235 bool FieldTrial::enable_benchmarking_ = false; 235 bool FieldTrial::enable_benchmarking_ = false;
236 236
237 int FieldTrialList::kNoExpirationYear = 0; 237 int FieldTrialList::kNoExpirationYear = 0;
238 238
239 //------------------------------------------------------------------------------ 239 //------------------------------------------------------------------------------
(...skipping 532 matching lines...) Expand 10 before | Expand all | Expand 10 after
772 772
773 #if defined(OS_WIN) 773 #if defined(OS_WIN)
774 if (cmd_line.HasSwitch(field_trial_handle_switch)) { 774 if (cmd_line.HasSwitch(field_trial_handle_switch)) {
775 std::string handle_switch = 775 std::string handle_switch =
776 cmd_line.GetSwitchValueASCII(field_trial_handle_switch); 776 cmd_line.GetSwitchValueASCII(field_trial_handle_switch);
777 bool result = CreateTrialsFromHandleSwitch(handle_switch); 777 bool result = CreateTrialsFromHandleSwitch(handle_switch);
778 DCHECK(result); 778 DCHECK(result);
779 } 779 }
780 #endif 780 #endif
781 781
782 #if defined(POSIX_WITH_ZYGOTE) || defined(OS_MACOSX) 782 #if defined(OS_POSIX) && !defined(OS_NACL)
783 // On POSIX, we check if the handle is valid by seeing if the browser process 783 // On POSIX, we check if the handle is valid by seeing if the browser process
784 // sent over the switch (we don't care about the value). Invalid handles 784 // sent over the switch (we don't care about the value). Invalid handles
785 // occur in some browser tests which don't initialize the allocator. 785 // occur in some browser tests which don't initialize the allocator.
786 if (cmd_line.HasSwitch(field_trial_handle_switch)) { 786 if (cmd_line.HasSwitch(field_trial_handle_switch)) {
787 bool result = CreateTrialsFromDescriptor(fd_key); 787 bool result = CreateTrialsFromDescriptor(fd_key);
788 DCHECK(result); 788 DCHECK(result);
789 } 789 }
790 #endif 790 #endif
791 791
792 if (cmd_line.HasSwitch(switches::kForceFieldTrials)) { 792 if (cmd_line.HasSwitch(switches::kForceFieldTrials)) {
(...skipping 15 matching lines...) Expand all
808 !global_->field_trial_allocator_.get()) { 808 !global_->field_trial_allocator_.get()) {
809 return feature_list->InitializeFromCommandLine( 809 return feature_list->InitializeFromCommandLine(
810 command_line.GetSwitchValueASCII(enable_features_switch), 810 command_line.GetSwitchValueASCII(enable_features_switch),
811 command_line.GetSwitchValueASCII(disable_features_switch)); 811 command_line.GetSwitchValueASCII(disable_features_switch));
812 } 812 }
813 813
814 feature_list->InitializeFromSharedMemory( 814 feature_list->InitializeFromSharedMemory(
815 global_->field_trial_allocator_.get()); 815 global_->field_trial_allocator_.get());
816 } 816 }
817 817
818 #if defined(POSIX_WITH_ZYGOTE) || defined(OS_MACOSX)
819 // static
820 bool FieldTrialList::CreateTrialsFromDescriptor(int fd_key) {
821 if (!kUseSharedMemoryForFieldTrials)
822 return false;
823
824 if (fd_key == -1)
825 return false;
826
827 int fd = GlobalDescriptors::GetInstance()->MaybeGet(fd_key);
828 if (fd == -1)
829 return false;
830
831 #if defined(POSIX_WITH_ZYGOTE)
832 SharedMemoryHandle shm_handle(fd, true);
833 #elif defined(OS_MACOSX)
834 SharedMemoryHandle shm_handle(FileDescriptor(fd, true));
835 #endif
836
837 bool result = FieldTrialList::CreateTrialsFromSharedMemoryHandle(shm_handle);
838 DCHECK(result);
839 return true;
840 }
841 #endif
842
843 #if defined(OS_WIN) 818 #if defined(OS_WIN)
844 // static 819 // static
845 void FieldTrialList::AppendFieldTrialHandleIfNeeded( 820 void FieldTrialList::AppendFieldTrialHandleIfNeeded(
846 HandlesToInheritVector* handles) { 821 HandlesToInheritVector* handles) {
847 if (!global_) 822 if (!global_)
848 return; 823 return;
849 if (kUseSharedMemoryForFieldTrials) { 824 if (kUseSharedMemoryForFieldTrials) {
850 InstantiateFieldTrialAllocatorIfNeeded(); 825 InstantiateFieldTrialAllocatorIfNeeded();
851 if (global_->readonly_allocator_handle_) 826 if (global_->readonly_allocator_handle_)
852 handles->push_back(global_->readonly_allocator_handle_); 827 handles->push_back(global_->readonly_allocator_handle_);
(...skipping 23 matching lines...) Expand all
876 // content browser tests currently don't create a FieldTrialList because they 851 // content browser tests currently don't create a FieldTrialList because they
877 // don't run ChromeBrowserMainParts code where it's done for Chrome. 852 // don't run ChromeBrowserMainParts code where it's done for Chrome.
878 // Some tests depend on the enable and disable features flag switch, though, 853 // Some tests depend on the enable and disable features flag switch, though,
879 // so we can still add those even though AllStatesToString() will be a no-op. 854 // so we can still add those even though AllStatesToString() will be a no-op.
880 if (!global_) { 855 if (!global_) {
881 AddFeatureAndFieldTrialFlags(enable_features_switch, 856 AddFeatureAndFieldTrialFlags(enable_features_switch,
882 disable_features_switch, cmd_line); 857 disable_features_switch, cmd_line);
883 return; 858 return;
884 } 859 }
885 860
886 #if defined(OS_WIN) || defined(POSIX_WITH_ZYGOTE) || defined(OS_MACOSX)
887 // Use shared memory to pass the state if the feature is enabled, otherwise 861 // Use shared memory to pass the state if the feature is enabled, otherwise
888 // fallback to passing it via the command line as a string. 862 // fallback to passing it via the command line as a string.
889 if (kUseSharedMemoryForFieldTrials) { 863 if (kUseSharedMemoryForFieldTrials) {
890 InstantiateFieldTrialAllocatorIfNeeded(); 864 InstantiateFieldTrialAllocatorIfNeeded();
891 // If the readonly handle didn't get duplicated properly, then fallback to 865 // If the readonly handle didn't get duplicated properly, then fallback to
892 // original behavior. 866 // original behavior.
893 if (global_->readonly_allocator_handle_ == kInvalidPlatformFile) { 867 if (global_->readonly_allocator_handle_ == kInvalidPlatformFile) {
894 AddFeatureAndFieldTrialFlags(enable_features_switch, 868 AddFeatureAndFieldTrialFlags(enable_features_switch,
895 disable_features_switch, cmd_line); 869 disable_features_switch, cmd_line);
896 return; 870 return;
897 } 871 }
898 872
899 global_->field_trial_allocator_->UpdateTrackingHistograms(); 873 global_->field_trial_allocator_->UpdateTrackingHistograms();
900 874
901 #if defined(OS_WIN) 875 #if defined(OS_WIN)
902 // We need to pass a named anonymous handle to shared memory over the 876 // We need to pass a named anonymous handle to shared memory over the
903 // command line on Windows, since the child doesn't know which of the 877 // command line on Windows, since the child doesn't know which of the
904 // handles it inherited it should open. 878 // handles it inherited it should open.
905 // PlatformFile is typedef'd to HANDLE which is typedef'd to void *. We 879 // PlatformFile is typedef'd to HANDLE which is typedef'd to void *. We
906 // basically cast the handle into an int (uintptr_t, to be exact), stringify 880 // basically cast the handle into an int (uintptr_t, to be exact), stringify
907 // the int, and pass it as a command-line flag. The child process will do 881 // the int, and pass it as a command-line flag. The child process will do
908 // the reverse conversions to retrieve the handle. See 882 // the reverse conversions to retrieve the handle. See
909 // http://stackoverflow.com/a/153077 883 // http://stackoverflow.com/a/153077
910 auto uintptr_handle = 884 auto uintptr_handle =
911 reinterpret_cast<uintptr_t>(global_->readonly_allocator_handle_); 885 reinterpret_cast<uintptr_t>(global_->readonly_allocator_handle_);
912 std::string field_trial_handle = std::to_string(uintptr_handle); 886 std::string field_trial_handle = std::to_string(uintptr_handle);
913 cmd_line->AppendSwitchASCII(field_trial_handle_switch, field_trial_handle); 887 cmd_line->AppendSwitchASCII(field_trial_handle_switch, field_trial_handle);
914 #elif defined(POSIX_WITH_ZYGOTE) || defined(OS_MACOSX) 888 #elif defined(OS_POSIX)
915 // On POSIX, we dup the fd into a fixed fd kFieldTrialDescriptor, so we 889 // On POSIX, we dup the fd into a fixed fd kFieldTrialDescriptor, so we
916 // don't have to pass over the handle (it's not even the right handle 890 // don't have to pass over the handle (it's not even the right handle
917 // anyways). But some browser tests don't create the allocator, so we need 891 // anyways). But some browser tests don't create the allocator, so we need
918 // to be able to distinguish valid and invalid handles. We do that by just 892 // to be able to distinguish valid and invalid handles. We do that by just
919 // checking that the flag is set with a dummy value. 893 // checking that the flag is set with a dummy value.
920 cmd_line->AppendSwitchASCII(field_trial_handle_switch, "1"); 894 cmd_line->AppendSwitchASCII(field_trial_handle_switch, "1");
895 #else
896 #error Unsupported OS
921 #endif 897 #endif
922 return; 898 return;
923 } 899 }
924 #endif
925 900
926 AddFeatureAndFieldTrialFlags(enable_features_switch, disable_features_switch, 901 AddFeatureAndFieldTrialFlags(enable_features_switch, disable_features_switch,
927 cmd_line); 902 cmd_line);
928 } 903 }
929 904
930 // static 905 // static
931 FieldTrial* FieldTrialList::CreateFieldTrial( 906 FieldTrial* FieldTrialList::CreateFieldTrial(
932 const std::string& name, 907 const std::string& name,
933 const std::string& group_name) { 908 const std::string& group_name) {
934 DCHECK(global_); 909 DCHECK(global_);
(...skipping 207 matching lines...) Expand 10 before | Expand all | Expand 10 after
1142 // static 1117 // static
1143 bool FieldTrialList::CreateTrialsFromHandleSwitch( 1118 bool FieldTrialList::CreateTrialsFromHandleSwitch(
1144 const std::string& handle_switch) { 1119 const std::string& handle_switch) {
1145 int field_trial_handle = std::stoi(handle_switch); 1120 int field_trial_handle = std::stoi(handle_switch);
1146 HANDLE handle = reinterpret_cast<HANDLE>(field_trial_handle); 1121 HANDLE handle = reinterpret_cast<HANDLE>(field_trial_handle);
1147 SharedMemoryHandle shm_handle(handle, GetCurrentProcId()); 1122 SharedMemoryHandle shm_handle(handle, GetCurrentProcId());
1148 return FieldTrialList::CreateTrialsFromSharedMemoryHandle(shm_handle); 1123 return FieldTrialList::CreateTrialsFromSharedMemoryHandle(shm_handle);
1149 } 1124 }
1150 #endif 1125 #endif
1151 1126
1152 #if !defined(OS_NACL) 1127 #if defined(OS_POSIX) && !defined(OS_NACL)
1128 // static
1129 bool FieldTrialList::CreateTrialsFromDescriptor(int fd_key) {
1130 if (!kUseSharedMemoryForFieldTrials)
1131 return false;
1132
1133 if (fd_key == -1)
1134 return false;
1135
1136 int fd = GlobalDescriptors::GetInstance()->MaybeGet(fd_key);
1137 if (fd == -1)
1138 return false;
1139
1140 #if defined(OS_MACOSX) && !defined(OS_IOS)
1141 SharedMemoryHandle shm_handle(FileDescriptor(fd, true));
1142 #else
1143 SharedMemoryHandle shm_handle(fd, true);
1144 #endif
1145
1146 bool result = FieldTrialList::CreateTrialsFromSharedMemoryHandle(shm_handle);
1147 DCHECK(result);
1148 return true;
1149 }
1150 #endif
1151
1153 // static 1152 // static
1154 bool FieldTrialList::CreateTrialsFromSharedMemoryHandle( 1153 bool FieldTrialList::CreateTrialsFromSharedMemoryHandle(
1155 SharedMemoryHandle shm_handle) { 1154 SharedMemoryHandle shm_handle) {
1156 // shm gets deleted when it gets out of scope, but that's OK because we need 1155 // shm gets deleted when it gets out of scope, but that's OK because we need
1157 // it only for the duration of this method. 1156 // it only for the duration of this method.
1158 std::unique_ptr<SharedMemory> shm(new SharedMemory(shm_handle, true)); 1157 std::unique_ptr<SharedMemory> shm(new SharedMemory(shm_handle, true));
1159 if (!shm.get()->Map(kFieldTrialAllocationSize)) 1158 if (!shm.get()->Map(kFieldTrialAllocationSize))
1160 TerminateBecauseOutOfMemory(kFieldTrialAllocationSize); 1159 OnOutOfMemory(kFieldTrialAllocationSize);
1161 1160
1162 return FieldTrialList::CreateTrialsFromSharedMemory(std::move(shm)); 1161 return FieldTrialList::CreateTrialsFromSharedMemory(std::move(shm));
1163 } 1162 }
1164 #endif
1165 1163
1166 // static 1164 // static
1167 bool FieldTrialList::CreateTrialsFromSharedMemory( 1165 bool FieldTrialList::CreateTrialsFromSharedMemory(
1168 std::unique_ptr<SharedMemory> shm) { 1166 std::unique_ptr<SharedMemory> shm) {
1169 global_->field_trial_allocator_.reset( 1167 global_->field_trial_allocator_.reset(
1170 new FieldTrialAllocator(std::move(shm), 0, kAllocatorName, true)); 1168 new FieldTrialAllocator(std::move(shm), 0, kAllocatorName, true));
1171 FieldTrialAllocator* shalloc = global_->field_trial_allocator_.get(); 1169 FieldTrialAllocator* shalloc = global_->field_trial_allocator_.get();
1172 FieldTrialAllocator::Iterator mem_iter(shalloc); 1170 FieldTrialAllocator::Iterator mem_iter(shalloc);
1173 1171
1174 const FieldTrial::FieldTrialEntry* entry; 1172 const FieldTrial::FieldTrialEntry* entry;
(...skipping 13 matching lines...) Expand all
1188 if (subtle::NoBarrier_Load(&entry->activated)) { 1186 if (subtle::NoBarrier_Load(&entry->activated)) {
1189 // Call |group()| to mark the trial as "used" and notify observers, if 1187 // Call |group()| to mark the trial as "used" and notify observers, if
1190 // any. This is useful to ensure that field trials created in child 1188 // any. This is useful to ensure that field trials created in child
1191 // processes are properly reported in crash reports. 1189 // processes are properly reported in crash reports.
1192 trial->group(); 1190 trial->group();
1193 } 1191 }
1194 } 1192 }
1195 return true; 1193 return true;
1196 } 1194 }
1197 1195
1198 #if !defined(OS_NACL)
1199 // static 1196 // static
1200 void FieldTrialList::InstantiateFieldTrialAllocatorIfNeeded() { 1197 void FieldTrialList::InstantiateFieldTrialAllocatorIfNeeded() {
1201 if (!global_) 1198 if (!global_)
1202 return; 1199 return;
1203 AutoLock auto_lock(global_->lock_); 1200 AutoLock auto_lock(global_->lock_);
1204 // Create the allocator if not already created and add all existing trials. 1201 // Create the allocator if not already created and add all existing trials.
1205 if (global_->field_trial_allocator_ != nullptr) 1202 if (global_->field_trial_allocator_ != nullptr)
1206 return; 1203 return;
1207 1204
1208 SharedMemoryCreateOptions options; 1205 SharedMemoryCreateOptions options;
1209 options.size = kFieldTrialAllocationSize; 1206 options.size = kFieldTrialAllocationSize;
1210 options.share_read_only = true; 1207 options.share_read_only = true;
1211 #if defined(OS_MACOSX) && !defined(OS_IOS) 1208 #if defined(OS_MACOSX) && !defined(OS_IOS)
1212 options.type = SharedMemoryHandle::POSIX; 1209 options.type = SharedMemoryHandle::POSIX;
1213 #endif 1210 #endif
1214 1211
1215 std::unique_ptr<SharedMemory> shm(new SharedMemory()); 1212 std::unique_ptr<SharedMemory> shm(new SharedMemory());
1216 if (!shm->Create(options)) 1213 if (!shm->Create(options))
1217 TerminateBecauseOutOfMemory(kFieldTrialAllocationSize); 1214 OnOutOfMemory(kFieldTrialAllocationSize);
1218 1215
1219 if (!shm->Map(kFieldTrialAllocationSize)) 1216 if (!shm->Map(kFieldTrialAllocationSize))
1220 TerminateBecauseOutOfMemory(kFieldTrialAllocationSize); 1217 OnOutOfMemory(kFieldTrialAllocationSize);
1221 1218
1222 global_->field_trial_allocator_.reset( 1219 global_->field_trial_allocator_.reset(
1223 new FieldTrialAllocator(std::move(shm), 0, kAllocatorName, false)); 1220 new FieldTrialAllocator(std::move(shm), 0, kAllocatorName, false));
1224 global_->field_trial_allocator_->CreateTrackingHistograms(kAllocatorName); 1221 global_->field_trial_allocator_->CreateTrackingHistograms(kAllocatorName);
1225 1222
1226 // Add all existing field trials. 1223 // Add all existing field trials.
1227 for (const auto& registered : global_->registered_) { 1224 for (const auto& registered : global_->registered_) {
1228 AddToAllocatorWhileLocked(global_->field_trial_allocator_.get(), 1225 AddToAllocatorWhileLocked(global_->field_trial_allocator_.get(),
1229 registered.second); 1226 registered.second);
1230 } 1227 }
1231 1228
1232 // Add all existing features. 1229 // Add all existing features.
1233 FeatureList::GetInstance()->AddFeaturesToAllocator( 1230 FeatureList::GetInstance()->AddFeaturesToAllocator(
1234 global_->field_trial_allocator_.get()); 1231 global_->field_trial_allocator_.get());
1235 1232
1236 #if defined(OS_WIN) || defined(POSIX_WITH_ZYGOTE) || defined(OS_MACOSX) 1233 #if !defined(OS_NACL)
1237 // Set |readonly_allocator_handle_| so we can pass it to be inherited and 1234 // Set |readonly_allocator_handle_| so we can pass it to be inherited and
1238 // via the command line. 1235 // via the command line.
1239 global_->readonly_allocator_handle_ = 1236 global_->readonly_allocator_handle_ =
1240 CreateReadOnlyHandle(global_->field_trial_allocator_.get()); 1237 CreateReadOnlyHandle(global_->field_trial_allocator_.get());
1241 #endif 1238 #endif
1242 } 1239 }
1243 #endif
1244 1240
1245 // static 1241 // static
1246 void FieldTrialList::AddToAllocatorWhileLocked( 1242 void FieldTrialList::AddToAllocatorWhileLocked(
1247 PersistentMemoryAllocator* allocator, 1243 PersistentMemoryAllocator* allocator,
1248 FieldTrial* field_trial) { 1244 FieldTrial* field_trial) {
1249 // Don't do anything if the allocator hasn't been instantiated yet. 1245 // Don't do anything if the allocator hasn't been instantiated yet.
1250 if (allocator == nullptr) 1246 if (allocator == nullptr)
1251 return; 1247 return;
1252 1248
1253 // Or if the allocator is read only, which means we are in a child process and 1249 // Or if the allocator is read only, which means we are in a child process and
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after
1343 return; 1339 return;
1344 } 1340 }
1345 AutoLock auto_lock(global_->lock_); 1341 AutoLock auto_lock(global_->lock_);
1346 CHECK(!global_->PreLockedFind(trial->trial_name())) << trial->trial_name(); 1342 CHECK(!global_->PreLockedFind(trial->trial_name())) << trial->trial_name();
1347 trial->AddRef(); 1343 trial->AddRef();
1348 trial->SetTrialRegistered(); 1344 trial->SetTrialRegistered();
1349 global_->registered_[trial->trial_name()] = trial; 1345 global_->registered_[trial->trial_name()] = trial;
1350 } 1346 }
1351 1347
1352 } // namespace base 1348 } // namespace base
OLDNEW
« no previous file with comments | « base/metrics/field_trial.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698