forked from mirrors/gecko-dev
		
	
		
			
				
	
	
		
			143 lines
		
	
	
	
		
			4 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
			
		
		
	
	
			143 lines
		
	
	
	
		
			4 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
| /* Any copyright is dedicated to the Public Domain.
 | |
|    http://creativecommons.org/publicdomain/zero/1.0/
 | |
| */
 | |
| /* A testcase to make sure reading late writes stacks works.  */
 | |
| 
 | |
| // Constants from prio.h for nsIFileOutputStream.init
 | |
| const PR_WRONLY = 0x2;
 | |
| const PR_CREATE_FILE = 0x8;
 | |
| const PR_TRUNCATE = 0x20;
 | |
| const RW_OWNER = parseInt("0600", 8);
 | |
| 
 | |
| const STACK_SUFFIX1 = "stack1.txt";
 | |
| const STACK_SUFFIX2 = "stack2.txt";
 | |
| const STACK_BOGUS_SUFFIX = "bogus.txt";
 | |
| const LATE_WRITE_PREFIX = "Telemetry.LateWriteFinal-";
 | |
| 
 | |
| // The names and IDs don't matter, but the format of the IDs does.
 | |
| const LOADED_MODULES = {
 | |
|   "4759A7E6993548C89CAF716A67EC242D00": "libtest.so",
 | |
|   F77AF15BB8D6419FA875954B4A3506CA00: "libxul.so",
 | |
|   "1E2F7FB590424E8F93D60BB88D66B8C500": "libc.so",
 | |
|   E4D6D70CC09A63EF8B88D532F867858800: "libmodμles.so",
 | |
| };
 | |
| const N_MODULES = Object.keys(LOADED_MODULES).length;
 | |
| 
 | |
| // Format of individual items is [index, offset-in-library].
 | |
| const STACK1 = [
 | |
|   [0, 0],
 | |
|   [1, 1],
 | |
|   [2, 2],
 | |
|   [3, 3],
 | |
| ];
 | |
| const STACK2 = [
 | |
|   [0, 0],
 | |
|   [1, 5],
 | |
|   [2, 10],
 | |
|   [3, 15],
 | |
| ];
 | |
| // XXX The only error checking is for a zero-sized stack.
 | |
| const STACK_BOGUS = [];
 | |
| 
 | |
| function write_string_to_file(file, contents) {
 | |
|   let ostream = Cc[
 | |
|     "@mozilla.org/network/safe-file-output-stream;1"
 | |
|   ].createInstance(Ci.nsIFileOutputStream);
 | |
|   ostream.init(
 | |
|     file,
 | |
|     PR_WRONLY | PR_CREATE_FILE | PR_TRUNCATE,
 | |
|     RW_OWNER,
 | |
|     ostream.DEFER_OPEN
 | |
|   );
 | |
| 
 | |
|   var bos = Cc["@mozilla.org/binaryoutputstream;1"].createInstance(
 | |
|     Ci.nsIBinaryOutputStream
 | |
|   );
 | |
|   bos.setOutputStream(ostream);
 | |
| 
 | |
|   let utf8 = new TextEncoder().encode(contents);
 | |
|   bos.writeByteArray(utf8);
 | |
|   ostream.QueryInterface(Ci.nsISafeOutputStream).finish();
 | |
|   ostream.close();
 | |
| }
 | |
| 
 | |
| function construct_file(suffix) {
 | |
|   let profileDirectory = Services.dirsvc.get("ProfD", Ci.nsIFile);
 | |
|   let file = profileDirectory.clone();
 | |
|   file.append(LATE_WRITE_PREFIX + suffix);
 | |
|   return file;
 | |
| }
 | |
| 
 | |
| function write_late_writes_file(stack, suffix) {
 | |
|   let file = construct_file(suffix);
 | |
|   let contents = N_MODULES + "\n";
 | |
|   for (let id in LOADED_MODULES) {
 | |
|     contents += id + " " + LOADED_MODULES[id] + "\n";
 | |
|   }
 | |
| 
 | |
|   contents += stack.length + "\n";
 | |
|   for (let element of stack) {
 | |
|     contents += element[0] + " " + element[1].toString(16) + "\n";
 | |
|   }
 | |
| 
 | |
|   write_string_to_file(file, contents);
 | |
| }
 | |
| 
 | |
| function run_test() {
 | |
|   do_get_profile();
 | |
| 
 | |
|   write_late_writes_file(STACK1, STACK_SUFFIX1);
 | |
|   write_late_writes_file(STACK2, STACK_SUFFIX2);
 | |
|   write_late_writes_file(STACK_BOGUS, STACK_BOGUS_SUFFIX);
 | |
| 
 | |
|   let lateWrites = Telemetry.lateWrites;
 | |
|   Assert.ok("memoryMap" in lateWrites);
 | |
|   Assert.equal(lateWrites.memoryMap.length, 0);
 | |
|   Assert.ok("stacks" in lateWrites);
 | |
|   Assert.equal(lateWrites.stacks.length, 0);
 | |
| 
 | |
|   do_test_pending();
 | |
|   Telemetry.asyncFetchTelemetryData(function() {
 | |
|     actual_test();
 | |
|   });
 | |
| }
 | |
| 
 | |
| function actual_test() {
 | |
|   Assert.ok(!construct_file(STACK_SUFFIX1).exists());
 | |
|   Assert.ok(!construct_file(STACK_SUFFIX2).exists());
 | |
|   Assert.ok(!construct_file(STACK_BOGUS_SUFFIX).exists());
 | |
| 
 | |
|   let lateWrites = Telemetry.lateWrites;
 | |
| 
 | |
|   Assert.ok("memoryMap" in lateWrites);
 | |
|   Assert.equal(lateWrites.memoryMap.length, N_MODULES);
 | |
|   for (let id in LOADED_MODULES) {
 | |
|     let matchingLibrary = lateWrites.memoryMap.filter(function(
 | |
|       library,
 | |
|       idx,
 | |
|       array
 | |
|     ) {
 | |
|       return library[1] == id;
 | |
|     });
 | |
|     Assert.equal(matchingLibrary.length, 1);
 | |
|     let library = matchingLibrary[0];
 | |
|     let name = library[0];
 | |
|     Assert.equal(LOADED_MODULES[id], name);
 | |
|   }
 | |
| 
 | |
|   Assert.ok("stacks" in lateWrites);
 | |
|   Assert.equal(lateWrites.stacks.length, 2);
 | |
|   let uneval_STACKS = [uneval(STACK1), uneval(STACK2)];
 | |
|   let first_stack = lateWrites.stacks[0];
 | |
|   let second_stack = lateWrites.stacks[1];
 | |
|   function stackChecker(canonicalStack) {
 | |
|     let unevalCanonicalStack = uneval(canonicalStack);
 | |
|     return function(obj, idx, array) {
 | |
|       return unevalCanonicalStack == obj;
 | |
|     };
 | |
|   }
 | |
|   Assert.equal(uneval_STACKS.filter(stackChecker(first_stack)).length, 1);
 | |
|   Assert.equal(uneval_STACKS.filter(stackChecker(second_stack)).length, 1);
 | |
| 
 | |
|   do_test_finished();
 | |
| }
 | 
