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 3# found in the LICENSE file. 4from telemetry import test 5from telemetry.page import page_test 6 7MEMORY_LIMIT_MB = 256 8SINGLE_TAB_LIMIT_MB = 128 9WIGGLE_ROOM_MB = 4 10 11test_harness_script = r""" 12 var domAutomationController = {}; 13 domAutomationController._finished = false; 14 15 domAutomationController.send = function(msg) { 16 // This should wait until all effects of memory management complete. 17 // We will need to wait until all 18 // 1. pending commits from the main thread to the impl thread in the 19 // compositor complete (for visible compositors). 20 // 2. allocations that the renderer's impl thread will make due to the 21 // compositor and WebGL are completed. 22 // 3. pending GpuMemoryManager::Manage() calls to manage are made. 23 // 4. renderers' OnMemoryAllocationChanged callbacks in response to 24 // manager are made. 25 // Each step in this sequence can cause trigger the next (as a 1-2-3-4-1 26 // cycle), so we will need to pump this cycle until it stabilizes. 27 28 // Pump the cycle 8 times (in principle it could take an infinite number 29 // of iterations to settle). 30 31 var rafCount = 0; 32 var totalRafCount = 8; 33 34 function pumpRAF() { 35 if (rafCount == totalRafCount) { 36 domAutomationController._finished = true; 37 return; 38 } 39 ++rafCount; 40 window.requestAnimationFrame(pumpRAF); 41 } 42 pumpRAF(); 43 } 44 45 window.domAutomationController = domAutomationController; 46 47 window.addEventListener("load", function() { 48 useGpuMemory(%d); 49 }, false); 50""" % MEMORY_LIMIT_MB 51 52class MemoryValidator(page_test.PageTest): 53 def __init__(self): 54 super(MemoryValidator, self).__init__('ValidatePage') 55 56 def ValidatePage(self, page, tab, results): 57 mb_used = MemoryValidator.GpuMemoryUsageMbytes(tab) 58 59 if mb_used + WIGGLE_ROOM_MB < SINGLE_TAB_LIMIT_MB: 60 raise page_test.Failure('Memory allocation too low') 61 62 if mb_used - WIGGLE_ROOM_MB > MEMORY_LIMIT_MB: 63 raise page_test.Failure('Memory allocation too high') 64 65 @staticmethod 66 def GpuMemoryUsageMbytes(tab): 67 gpu_rendering_stats_js = 'chrome.gpuBenchmarking.gpuRenderingStats()' 68 gpu_rendering_stats = tab.EvaluateJavaScript(gpu_rendering_stats_js) 69 return gpu_rendering_stats['globalVideoMemoryBytesAllocated'] / 1048576 70 71 def CustomizeBrowserOptions(self, options): 72 options.AppendExtraBrowserArgs('--enable-logging') 73 options.AppendExtraBrowserArgs( 74 '--force-gpu-mem-available-mb=%s' % MEMORY_LIMIT_MB) 75 options.AppendExtraBrowserArgs('--enable-gpu-benchmarking') 76 77class Memory(test.Test): 78 """Tests GPU memory limits""" 79 test = MemoryValidator 80 page_set = 'page_sets/memory_tests.json' 81 82 def CreatePageSet(self, options): 83 page_set = super(Memory, self).CreatePageSet(options) 84 for page in page_set.pages: 85 page.script_to_evaluate_on_commit = test_harness_script 86 return page_set