mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-25 22:01:30 +00:00
Merging mozilla-central into mozilla-inbound.
This commit is contained in:
commit
416f33776c
@ -26,6 +26,7 @@ Browser context menu subtest.
|
||||
<menu id="myMenu" type="context">
|
||||
<menuitem label="Plain item" onclick="document.getElementById('test-pagemenu').removeAttribute('hopeless');"></menuitem>
|
||||
<menuitem label="Disabled item" disabled></menuitem>
|
||||
<menuitem> Item w/ textContent</menuitem>
|
||||
<menu>
|
||||
<menuitem type="checkbox" label="Checkbox" checked></menuitem>
|
||||
</menu>
|
||||
|
@ -476,6 +476,7 @@ function runTest(testNum) {
|
||||
// Context menu for element with assigned content context menu
|
||||
checkContextMenu(["+Plain item", {type: "", icon: "", checked: false, disabled: false},
|
||||
"+Disabled item", {type: "", icon: "", checked: false, disabled: true},
|
||||
"+Item w/ textContent", {type: "", icon: "", checked: false, disabled: false},
|
||||
"---", null,
|
||||
"+Checkbox", {type: "checkbox", icon: "", checked: true, disabled: false},
|
||||
"---", null,
|
||||
|
@ -1,3 +1,4 @@
|
||||
# -*- makefile -*-
|
||||
#
|
||||
# ***** BEGIN LICENSE BLOCK *****
|
||||
# Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||
@ -21,6 +22,7 @@
|
||||
# the Initial Developer. All Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
# Joey Armstrong <joey@mozilla.com>
|
||||
#
|
||||
# Alternatively, the contents of this file may be used under the terms of
|
||||
# either of the GNU General Public License Version 2 or later (the "GPL"),
|
||||
@ -49,7 +51,15 @@ ifdef USE_ELF_HACK
|
||||
DIRS = elfhack
|
||||
endif
|
||||
|
||||
ifdef ENABLE_TESTS
|
||||
ifeq (,$(filter WINNT OS2,$(OS_ARCH)))
|
||||
DIRS += test
|
||||
endif # WIN
|
||||
endif # ENABLE_TESTS
|
||||
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
||||
libs:: $(srcdir)/run-mozilla.sh
|
||||
$(INSTALL) $< $(DIST)/bin
|
||||
|
||||
# EOF
|
||||
|
76
build/unix/test/Makefile.in
Normal file
76
build/unix/test/Makefile.in
Normal file
@ -0,0 +1,76 @@
|
||||
# -*- makefile -*-
|
||||
#
|
||||
# ***** BEGIN LICENSE BLOCK *****
|
||||
# Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||
#
|
||||
# The contents of this file are subject to the Mozilla Public License Version
|
||||
# 1.1 (the "License"); you may not use this file except in compliance with
|
||||
# the License. You may obtain a copy of the License at
|
||||
# http://www.mozilla.org/MPL/
|
||||
#
|
||||
# Software distributed under the License is distributed on an "AS IS" basis,
|
||||
# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||
# for the specific language governing rights and limitations under the
|
||||
# License.
|
||||
#
|
||||
# The Original Code is mozilla.org code.
|
||||
#
|
||||
# The Initial Developer of the Original Code is Mozilla Foundation.
|
||||
# Portions created by the Initial Developer are Copyright (C) 2011
|
||||
# the Initial Developer. All Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
# Joey Armstrong <joey@mozilla.com>
|
||||
#
|
||||
# Alternatively, the contents of this file may be used under the terms of
|
||||
# either of the GNU General Public License Version 2 or later (the "GPL"),
|
||||
# or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||
# in which case the provisions of the GPL or the LGPL are applicable instead
|
||||
# of those above. If you wish to allow use of your version of this file only
|
||||
# under the terms of either the GPL or the LGPL, and not to allow others to
|
||||
# use your version of this file under the terms of the MPL, indicate your
|
||||
# decision by deleting the provisions above and replace them with the notice
|
||||
# and other provisions required by the GPL or the LGPL. If you do not delete
|
||||
# the provisions above, a recipient may use your version of this file under
|
||||
# the terms of any one of the MPL, the GPL or the LGPL.
|
||||
#
|
||||
# ***** END LICENSE BLOCK *****
|
||||
|
||||
DEPTH = ../../..
|
||||
topsrcdir = @top_srcdir@
|
||||
srcdir = @srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
include $(DEPTH)/config/autoconf.mk
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
||||
##################################################
|
||||
## Gather a list of tests, generate timestamp deps
|
||||
##################################################
|
||||
TS=.ts
|
||||
ifneq (,$(findstring check,$(MAKECMDGOALS)))
|
||||
allsrc = $(wildcard $(srcdir)/*)
|
||||
tests2run = $(notdir $(filter %.tpl,$(allsrc)))
|
||||
check_targets += $(addprefix $(TS)/,$(tests2run))
|
||||
endif
|
||||
|
||||
check:: $(TS) $(check_targets)
|
||||
|
||||
#############################################
|
||||
# Only invoke tests when sources have changed
|
||||
#############################################
|
||||
$(TS)/%: $(srcdir)/%
|
||||
$(PERL) $(srcdir)/runtest $<
|
||||
@touch $@
|
||||
|
||||
#####################################################
|
||||
## Extra dep needed to synchronize parallel execution
|
||||
#####################################################
|
||||
$(TS): $(TS)/.done
|
||||
$(TS)/.done:
|
||||
$(MKDIR) -p $(dir $@)
|
||||
touch $@
|
||||
|
||||
GARBAGE_DIRS += $(TS)
|
||||
|
||||
# EOF
|
95
build/unix/test/runtest
Normal file
95
build/unix/test/runtest
Normal file
@ -0,0 +1,95 @@
|
||||
#!/usr/bin/env perl
|
||||
###########################################################################
|
||||
## Intent:
|
||||
## Test::Harness is a testing wrapper that will process output
|
||||
## from Test.pm module tests. Sumarize results, report stats
|
||||
## and exit with overall status for the testing suites.
|
||||
##
|
||||
## Run testing suite:
|
||||
## % make clean test
|
||||
## % perl runtest
|
||||
##
|
||||
## Run Individual tests
|
||||
## % perl tUtils0
|
||||
###########################################################################
|
||||
|
||||
##----------------------------##
|
||||
##---] CORE/CPAN INCLUDES [---##
|
||||
##----------------------------##
|
||||
use strict;
|
||||
use warnings;
|
||||
use Getopt::Long;
|
||||
|
||||
use Test::Harness;
|
||||
|
||||
##-------------------##
|
||||
##---] EXPORTS [---##
|
||||
##-------------------##
|
||||
our $VERSION = qw(1.0);
|
||||
use FindBin;
|
||||
|
||||
##-------------------##
|
||||
##---] GLOBALS [---##
|
||||
##-------------------##
|
||||
my %argv;
|
||||
|
||||
##----------------##
|
||||
##---] MAIN [---##
|
||||
##----------------##
|
||||
unless(GetOptions(\%argv,
|
||||
qw(debug|d)
|
||||
))
|
||||
{
|
||||
print "Usage: $0\n";
|
||||
print " --debug Enable debug mode\n";
|
||||
exit 1;
|
||||
}
|
||||
|
||||
if (2 > $Test::Harness::VERSION)
|
||||
{
|
||||
print "Unit tests will not be run, Test::Harness is too old\n"
|
||||
if ($argv{debug});
|
||||
exit 0;
|
||||
}
|
||||
|
||||
|
||||
my @tests;
|
||||
|
||||
########################################
|
||||
## Gather a list of tests if none passed
|
||||
########################################
|
||||
unless (@tests = @ARGV)
|
||||
{
|
||||
local *D;
|
||||
opendir(D, '.');
|
||||
while($_ = readdir(D)) {
|
||||
next unless /.t\S+$/;
|
||||
next if (/\.ts$/);
|
||||
push(@tests, $_);
|
||||
}
|
||||
closedir(D);
|
||||
}
|
||||
|
||||
###############################################
|
||||
## Glob a list of tests when directories passed
|
||||
###############################################
|
||||
my @tmp;
|
||||
foreach (@tests)
|
||||
{
|
||||
local *D;
|
||||
if (-d $_ && (my $dir = $_))
|
||||
{
|
||||
opendir(D, $_) || die "opendir(D) failed: $!";
|
||||
my @tests = grep(/\.t[^\.\s]+/o, readdir(D));
|
||||
closedir(D);
|
||||
push(@tmp, map{ join('/', $dir, $_); } @tests);
|
||||
} else {
|
||||
push(@tmp, $_);
|
||||
}
|
||||
}
|
||||
@tests = @tmp;
|
||||
|
||||
print "$0: @ARGV\n" if ($argv{debug});
|
||||
runtests(@tests);
|
||||
|
||||
# EOF
|
151
build/unix/test/uniq.tpl
Normal file
151
build/unix/test/uniq.tpl
Normal file
@ -0,0 +1,151 @@
|
||||
#!/usr/bin/env perl
|
||||
###########################################################################
|
||||
## Intent: Unit test to verify uniq.pl
|
||||
###########################################################################
|
||||
|
||||
##----------------------------##
|
||||
##---] CORE/CPAN INCLUDES [---##
|
||||
##----------------------------##
|
||||
use strict;
|
||||
use warnings;
|
||||
use Cwd;
|
||||
use Getopt::Long; # GetOptions
|
||||
|
||||
use Test;
|
||||
sub BEGIN { plan tests => 12 }
|
||||
|
||||
##-------------------##
|
||||
##---] EXPORTS [---##
|
||||
##-------------------##
|
||||
our $VERSION = qw(1.0);
|
||||
|
||||
##------------------##
|
||||
##---] INCLUDES [---##
|
||||
##------------------##
|
||||
use FindBin;
|
||||
|
||||
##-------------------##
|
||||
##---] GLOBALS [---##
|
||||
##-------------------##
|
||||
my %argv;
|
||||
|
||||
|
||||
###########################################################################
|
||||
## Intent: Run the arch command for output
|
||||
##
|
||||
## Returns:
|
||||
## 0 on success
|
||||
## $? command shell exit status
|
||||
###########################################################################
|
||||
sub uniq_pl
|
||||
{
|
||||
my $cmd = "perl $FindBin::RealBin/../uniq.pl @_";
|
||||
print "Running: $cmd\n" if ($argv{debug});
|
||||
my @tmp = `$cmd 2>&1`;
|
||||
my @output = map{ split(/\s+/o); } @tmp;
|
||||
wantarray ? @output : "@output";
|
||||
} # uniq_pl
|
||||
|
||||
###########################################################################
|
||||
## Intent:
|
||||
##
|
||||
## Returns:
|
||||
## 0 on success
|
||||
###########################################################################
|
||||
sub check_uniq
|
||||
{
|
||||
print STDERR "Running test: check_uniq\n" if ($argv{debug});
|
||||
|
||||
# TODO: improve test, uniq.pl regexpr handling not quite right
|
||||
|
||||
my @todo =
|
||||
(
|
||||
[ '', qw(a a/b a/b/c) ] => [ qw(a a/b a/b/c) ],
|
||||
[ '', qw(a/b a a/b/c) ] => [ qw(a/b a a/b/c) ],
|
||||
[ '', qw(a/b/c a/b a) ] => [ qw(a/b/c a/b a) ],
|
||||
|
||||
[ '', qw(a a/b a/b/c a/b a) ] => [ qw(a a/b a/b/c) ], # dup removal
|
||||
|
||||
[ '-s', qw(a a/b a/b/c) ] => [ qw(a a/b a/b/c) ],
|
||||
[ '-s', qw(a/b a a/b/c) ] => [ qw(a a/b a/b/c) ],
|
||||
[ '-s', qw(a/b/c a/b a) ] => [ qw(a a/b a/b/c) ],
|
||||
|
||||
[ '-r', qw(a a/b a/b/c) ] => [ qw(a) ],
|
||||
[ '-r', qw(a/b a a/b/c) ] => [ qw(a/b a) ],
|
||||
[ '-r', qw(a/b/c a/b a) ] => [ qw(a/b/c a/b a) ],
|
||||
|
||||
[ '-r', qw(. .. a/b ../a aa/bb) ] => [ qw(. .. a/b aa/bb) ],
|
||||
[ '-r', qw(.. a/b ../a . aa/bb) ] => [ qw(.. a/b . aa/bb) ],
|
||||
);
|
||||
|
||||
my $ct=1;
|
||||
while (@todo)
|
||||
{
|
||||
my ($a, $b) = splice(@todo, 0, 2);
|
||||
my @args = @{ $a };
|
||||
my @exp = @{ $b };
|
||||
|
||||
my @out = uniq_pl(@args);
|
||||
# compareExp(\@out, \@exp, 'Failed on line ' . __LINE__ . ", dataset $ct");
|
||||
if (0 && 7 == $ct)
|
||||
{
|
||||
print STDERR "\n";
|
||||
print STDERR map{ "args> $_\n" }@args;
|
||||
print STDERR "\n";
|
||||
print STDERR map{ "exp> $_\n" }@exp;
|
||||
print STDERR "\n";
|
||||
print STDERR map{ "out> $_\n" }@out;
|
||||
}
|
||||
|
||||
ok("@out", "@exp", 'Failed on line ' . __LINE__ . ", dataset $ct");
|
||||
$ct++;
|
||||
}
|
||||
|
||||
} # check_uniq
|
||||
|
||||
###########################################################################
|
||||
## Intent: Smoke tests for the unittests module
|
||||
###########################################################################
|
||||
sub smoke
|
||||
{
|
||||
print STDERR "Running test: smoke()\n" if ($argv{debug});
|
||||
} # smoke()
|
||||
|
||||
###########################################################################
|
||||
## Intent: Intitialize global test objects and consts
|
||||
###########################################################################
|
||||
sub init
|
||||
{
|
||||
print "Running: init()\n" if ($argv{debug});
|
||||
# testplan(24, 0);
|
||||
} # init()
|
||||
|
||||
##----------------##
|
||||
##---] MAIN [---##
|
||||
##----------------##
|
||||
unless(GetOptions(\%argv,
|
||||
qw(
|
||||
debug|d
|
||||
manual
|
||||
test=s@
|
||||
verbose
|
||||
)))
|
||||
{
|
||||
print "USAGE: $0\n";
|
||||
print " --debug Enable script debug mode\n";
|
||||
print " --fail Force a testing failure condition\n";
|
||||
print " --manual Also run disabled tests\n";
|
||||
print " --smoke Run smoke tests then exit\n";
|
||||
print " --test Run a list of tests by function name\n";
|
||||
print " --verbose Enable script verbose mode\n";
|
||||
exit 1;
|
||||
}
|
||||
|
||||
init();
|
||||
testbyname(@{ $argv{test} }) if ($argv{test});
|
||||
smoke();
|
||||
|
||||
check_uniq();
|
||||
ok(1, 0, 'Forced failure by command line arg --fail') if ($argv{fail});
|
||||
|
||||
# EOF
|
@ -22,6 +22,7 @@
|
||||
#
|
||||
# Contributor(s):
|
||||
# Christopher Seawood <cls@seawood.org>
|
||||
# Joey Armstrong <joey@mozilla.com>
|
||||
#
|
||||
# Alternatively, the contents of this file may be used under the terms of
|
||||
# either of the GNU General Public License Version 2 or later (the "GPL"),
|
||||
@ -37,27 +38,88 @@
|
||||
#
|
||||
# ***** END LICENSE BLOCK *****
|
||||
|
||||
use Getopt::Std;
|
||||
##----------------------------##
|
||||
##---] CORE/CPAN INCLUDES [---##
|
||||
##----------------------------##
|
||||
use strict;
|
||||
use warnings;
|
||||
use Getopt::Long;
|
||||
|
||||
getopts('rs');
|
||||
$regexp = 1 if (defined($opt_r));
|
||||
$sort = 1 if (defined($opt_s));
|
||||
##-------------------##
|
||||
##---] EXPORTS [---##
|
||||
##-------------------##
|
||||
our $VERSION = qw(1.1);
|
||||
|
||||
undef @out;
|
||||
if ($sort) {
|
||||
@in = sort @ARGV;
|
||||
} else {
|
||||
@in = @ARGV;
|
||||
##-------------------##
|
||||
##---] GLOBALS [---##
|
||||
##-------------------##
|
||||
my %argv;
|
||||
my $modver = $Getopt::Long::VERSION || 0;
|
||||
my $isOldGetopt = ($modver eq '2.25') ? 1 : 0;
|
||||
|
||||
###########################################################################
|
||||
## Intent: Script init function
|
||||
###########################################################################
|
||||
sub init
|
||||
{
|
||||
if ($isOldGetopt)
|
||||
{
|
||||
# mozilla.build/mingw perl in need of an upgrade
|
||||
# emulate Getopt::Long switch|short:init
|
||||
foreach (qw(debug regex sort))
|
||||
{
|
||||
if (defined($argv{$_}))
|
||||
{
|
||||
$argv{$_} ||= 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
} # init
|
||||
|
||||
##----------------##
|
||||
##---] MAIN [---##
|
||||
##----------------##
|
||||
my @args = ($isOldGetopt)
|
||||
? qw(debug|d regex|r sort|s)
|
||||
: qw(debug|d:1 regex|r:1 sort|s:1)
|
||||
;
|
||||
|
||||
unless(GetOptions(\%argv, @args))
|
||||
{
|
||||
print "Usage: $0\n";
|
||||
print " --sort Sort list elements early\n";
|
||||
print " --regex Exclude subdirs by pattern\n";
|
||||
}
|
||||
foreach $d (@in) {
|
||||
if ($regexp) {
|
||||
$found = 0;
|
||||
foreach $dir (@out) {
|
||||
$found++, last if ($d =~ m/^$dir\// || $d eq $dir);
|
||||
|
||||
init();
|
||||
my $debug = $argv{debug} || 0;
|
||||
|
||||
my %seen;
|
||||
my @out;
|
||||
my @in = ($argv{sort}) ? sort @ARGV : @ARGV;
|
||||
|
||||
foreach my $d (@in)
|
||||
{
|
||||
next if ($seen{$d}++);
|
||||
|
||||
print " arg is $d\n" if ($debug);
|
||||
|
||||
if ($argv{regex})
|
||||
{
|
||||
my $found = 0;
|
||||
foreach my $dir (@out)
|
||||
{
|
||||
my $dirM = quotemeta($dir);
|
||||
$found++, last if ($d eq $dir || $d =~ m!^${dirM}\/!);
|
||||
}
|
||||
print "Adding $d\n" if ($debug && !$found);
|
||||
push @out, $d if (!$found);
|
||||
} else {
|
||||
push @out, $d if (!grep(/^$d$/, @out));
|
||||
print "Adding: $d\n" if ($debug);
|
||||
push(@out, $d);
|
||||
}
|
||||
}
|
||||
|
||||
print "@out\n"
|
||||
|
||||
# EOF
|
||||
|
@ -1532,6 +1532,7 @@ $(XPIDL_GEN_DIR)/.done:
|
||||
|
||||
XPIDL_DEPS = \
|
||||
$(topsrcdir)/xpcom/idl-parser/header.py \
|
||||
$(topsrcdir)/xpcom/idl-parser/typelib.py \
|
||||
$(topsrcdir)/xpcom/idl-parser/xpidl.py \
|
||||
$(NULL)
|
||||
|
||||
@ -1547,9 +1548,13 @@ $(XPIDL_GEN_DIR)/%.h: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
||||
ifndef NO_GEN_XPT
|
||||
# generate intermediate .xpt files into $(XPIDL_GEN_DIR), then link
|
||||
# into $(XPIDL_MODULE).xpt and export it to $(FINAL_TARGET)/components.
|
||||
$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_COMPILE) $(XPIDL_GEN_DIR)/.done
|
||||
$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
||||
$(REPORT_BUILD)
|
||||
$(ELOG) $(XPIDL_COMPILE) -m typelib -w $(XPIDL_FLAGS) -e $@ -d $(MDDEPDIR)/$(@F).pp $(_VPATH_SRCS)
|
||||
$(PYTHON_PATH) \
|
||||
-I$(topsrcdir)/other-licenses/ply \
|
||||
-I$(topsrcdir)/xpcom/idl-parser \
|
||||
-I$(topsrcdir)/xpcom/typelib/xpt/tools \
|
||||
$(topsrcdir)/xpcom/idl-parser/typelib.py --cachedir=$(topsrcdir)/xpcom/idl-parser $(XPIDL_FLAGS) $(_VPATH_SRCS) -d $(MDDEPDIR)/$(@F).pp -o $@
|
||||
|
||||
# no need to link together if XPIDLSRCS contains only XPIDL_MODULE
|
||||
ifneq ($(XPIDL_MODULE).idl,$(strip $(XPIDLSRCS)))
|
||||
|
@ -336,4 +336,27 @@ private:
|
||||
PRPackedBool mDocumentParsingDone;
|
||||
};
|
||||
|
||||
class nsAutoScriptLoaderDisabler
|
||||
{
|
||||
public:
|
||||
nsAutoScriptLoaderDisabler(nsIDocument* aDoc)
|
||||
{
|
||||
mLoader = aDoc->ScriptLoader();
|
||||
mWasEnabled = mLoader->GetEnabled();
|
||||
if (mWasEnabled) {
|
||||
mLoader->SetEnabled(PR_FALSE);
|
||||
}
|
||||
}
|
||||
|
||||
~nsAutoScriptLoaderDisabler()
|
||||
{
|
||||
if (mWasEnabled) {
|
||||
mLoader->SetEnabled(PR_TRUE);
|
||||
}
|
||||
}
|
||||
|
||||
PRBool mWasEnabled;
|
||||
nsRefPtr<nsScriptLoader> mLoader;
|
||||
};
|
||||
|
||||
#endif //__nsScriptLoader_h__
|
||||
|
@ -1195,7 +1195,7 @@ nsTreeSanitizer::SanitizeAttributes(mozilla::dom::Element* aElement,
|
||||
rv = NS_OK;
|
||||
const nsAttrName* attrName = aElement->GetAttrNameAt(i);
|
||||
PRInt32 attrNs = attrName->NamespaceID();
|
||||
nsIAtom* attrLocal = attrName->LocalName();
|
||||
nsCOMPtr<nsIAtom> attrLocal = attrName->LocalName();
|
||||
|
||||
if (kNameSpaceID_None == attrNs) {
|
||||
if (aAllowStyle && nsGkAtoms::style == attrLocal) {
|
||||
|
@ -2183,17 +2183,17 @@ class WebGLMemoryReporter
|
||||
typedef nsTArray<const WebGLContext*> ContextsArrayType;
|
||||
ContextsArrayType mContexts;
|
||||
|
||||
nsIMemoryReporter *mTextureMemoryUsageReporter;
|
||||
nsIMemoryReporter *mTextureCountReporter;
|
||||
nsIMemoryReporter *mBufferMemoryUsageReporter;
|
||||
nsIMemoryReporter *mBufferCacheMemoryUsageReporter;
|
||||
nsIMemoryReporter *mBufferCountReporter;
|
||||
nsIMemoryReporter *mRenderbufferMemoryUsageReporter;
|
||||
nsIMemoryReporter *mRenderbufferCountReporter;
|
||||
nsIMemoryReporter *mShaderSourcesSizeReporter;
|
||||
nsIMemoryReporter *mShaderTranslationLogsSizeReporter;
|
||||
nsIMemoryReporter *mShaderCountReporter;
|
||||
nsIMemoryReporter *mContextCountReporter;
|
||||
nsCOMPtr<nsIMemoryReporter> mTextureMemoryUsageReporter;
|
||||
nsCOMPtr<nsIMemoryReporter> mTextureCountReporter;
|
||||
nsCOMPtr<nsIMemoryReporter> mBufferMemoryUsageReporter;
|
||||
nsCOMPtr<nsIMemoryReporter> mBufferCacheMemoryUsageReporter;
|
||||
nsCOMPtr<nsIMemoryReporter> mBufferCountReporter;
|
||||
nsCOMPtr<nsIMemoryReporter> mRenderbufferMemoryUsageReporter;
|
||||
nsCOMPtr<nsIMemoryReporter> mRenderbufferCountReporter;
|
||||
nsCOMPtr<nsIMemoryReporter> mShaderSourcesSizeReporter;
|
||||
nsCOMPtr<nsIMemoryReporter> mShaderTranslationLogsSizeReporter;
|
||||
nsCOMPtr<nsIMemoryReporter> mShaderCountReporter;
|
||||
nsCOMPtr<nsIMemoryReporter> mContextCountReporter;
|
||||
|
||||
static WebGLMemoryReporter* UniqueInstance();
|
||||
|
||||
|
@ -765,6 +765,8 @@ nsGenericHTMLElement::SetInnerHTML(const nsAString& aInnerHTML)
|
||||
RemoveChildAt(0, PR_TRUE);
|
||||
}
|
||||
|
||||
nsAutoScriptLoaderDisabler sld(doc);
|
||||
|
||||
nsCOMPtr<nsIDOMDocumentFragment> df;
|
||||
|
||||
if (doc->IsHTML()) {
|
||||
@ -828,6 +830,10 @@ nsGenericHTMLElement::InsertAdjacentHTML(const nsAString& aPosition,
|
||||
nsIDocument* doc = GetOwnerDoc();
|
||||
NS_ENSURE_STATE(doc);
|
||||
|
||||
// Needed when insertAdjacentHTML is used in combination with contenteditable
|
||||
mozAutoDocUpdate updateBatch(doc, UPDATE_CONTENT_MODEL, PR_TRUE);
|
||||
nsAutoScriptLoaderDisabler sld(doc);
|
||||
|
||||
// Batch possible DOMSubtreeModified events.
|
||||
mozAutoSubtreeModified subtree(doc, nsnull);
|
||||
|
||||
@ -836,9 +842,6 @@ nsGenericHTMLElement::InsertAdjacentHTML(const nsAString& aPosition,
|
||||
(position == eBeforeEnd ||
|
||||
(position == eAfterEnd && !GetNextSibling()) ||
|
||||
(position == eAfterBegin && !GetFirstChild()))) {
|
||||
// Needed when insertAdjacentHTML is used in combination with contenteditable
|
||||
mozAutoDocUpdate updateBatch(doc, UPDATE_CONTENT_MODEL, PR_TRUE);
|
||||
|
||||
PRInt32 oldChildCount = destination->GetChildCount();
|
||||
PRInt32 contextNs = destination->GetNameSpaceID();
|
||||
nsIAtom* contextLocal = destination->Tag();
|
||||
@ -869,6 +872,11 @@ nsGenericHTMLElement::InsertAdjacentHTML(const nsAString& aPosition,
|
||||
nsCOMPtr<nsINode> fragment = do_QueryInterface(df);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
// Suppress assertion about node removal mutation events that can't have
|
||||
// listeners anyway, because no one has had the chance to register mutation
|
||||
// listeners on the fragment that comes from the parser.
|
||||
nsAutoScriptBlockerSuppressNodeRemoved scriptBlocker;
|
||||
|
||||
switch (position) {
|
||||
case eBeforeBegin:
|
||||
destination->InsertBefore(fragment, this, &rv);
|
||||
|
@ -1103,6 +1103,25 @@ protected:
|
||||
return SetAttrHelper(nsGkAtoms::_atom, aValue); \
|
||||
}
|
||||
|
||||
/**
|
||||
* This macro is similar to NS_IMPL_STRING_ATTR except that the getter method
|
||||
* falls back to an alternative method if the content attribute isn't set.
|
||||
*/
|
||||
#define NS_IMPL_STRING_ATTR_WITH_FALLBACK(_class, _method, _atom, _fallback) \
|
||||
NS_IMETHODIMP \
|
||||
_class::Get##_method(nsAString& aValue) \
|
||||
{ \
|
||||
if (!GetAttr(kNameSpaceID_None, nsGkAtoms::_atom, aValue)) { \
|
||||
_fallback(aValue); \
|
||||
} \
|
||||
return NS_OK; \
|
||||
} \
|
||||
NS_IMETHODIMP \
|
||||
_class::Set##_method(const nsAString& aValue) \
|
||||
{ \
|
||||
return SetAttrHelper(nsGkAtoms::_atom, aValue); \
|
||||
}
|
||||
|
||||
/**
|
||||
* A macro to implement the getter and setter for a given boolean
|
||||
* valued content property. The method uses the generic GetAttr and
|
||||
|
@ -248,7 +248,8 @@ nsHTMLMenuItemElement::Clone(nsINodeInfo *aNodeInfo, nsINode **aResult) const
|
||||
|
||||
NS_IMPL_ENUM_ATTR_DEFAULT_VALUE(nsHTMLMenuItemElement, Type, type,
|
||||
kMenuItemDefaultType->tag)
|
||||
NS_IMPL_STRING_ATTR(nsHTMLMenuItemElement, Label, label)
|
||||
// GetText returns a whitespace compressed .textContent value.
|
||||
NS_IMPL_STRING_ATTR_WITH_FALLBACK(nsHTMLMenuItemElement, Label, label, GetText)
|
||||
NS_IMPL_URI_ATTR(nsHTMLMenuItemElement, Icon, icon)
|
||||
NS_IMPL_BOOL_ATTR(nsHTMLMenuItemElement, Disabled, disabled)
|
||||
NS_IMPL_BOOL_ATTR(nsHTMLMenuItemElement, DefaultChecked, checked)
|
||||
@ -408,6 +409,16 @@ nsHTMLMenuItemElement::DoneCreatingElement()
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
nsHTMLMenuItemElement::GetText(nsAString& aText)
|
||||
{
|
||||
nsAutoString text;
|
||||
nsContentUtils::GetNodeTextContent(this, PR_FALSE, text);
|
||||
|
||||
text.CompressWhitespace(PR_TRUE, PR_TRUE);
|
||||
aText = text;
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsHTMLMenuItemElement::AfterSetAttr(PRInt32 aNameSpaceID, nsIAtom* aName,
|
||||
const nsAString* aValue, PRBool aNotify)
|
||||
|
@ -100,6 +100,8 @@ public:
|
||||
PRBool IsChecked() const { return mChecked; }
|
||||
PRBool IsCheckedDirty() const { return mCheckedDirty; }
|
||||
|
||||
void GetText(nsAString& aText);
|
||||
|
||||
protected:
|
||||
virtual nsresult AfterSetAttr(PRInt32 aNamespaceID, nsIAtom* aName,
|
||||
const nsAString* aValue, PRBool aNotify);
|
||||
|
@ -67,26 +67,6 @@
|
||||
|
||||
using namespace mozilla::dom;
|
||||
|
||||
/**
|
||||
* This macro is similar to NS_IMPL_STRING_ATTR except that the getter method
|
||||
* falls back to GetText if the content attribute isn't set. GetText returns a
|
||||
* whitespace compressed .textContent value.
|
||||
*/
|
||||
#define NS_IMPL_STRING_ATTR_WITH_TEXTCONTENT(_class, _method, _atom) \
|
||||
NS_IMETHODIMP \
|
||||
_class::Get##_method(nsAString& aValue) \
|
||||
{ \
|
||||
if (!GetAttr(kNameSpaceID_None, nsGkAtoms::_atom, aValue)) { \
|
||||
GetText(aValue); \
|
||||
} \
|
||||
return NS_OK; \
|
||||
} \
|
||||
NS_IMETHODIMP \
|
||||
_class::Set##_method(const nsAString& aValue) \
|
||||
{ \
|
||||
return SetAttrHelper(nsGkAtoms::_atom, aValue); \
|
||||
}
|
||||
|
||||
/**
|
||||
* Implementation of <option>
|
||||
*/
|
||||
@ -209,8 +189,9 @@ nsHTMLOptionElement::SetSelected(PRBool aValue)
|
||||
}
|
||||
|
||||
NS_IMPL_BOOL_ATTR(nsHTMLOptionElement, DefaultSelected, selected)
|
||||
NS_IMPL_STRING_ATTR_WITH_TEXTCONTENT(nsHTMLOptionElement, Label, label)
|
||||
NS_IMPL_STRING_ATTR_WITH_TEXTCONTENT(nsHTMLOptionElement, Value, value)
|
||||
// GetText returns a whitespace compressed .textContent value.
|
||||
NS_IMPL_STRING_ATTR_WITH_FALLBACK(nsHTMLOptionElement, Label, label, GetText)
|
||||
NS_IMPL_STRING_ATTR_WITH_FALLBACK(nsHTMLOptionElement, Value, value, GetText)
|
||||
NS_IMPL_BOOL_ATTR(nsHTMLOptionElement, Disabled, disabled)
|
||||
|
||||
NS_IMETHODIMP
|
||||
|
@ -281,6 +281,8 @@ _TEST_FILES = \
|
||||
test_restore_from_parser_fragment.html \
|
||||
test_bug617528.html \
|
||||
test_checked.html \
|
||||
test_bug677658.html \
|
||||
test_bug677463.html \
|
||||
$(NULL)
|
||||
|
||||
libs:: $(_TEST_FILES)
|
||||
|
39
content/html/content/test/test_bug677463.html
Normal file
39
content/html/content/test/test_bug677463.html
Normal file
@ -0,0 +1,39 @@
|
||||
<!DOCTYPE HTML>
|
||||
<html>
|
||||
<!--
|
||||
https://bugzilla.mozilla.org/show_bug.cgi?id=677463
|
||||
-->
|
||||
<head>
|
||||
<title>Test for Bug 677463</title>
|
||||
<script type="application/javascript" src="/MochiKit/packed.js"></script>
|
||||
<script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
|
||||
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
|
||||
</head>
|
||||
<body>
|
||||
<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=677463">Mozilla Bug 677463</a>
|
||||
<p id="display"></p>
|
||||
<pre id="test">
|
||||
<script type="application/javascript">
|
||||
|
||||
/** Test for Bug 677463 **/
|
||||
|
||||
var o = document.createElement("option");
|
||||
var m = document.createElement("menuitem");
|
||||
is(o.label, m.label, "Should have same labels");
|
||||
o.textContent = " ";
|
||||
is(o.label, m.label, "Should have same labels");
|
||||
m.textContent = " ";
|
||||
is(o.label, m.label, "Should have same labels");
|
||||
o.textContent = " foo";
|
||||
isnot(o.label, m.label, "Shouldn't have same labels");
|
||||
m.textContent = "foo ";
|
||||
is(o.label, m.label, "Should have same labels");
|
||||
m.label = "bar";
|
||||
isnot(o.label, m.label, "Shouldn't have same labels");
|
||||
o.label = "bar";
|
||||
is(o.label, m.label, "Should have same labels");
|
||||
|
||||
</script>
|
||||
</pre>
|
||||
</body>
|
||||
</html>
|
42
content/html/content/test/test_bug677658.html
Normal file
42
content/html/content/test/test_bug677658.html
Normal file
@ -0,0 +1,42 @@
|
||||
<!DOCTYPE HTML>
|
||||
<html>
|
||||
<!--
|
||||
https://bugzilla.mozilla.org/show_bug.cgi?id=677658
|
||||
-->
|
||||
<head>
|
||||
<title>Test for Bug 677658</title>
|
||||
<script type="application/javascript" src="/MochiKit/packed.js"></script>
|
||||
<script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
|
||||
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
|
||||
</head>
|
||||
<body onload="test()">
|
||||
<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=677658">Mozilla Bug 677658</a>
|
||||
<p id="display"></p>
|
||||
<div id="content" style="display: none">
|
||||
|
||||
</div>
|
||||
<pre id="test">
|
||||
<script type="application/javascript"><!--
|
||||
|
||||
/** Test for Bug 677658 **/
|
||||
|
||||
SimpleTest.waitForExplicitFinish();
|
||||
|
||||
function testDone() {
|
||||
ok(window.testPassed, "Script shouldn't have run!");
|
||||
SimpleTest.finish();
|
||||
}
|
||||
|
||||
function test() {
|
||||
window.testPassed = true;
|
||||
document.getElementById("testtarget").innerHTML =
|
||||
"<script async src='data:text/plain, window.testPassed = false;'></script>";
|
||||
SimpleTest.executeSoon(testDone);
|
||||
}
|
||||
|
||||
// -->
|
||||
</script>
|
||||
</pre>
|
||||
<div id="testtarget"></div>
|
||||
</body>
|
||||
</html>
|
@ -60,7 +60,11 @@ ENABLE_CXX_EXCEPTIONS=1
|
||||
OS_COMPILE_CFLAGS = $(OS_CPPFLAGS)
|
||||
OS_COMPILE_CXXFLAGS = $(OS_CPPFLAGS)
|
||||
|
||||
LOCAL_INCLUDES += -I$(srcdir)/../../include -I$(srcdir)/.. -I"$(DXSDK_DIR)/include"
|
||||
LOCAL_INCLUDES = \
|
||||
-I$(srcdir)/../../include \
|
||||
-I$(srcdir)/.. \
|
||||
-I"$(DXSDK_DIR)/include" \
|
||||
-I"$(MOZ_DIRECTX_SDK_PATH)/include" \
|
||||
|
||||
VPATH += $(srcdir)/.. \
|
||||
$(srcdir)/../compiler \
|
||||
|
@ -60,7 +60,12 @@ ENABLE_CXX_EXCEPTIONS=1
|
||||
OS_COMPILE_CFLAGS = $(OS_CPPFLAGS)
|
||||
OS_COMPILE_CXXFLAGS = $(OS_CPPFLAGS)
|
||||
|
||||
LOCAL_INCLUDES = -I$(srcdir)/../../include -I$(srcdir)/.. -I"$(DXSDK_DIR)/include"
|
||||
LOCAL_INCLUDES = \
|
||||
-I$(srcdir)/../../include \
|
||||
-I$(srcdir)/.. \
|
||||
-I"$(DXSDK_DIR)/include" \
|
||||
-I"$(MOZ_DIRECTX_SDK_PATH)/include" \
|
||||
|
||||
|
||||
VPATH += $(srcdir)/..
|
||||
VPATH += $(srcdir)/../compiler
|
||||
|
@ -22,6 +22,7 @@
|
||||
#
|
||||
# Contributor(s):
|
||||
# Christopher Seawood <cls@seawood.org>
|
||||
# Joey Armstrong <joey@mozilla.com>
|
||||
#
|
||||
# Alternatively, the contents of this file may be used under the terms of
|
||||
# either of the GNU General Public License Version 2 or later (the "GPL"),
|
||||
@ -37,27 +38,88 @@
|
||||
#
|
||||
# ***** END LICENSE BLOCK *****
|
||||
|
||||
use Getopt::Std;
|
||||
##----------------------------##
|
||||
##---] CORE/CPAN INCLUDES [---##
|
||||
##----------------------------##
|
||||
use strict;
|
||||
use warnings;
|
||||
use Getopt::Long;
|
||||
|
||||
getopts('rs');
|
||||
$regexp = 1 if (defined($opt_r));
|
||||
$sort = 1 if (defined($opt_s));
|
||||
##-------------------##
|
||||
##---] EXPORTS [---##
|
||||
##-------------------##
|
||||
our $VERSION = qw(1.1);
|
||||
|
||||
undef @out;
|
||||
if ($sort) {
|
||||
@in = sort @ARGV;
|
||||
} else {
|
||||
@in = @ARGV;
|
||||
##-------------------##
|
||||
##---] GLOBALS [---##
|
||||
##-------------------##
|
||||
my %argv;
|
||||
my $modver = $Getopt::Long::VERSION || 0;
|
||||
my $isOldGetopt = ($modver eq '2.25') ? 1 : 0;
|
||||
|
||||
###########################################################################
|
||||
## Intent: Script init function
|
||||
###########################################################################
|
||||
sub init
|
||||
{
|
||||
if ($isOldGetopt)
|
||||
{
|
||||
# mozilla.build/mingw perl in need of an upgrade
|
||||
# emulate Getopt::Long switch|short:init
|
||||
foreach (qw(debug regex sort))
|
||||
{
|
||||
if (defined($argv{$_}))
|
||||
{
|
||||
$argv{$_} ||= 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
} # init
|
||||
|
||||
##----------------##
|
||||
##---] MAIN [---##
|
||||
##----------------##
|
||||
my @args = ($isOldGetopt)
|
||||
? qw(debug|d regex|r sort|s)
|
||||
: qw(debug|d:1 regex|r:1 sort|s:1)
|
||||
;
|
||||
|
||||
unless(GetOptions(\%argv, @args))
|
||||
{
|
||||
print "Usage: $0\n";
|
||||
print " --sort Sort list elements early\n";
|
||||
print " --regex Exclude subdirs by pattern\n";
|
||||
}
|
||||
foreach $d (@in) {
|
||||
if ($regexp) {
|
||||
$found = 0;
|
||||
foreach $dir (@out) {
|
||||
$found++, last if ($d =~ m/^$dir\// || $d eq $dir);
|
||||
|
||||
init();
|
||||
my $debug = $argv{debug} || 0;
|
||||
|
||||
my %seen;
|
||||
my @out;
|
||||
my @in = ($argv{sort}) ? sort @ARGV : @ARGV;
|
||||
|
||||
foreach my $d (@in)
|
||||
{
|
||||
next if ($seen{$d}++);
|
||||
|
||||
print " arg is $d\n" if ($debug);
|
||||
|
||||
if ($argv{regex})
|
||||
{
|
||||
my $found = 0;
|
||||
foreach my $dir (@out)
|
||||
{
|
||||
my $dirM = quotemeta($dir);
|
||||
$found++, last if ($d eq $dir || $d =~ m!^${dirM}\/!);
|
||||
}
|
||||
print "Adding $d\n" if ($debug && !$found);
|
||||
push @out, $d if (!$found);
|
||||
} else {
|
||||
push @out, $d if (!grep(/^$d$/, @out));
|
||||
print "Adding: $d\n" if ($debug);
|
||||
push(@out, $d);
|
||||
}
|
||||
}
|
||||
|
||||
print "@out\n"
|
||||
|
||||
# EOF
|
||||
|
@ -1532,6 +1532,7 @@ $(XPIDL_GEN_DIR)/.done:
|
||||
|
||||
XPIDL_DEPS = \
|
||||
$(topsrcdir)/xpcom/idl-parser/header.py \
|
||||
$(topsrcdir)/xpcom/idl-parser/typelib.py \
|
||||
$(topsrcdir)/xpcom/idl-parser/xpidl.py \
|
||||
$(NULL)
|
||||
|
||||
@ -1547,9 +1548,13 @@ $(XPIDL_GEN_DIR)/%.h: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
||||
ifndef NO_GEN_XPT
|
||||
# generate intermediate .xpt files into $(XPIDL_GEN_DIR), then link
|
||||
# into $(XPIDL_MODULE).xpt and export it to $(FINAL_TARGET)/components.
|
||||
$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_COMPILE) $(XPIDL_GEN_DIR)/.done
|
||||
$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
|
||||
$(REPORT_BUILD)
|
||||
$(ELOG) $(XPIDL_COMPILE) -m typelib -w $(XPIDL_FLAGS) -e $@ -d $(MDDEPDIR)/$(@F).pp $(_VPATH_SRCS)
|
||||
$(PYTHON_PATH) \
|
||||
-I$(topsrcdir)/other-licenses/ply \
|
||||
-I$(topsrcdir)/xpcom/idl-parser \
|
||||
-I$(topsrcdir)/xpcom/typelib/xpt/tools \
|
||||
$(topsrcdir)/xpcom/idl-parser/typelib.py --cachedir=$(topsrcdir)/xpcom/idl-parser $(XPIDL_FLAGS) $(_VPATH_SRCS) -d $(MDDEPDIR)/$(@F).pp -o $@
|
||||
|
||||
# no need to link together if XPIDLSRCS contains only XPIDL_MODULE
|
||||
ifneq ($(XPIDL_MODULE).idl,$(strip $(XPIDLSRCS)))
|
||||
|
@ -141,10 +141,14 @@ struct RuleValue : RuleSelectorPair {
|
||||
|
||||
// Uses any of the sets of ops below.
|
||||
struct RuleHashTableEntry : public PLDHashEntryHdr {
|
||||
// If you add members that have heap allocated memory be sure to change the
|
||||
// logic in RuleHashTableSizeOfEnumerator.
|
||||
nsTArray<RuleValue> mRules;
|
||||
};
|
||||
|
||||
struct RuleHashTagTableEntry : public RuleHashTableEntry {
|
||||
// If you add members that have heap allocated memory be sure to change the
|
||||
// logic in RuleHash::SizeOf.
|
||||
nsCOMPtr<nsIAtom> mTag;
|
||||
};
|
||||
|
||||
@ -734,6 +738,12 @@ RuleHash::SizeOf() const
|
||||
|
||||
n += mUniversalRules.SizeOf();
|
||||
|
||||
const PLArena* current = &mArena.first;
|
||||
while (current) {
|
||||
n += current->limit - current->base;
|
||||
current = current->next;
|
||||
}
|
||||
|
||||
return n;
|
||||
}
|
||||
|
||||
|
@ -38,7 +38,7 @@
|
||||
#
|
||||
# ***** END LICENSE BLOCK ***** */
|
||||
|
||||
import re, sys, os, os.path, logging, shutil, signal, math
|
||||
import re, sys, os, os.path, logging, shutil, signal, math, time
|
||||
from glob import glob
|
||||
from optparse import OptionParser
|
||||
from subprocess import Popen, PIPE, STDOUT
|
||||
@ -496,6 +496,7 @@ class XPCShellTests(object):
|
||||
|
||||
try:
|
||||
self.log.info("TEST-INFO | %s | running test ..." % name)
|
||||
startTime = time.time()
|
||||
|
||||
proc = self.launchProcess(cmdH + cmdT + self.xpcsRunArgs,
|
||||
stdout=pStdout, stderr=pStderr, env=self.env, cwd=testdir)
|
||||
@ -529,7 +530,8 @@ class XPCShellTests(object):
|
||||
print_stdout(stdout)
|
||||
self.failCount += 1
|
||||
else:
|
||||
self.log.info("TEST-%s | %s | test passed" % ("PASS" if expected else "KNOWN-FAIL", name))
|
||||
timeTaken = (time.time() - startTime) * 1000
|
||||
self.log.info("TEST-%s | %s | test passed (time: %.3fms)" % ("PASS" if expected else "KNOWN-FAIL", name, timeTaken))
|
||||
if verbose:
|
||||
print_stdout(stdout)
|
||||
if expected:
|
||||
|
@ -247,6 +247,15 @@ function populateGraphicsSection() {
|
||||
pushInfoRow(trGraphics, "driverDate", gfxInfo.adapterDriverDate);
|
||||
|
||||
#ifdef XP_WIN
|
||||
pushInfoRow(trGraphics, "adapterDescription2", gfxInfo.adapterDescription2);
|
||||
pushInfoRow(trGraphics, "adapterVendorID2", hexValueToString(gfxInfo.adapterVendorID2));
|
||||
pushInfoRow(trGraphics, "adapterDeviceID2", hexValueToString(gfxInfo.adapterDeviceID2));
|
||||
pushInfoRow(trGraphics, "adapterRAM2", gfxInfo.adapterRAM2);
|
||||
pushInfoRow(trGraphics, "adapterDrivers2", gfxInfo.adapterDriver2);
|
||||
pushInfoRow(trGraphics, "driverVersion2", gfxInfo.adapterDriverVersion2);
|
||||
pushInfoRow(trGraphics, "driverDate2", gfxInfo.adapterDriverDate2);
|
||||
pushInfoRow(trGraphics, "isGPU2Active", gfxInfo.isGPU2Active);
|
||||
|
||||
var version = Cc["@mozilla.org/system-info;1"]
|
||||
.getService(Ci.nsIPropertyBag2)
|
||||
.getProperty("version");
|
||||
|
@ -31,4 +31,12 @@ adapterDrivers = Adapter Drivers
|
||||
adapterRAM = Adapter RAM
|
||||
driverVersion = Driver Version
|
||||
driverDate = Driver Date
|
||||
adapterDescription2 = Adapter Description (GPU #2)
|
||||
adapterVendorID2 = Vendor ID (GPU #2)
|
||||
adapterDeviceID2 = Device ID (GPU #2)
|
||||
adapterDrivers2 = Adapter Drivers (GPU #2)
|
||||
adapterRAM2 = Adapter RAM (GPU #2)
|
||||
driverVersion2 = Driver Version (GPU #2)
|
||||
driverDate2 = Driver Date (GPU #2)
|
||||
isGPU2Active = GPU #2 Active
|
||||
webglRenderer = WebGL Renderer
|
||||
|
@ -56,6 +56,10 @@
|
||||
* to invoke the original function (so address of trampoline is
|
||||
* returned).
|
||||
*
|
||||
* When the WindowsDllInterceptor class is destructed, OrigFunction is
|
||||
* patched again to jump directly to the trampoline instead of going
|
||||
* through the hook function. As such, re-intercepting the same function
|
||||
* won't work, as jump instructions are not supported.
|
||||
*/
|
||||
|
||||
class WindowsDllInterceptor
|
||||
@ -71,6 +75,39 @@ public:
|
||||
Init(modulename, nhooks);
|
||||
}
|
||||
|
||||
~WindowsDllInterceptor() {
|
||||
int i;
|
||||
byteptr_t p;
|
||||
for (i = 0, p = mHookPage; i < mCurHooks; i++, p += kHookSize) {
|
||||
#if defined(_M_IX86)
|
||||
size_t nBytes = 1 + sizeof(intptr_t);
|
||||
#elif defined(_M_X64)
|
||||
size_t nBytes = 2 + sizeof(intptr_t);
|
||||
#else
|
||||
#error "Unknown processor type"
|
||||
#endif
|
||||
byteptr_t origBytes = *((byteptr_t *)p);
|
||||
// ensure we can modify the original code
|
||||
DWORD op;
|
||||
if (!VirtualProtectEx(GetCurrentProcess(), origBytes, nBytes, PAGE_EXECUTE_READWRITE, &op)) {
|
||||
//printf ("VirtualProtectEx failed! %d\n", GetLastError());
|
||||
continue;
|
||||
}
|
||||
// Remove the hook by making the original function jump directly
|
||||
// in the trampoline.
|
||||
intptr_t dest = (intptr_t)(p + sizeof(void *));
|
||||
#if defined(_M_IX86)
|
||||
*((intptr_t*)(origBytes+1)) = dest - (intptr_t)(origBytes+5); // target displacement
|
||||
#elif defined(_M_X64)
|
||||
*((intptr_t*)(origBytes+2)) = dest;
|
||||
#else
|
||||
#error "Unknown processor type"
|
||||
#endif
|
||||
// restore protection; if this fails we can't really do anything about it
|
||||
VirtualProtectEx(GetCurrentProcess(), origBytes, nBytes, op, &op);
|
||||
}
|
||||
}
|
||||
|
||||
void Init(const char *modulename, int nhooks = 0) {
|
||||
if (mModule)
|
||||
return;
|
||||
@ -301,6 +338,11 @@ protected:
|
||||
return 0;
|
||||
}
|
||||
|
||||
// We keep the address of the original function in the first bytes of
|
||||
// the trampoline buffer
|
||||
*((void **)tramp) = origFunction;
|
||||
tramp += sizeof(void *);
|
||||
|
||||
memcpy(tramp, origFunction, nBytes);
|
||||
|
||||
// OrigFunction+N, the target of the trampoline
|
||||
|
@ -45,18 +45,19 @@ MODULE = test_xulapp
|
||||
|
||||
|
||||
CPPSRCS = \
|
||||
TestXREMakeCommandLineWin.cpp \
|
||||
$(NULL)
|
||||
TestXREMakeCommandLineWin.cpp \
|
||||
TestDllInterceptor.cpp \
|
||||
$(NULL)
|
||||
|
||||
OS_LIBS += $(call EXPAND_LIBNAME,comctl32 ws2_32 shell32)
|
||||
|
||||
SIMPLE_PROGRAMS = $(CPPSRCS:.cpp=$(BIN_SUFFIX))
|
||||
|
||||
LOCAL_INCLUDES += \
|
||||
-I$(srcdir) \
|
||||
-I$(topsrcdir)/toolkit/xre \
|
||||
-I$(topsrcdir)/config \
|
||||
$(NULL)
|
||||
-I$(srcdir) \
|
||||
-I$(topsrcdir)/toolkit/xre \
|
||||
-I$(topsrcdir)/config \
|
||||
$(NULL)
|
||||
|
||||
MOZ_WINCONSOLE = 1
|
||||
|
||||
@ -70,3 +71,5 @@ libs:: TestXREMakeCommandLineWin.ini
|
||||
check::
|
||||
@echo "Running TestXREMakeCommandLineWin tests"
|
||||
@$(RUN_TEST_PROGRAM) $(FINAL_TARGET)/TestXREMakeCommandLineWin.exe
|
||||
@echo "Running TestDllInterceptor tests"
|
||||
@$(RUN_TEST_PROGRAM) $(FINAL_TARGET)/TestDllInterceptor.exe
|
||||
|
118
toolkit/xre/test/win/TestDllInterceptor.cpp
Normal file
118
toolkit/xre/test/win/TestDllInterceptor.cpp
Normal file
@ -0,0 +1,118 @@
|
||||
/* ***** BEGIN LICENSE BLOCK *****
|
||||
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||
*
|
||||
* The contents of this file are subject to the Mozilla Public License Version
|
||||
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
* http://www.mozilla.org/MPL/
|
||||
*
|
||||
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||
* for the specific language governing rights and limitations under the
|
||||
* License.
|
||||
*
|
||||
* The Original Code is mozilla.org
|
||||
*
|
||||
* The Initial Developer of the Original Code is
|
||||
* Mozilla Foundation
|
||||
* Portions created by the Initial Developer are Copyright (C) 2011
|
||||
* the Initial Developer. All Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Mike Hommey <mh@glandium.org>
|
||||
*
|
||||
* Alternatively, the contents of this file may be used under the terms of
|
||||
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||||
* of those above. If you wish to allow use of your version of this file only
|
||||
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||||
* use your version of this file under the terms of the MPL, indicate your
|
||||
* decision by deleting the provisions above and replace them with the notice
|
||||
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||||
* the provisions above, a recipient may use your version of this file under
|
||||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
|
||||
#include <stdio.h>
|
||||
#include "nsWindowsDllInterceptor.h"
|
||||
|
||||
static bool patched_func_called = false;
|
||||
|
||||
static BOOL (WINAPI *orig_GetVersionExA)(__inout LPOSVERSIONINFO);
|
||||
|
||||
static BOOL WINAPI
|
||||
patched_GetVersionExA(__inout LPOSVERSIONINFO lpVersionInfo)
|
||||
{
|
||||
patched_func_called = true;
|
||||
return orig_GetVersionExA(lpVersionInfo);
|
||||
}
|
||||
|
||||
bool osvi_equal(OSVERSIONINFO &info0, OSVERSIONINFO &info1)
|
||||
{
|
||||
return (info0.dwMajorVersion == info1.dwMajorVersion &&
|
||||
info0.dwMinorVersion == info1.dwMinorVersion &&
|
||||
info0.dwBuildNumber == info1.dwBuildNumber &&
|
||||
info0.dwPlatformId == info1.dwPlatformId &&
|
||||
!strncmp(info0.szCSDVersion, info1.szCSDVersion, sizeof(info0.szCSDVersion)));
|
||||
}
|
||||
|
||||
int wmain()
|
||||
{
|
||||
OSVERSIONINFO info0, info1;
|
||||
ZeroMemory(&info0, sizeof(OSVERSIONINFO));
|
||||
ZeroMemory(&info1, sizeof(OSVERSIONINFO));
|
||||
info0.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
|
||||
info1.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
|
||||
|
||||
GetVersionExA(&info0);
|
||||
|
||||
{
|
||||
WindowsDllInterceptor Kernel32Intercept;
|
||||
Kernel32Intercept.Init("kernel32.dll");
|
||||
if (Kernel32Intercept.AddHook("GetVersionExA", reinterpret_cast<intptr_t>(patched_GetVersionExA), (void**) &orig_GetVersionExA)) {
|
||||
printf("TEST-PASS | WindowsDllInterceptor | Hook added\n");
|
||||
} else {
|
||||
printf("TEST-UNEXPECTED-FAIL | WindowsDllInterceptor | Failed to add hook\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
GetVersionExA(&info1);
|
||||
|
||||
if (patched_func_called) {
|
||||
printf("TEST-PASS | WindowsDllInterceptor | Hook called\n");
|
||||
} else {
|
||||
printf("TEST-UNEXPECTED-FAIL | WindowsDllInterceptor | Hook was not called\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (osvi_equal(info0, info1)) {
|
||||
printf("TEST-PASS | WindowsDllInterceptor | Hook works properly\n");
|
||||
} else {
|
||||
printf("TEST-UNEXPECTED-FAIL | WindowsDllInterceptor | Hook didn't return the right information\n");
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
patched_func_called = false;
|
||||
|
||||
GetVersionExA(&info1);
|
||||
|
||||
if (!patched_func_called) {
|
||||
printf("TEST-PASS | WindowsDllInterceptor | Hook was not called after unregistration\n");
|
||||
} else {
|
||||
printf("TEST-UNEXPECTED-FAIL | WindowsDllInterceptor | Hook was still called after unregistration\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (osvi_equal(info0, info1)) {
|
||||
printf("TEST-PASS | WindowsDllInterceptor | Original function worked properly\n");
|
||||
} else {
|
||||
printf("TEST-UNEXPECTED-FAIL | WindowsDllInterceptor | Original function didn't return the right information\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
printf("TEST-PASS | WindowsDllInterceptor | all checks passed\n");
|
||||
return 0;
|
||||
}
|
@ -51,27 +51,38 @@ interface nsIGfxInfo : nsISupports
|
||||
readonly attribute boolean AzureEnabled;
|
||||
readonly attribute DOMString DWriteVersion;
|
||||
readonly attribute DOMString cleartypeParameters;
|
||||
|
||||
|
||||
// XXX: Switch to a list of devices, rather than explicitly numbering them.
|
||||
|
||||
/**
|
||||
* The name of the display adapter.
|
||||
*/
|
||||
readonly attribute DOMString adapterDescription;
|
||||
readonly attribute DOMString adapterDescription2;
|
||||
|
||||
readonly attribute DOMString adapterDriver;
|
||||
readonly attribute DOMString adapterDriver2;
|
||||
|
||||
/* These types are inspired by DXGI_ADAPTER_DESC */
|
||||
readonly attribute unsigned long adapterVendorID;
|
||||
readonly attribute unsigned long adapterVendorID2;
|
||||
|
||||
readonly attribute unsigned long adapterDeviceID;
|
||||
|
||||
readonly attribute unsigned long adapterDeviceID2;
|
||||
|
||||
/**
|
||||
* The amount of RAM in MB in the display adapter.
|
||||
*/
|
||||
readonly attribute DOMString adapterRAM;
|
||||
readonly attribute DOMString adapterRAM2;
|
||||
|
||||
readonly attribute DOMString adapterDriverVersion;
|
||||
readonly attribute DOMString adapterDriverVersion2;
|
||||
|
||||
readonly attribute DOMString adapterDriverDate;
|
||||
readonly attribute DOMString adapterDriverDate2;
|
||||
|
||||
readonly attribute boolean isGPU2Active;
|
||||
|
||||
void getFailures(
|
||||
[optional] out unsigned long failureCount,
|
||||
|
@ -111,6 +111,13 @@ GfxInfo::GetAdapterDescription(nsAString & aAdapterDescription)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDescription2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDescription2(nsAString & aAdapterDescription)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterRAM; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterRAM(nsAString & aAdapterRAM)
|
||||
@ -119,6 +126,13 @@ GfxInfo::GetAdapterRAM(nsAString & aAdapterRAM)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterRAM2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterRAM2(nsAString & aAdapterRAM)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriver; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriver(nsAString & aAdapterDriver)
|
||||
@ -127,6 +141,13 @@ GfxInfo::GetAdapterDriver(nsAString & aAdapterDriver)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriver2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriver2(nsAString & aAdapterDriver)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverVersion; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverVersion(nsAString & aAdapterDriverVersion)
|
||||
@ -135,6 +156,13 @@ GfxInfo::GetAdapterDriverVersion(nsAString & aAdapterDriverVersion)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverVersion2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverVersion2(nsAString & aAdapterDriverVersion)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverDate; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverDate(nsAString & aAdapterDriverDate)
|
||||
@ -143,6 +171,13 @@ GfxInfo::GetAdapterDriverDate(nsAString & aAdapterDriverDate)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverDate2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverDate2(nsAString & aAdapterDriverDate)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterVendorID; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterVendorID(PRUint32 *aAdapterVendorID)
|
||||
@ -151,6 +186,13 @@ GfxInfo::GetAdapterVendorID(PRUint32 *aAdapterVendorID)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterVendorID2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterVendorID2(PRUint32 *aAdapterVendorID)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterDeviceID; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDeviceID(PRUint32 *aAdapterDeviceID)
|
||||
@ -159,6 +201,20 @@ GfxInfo::GetAdapterDeviceID(PRUint32 *aAdapterDeviceID)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterDeviceID2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDeviceID2(PRUint32 *aAdapterDeviceID)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute boolean isGPU2Active; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetIsGPU2Active(PRBool* aIsGPU2Active)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
void
|
||||
GfxInfo::AddCrashReportAnnotations()
|
||||
{
|
||||
|
@ -64,6 +64,14 @@ public:
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterRAM(nsAString & aAdapterRAM);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverVersion(nsAString & aAdapterDriverVersion);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverDate(nsAString & aAdapterDriverDate);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDescription2(nsAString & aAdapterDescription);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriver2(nsAString & aAdapterDriver);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterVendorID2(PRUint32 *aAdapterVendorID);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDeviceID2(PRUint32 *aAdapterDeviceID);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterRAM2(nsAString & aAdapterRAM);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverVersion2(nsAString & aAdapterDriverVersion);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverDate2(nsAString & aAdapterDriverDate);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetIsGPU2Active(PRBool *aIsGPU2Active);
|
||||
using GfxInfoBase::GetFeatureStatus;
|
||||
using GfxInfoBase::GetFeatureSuggestedDriverVersion;
|
||||
using GfxInfoBase::GetWebGLParameter;
|
||||
|
@ -64,6 +64,14 @@ public:
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterRAM(nsAString & aAdapterRAM);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverVersion(nsAString & aAdapterDriverVersion);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverDate(nsAString & aAdapterDriverDate);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDescription2(nsAString & aAdapterDescription);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriver2(nsAString & aAdapterDriver);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterVendorID2(PRUint32 *aAdapterVendorID);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDeviceID2(PRUint32 *aAdapterDeviceID);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterRAM2(nsAString & aAdapterRAM);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverVersion2(nsAString & aAdapterDriverVersion);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverDate2(nsAString & aAdapterDriverDate);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetIsGPU2Active(PRBool *aIsGPU2Active);
|
||||
using GfxInfoBase::GetFeatureStatus;
|
||||
using GfxInfoBase::GetFeatureSuggestedDriverVersion;
|
||||
using GfxInfoBase::GetWebGLParameter;
|
||||
|
@ -134,6 +134,13 @@ GfxInfo::GetAdapterDescription(nsAString & aAdapterDescription)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDescription2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDescription2(nsAString & aAdapterDescription)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterRAM; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterRAM(nsAString & aAdapterRAM)
|
||||
@ -142,6 +149,13 @@ GfxInfo::GetAdapterRAM(nsAString & aAdapterRAM)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterRAM2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterRAM2(nsAString & aAdapterRAM)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriver; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriver(nsAString & aAdapterDriver)
|
||||
@ -150,6 +164,13 @@ GfxInfo::GetAdapterDriver(nsAString & aAdapterDriver)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriver2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriver2(nsAString & aAdapterDriver)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverVersion; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverVersion(nsAString & aAdapterDriverVersion)
|
||||
@ -158,6 +179,13 @@ GfxInfo::GetAdapterDriverVersion(nsAString & aAdapterDriverVersion)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverVersion2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverVersion2(nsAString & aAdapterDriverVersion)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverDate; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverDate(nsAString & aAdapterDriverDate)
|
||||
@ -166,6 +194,13 @@ GfxInfo::GetAdapterDriverDate(nsAString & aAdapterDriverDate)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverDate2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverDate2(nsAString & aAdapterDriverDate)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterVendorID; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterVendorID(PRUint32 *aAdapterVendorID)
|
||||
@ -174,6 +209,13 @@ GfxInfo::GetAdapterVendorID(PRUint32 *aAdapterVendorID)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterVendorID2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterVendorID2(PRUint32 *aAdapterVendorID)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterDeviceID; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDeviceID(PRUint32 *aAdapterDeviceID)
|
||||
@ -182,6 +224,20 @@ GfxInfo::GetAdapterDeviceID(PRUint32 *aAdapterDeviceID)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterDeviceID2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDeviceID2(PRUint32 *aAdapterDeviceID)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute boolean isGPU2Active; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetIsGPU2Active(PRBool* aIsGPU2Active)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
void
|
||||
GfxInfo::AddCrashReportAnnotations()
|
||||
{
|
||||
|
@ -38,6 +38,7 @@
|
||||
|
||||
#include <windows.h>
|
||||
#include <setupapi.h>
|
||||
#include "d3d9.h"
|
||||
#include "gfxWindowsPlatform.h"
|
||||
#include "GfxInfo.h"
|
||||
#include "GfxInfoWebGL.h"
|
||||
@ -77,7 +78,11 @@ static const PRUint32 vendorATI = 0x1002;
|
||||
GfxInfo::GfxInfo()
|
||||
: mAdapterVendorID(0),
|
||||
mAdapterDeviceID(0),
|
||||
mWindowsVersion(0)
|
||||
mAdapterVendorID2(0),
|
||||
mAdapterDeviceID2(0),
|
||||
mWindowsVersion(0),
|
||||
mHasDualGPU(PR_FALSE),
|
||||
mIsGPU2Active(PR_FALSE)
|
||||
{
|
||||
}
|
||||
|
||||
@ -199,7 +204,42 @@ GfxInfo::GetCleartypeParameters(nsAString & aCleartypeParams)
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* XXX: GfxInfo doesn't handle multiple GPUs. We should try to do that. Bug #591057 */
|
||||
typedef IDirect3D9* (WINAPI*Direct3DCreate9Func) (
|
||||
UINT SDKVersion
|
||||
);
|
||||
|
||||
// XXX: Blacklisting logic doesn't use the result of this for now. Bug #628129.
|
||||
void
|
||||
GfxInfo::IdentifyActiveDevice()
|
||||
{
|
||||
|
||||
HMODULE d3d9 = LoadLibraryW(L"d3d9.dll");
|
||||
if (!d3d9) {
|
||||
NS_WARNING("Couldn't load d3d9.dll");
|
||||
return;
|
||||
}
|
||||
|
||||
Direct3DCreate9Func d3d9Create = (Direct3DCreate9Func)
|
||||
GetProcAddress(d3d9, "Direct3DCreate9");
|
||||
if (!d3d9Create) {
|
||||
NS_WARNING("Couldn't get Direct3DCreate9 function");
|
||||
return;
|
||||
}
|
||||
|
||||
nsRefPtr<IDirect3D9> d3d9Object = dont_AddRef(d3d9Create(D3D_SDK_VERSION));;
|
||||
if (!d3d9Object) {
|
||||
NS_WARNING("Couldn't create d3d9object");
|
||||
return;
|
||||
}
|
||||
|
||||
D3DADAPTER_IDENTIFIER9 ident;
|
||||
HRESULT result = d3d9Object->GetAdapterIdentifier(D3DADAPTER_DEFAULT, 0, &ident);
|
||||
|
||||
if ((result == D3D_OK) &&
|
||||
(mAdapterVendorID2 == ident.VendorId) && (mAdapterDeviceID2 = ident.DeviceId)) {
|
||||
mIsGPU2Active = PR_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
static nsresult GetKeyValue(const WCHAR* keyLocation, const WCHAR* keyName, nsAString& destString, int type)
|
||||
{
|
||||
@ -409,7 +449,40 @@ GfxInfo::Init()
|
||||
result = RegQueryValueExW(key, L"DriverDate", NULL, NULL, (LPBYTE)value, &dwcbData);
|
||||
if (result == ERROR_SUCCESS)
|
||||
mDriverDate = value;
|
||||
RegCloseKey(key);
|
||||
RegCloseKey(key);
|
||||
|
||||
// Check for second adapter:
|
||||
//
|
||||
// A second adapter will have the same driver key as the first adapter except for
|
||||
// the last character, where '1' will be swapped for '0' or vice-versa.
|
||||
// We know driverKey.Length() > 0 since driverKeyPre is a prefix of driverKey.
|
||||
if (driverKey[driverKey.Length()-1] == '0') {
|
||||
driverKey.SetCharAt('1', driverKey.Length()-1);
|
||||
} else {
|
||||
driverKey.SetCharAt('0', driverKey.Length()-1);
|
||||
}
|
||||
result = RegOpenKeyExW(HKEY_LOCAL_MACHINE, driverKey.BeginReading(), 0, KEY_QUERY_VALUE, &key);
|
||||
if (result == ERROR_SUCCESS) {
|
||||
mHasDualGPU = PR_TRUE;
|
||||
mDeviceKey2 = driverKey;
|
||||
dwcbData = sizeof(value);
|
||||
result = RegQueryValueExW(key, L"DriverVersion", NULL, NULL, (LPBYTE)value, &dwcbData);
|
||||
if (result == ERROR_SUCCESS)
|
||||
mDriverVersion2 = value;
|
||||
dwcbData = sizeof(value);
|
||||
result = RegQueryValueExW(key, L"DriverDate", NULL, NULL, (LPBYTE)value, &dwcbData);
|
||||
if (result == ERROR_SUCCESS)
|
||||
mDriverDate2 = value;
|
||||
dwcbData = sizeof(value);
|
||||
result = RegQueryValueExW(key, L"Device Description", NULL, NULL, (LPBYTE)value, &dwcbData);
|
||||
if (result == ERROR_SUCCESS)
|
||||
mDeviceString2 = value;
|
||||
dwcbData = sizeof(value);
|
||||
result = RegQueryValueExW(key, L"MatchingDeviceId", NULL, NULL, (LPBYTE)value, &dwcbData);
|
||||
if (result == ERROR_SUCCESS)
|
||||
mDeviceID2 = value;
|
||||
RegCloseKey(key);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
@ -422,6 +495,47 @@ GfxInfo::Init()
|
||||
FreeLibrary(setupapi);
|
||||
}
|
||||
|
||||
nsAutoString vendor(mDeviceID);
|
||||
ToUpperCase(vendor);
|
||||
PRInt32 start = vendor.Find(NS_LITERAL_CSTRING("VEN_"));
|
||||
if (start != -1) {
|
||||
vendor.Cut(0, start + strlen("VEN_"));
|
||||
vendor.Truncate(4);
|
||||
}
|
||||
nsresult err;
|
||||
mAdapterVendorID = vendor.ToInteger(&err, 16);
|
||||
|
||||
vendor = mDeviceID2;
|
||||
ToUpperCase(vendor);
|
||||
start = vendor.Find(NS_LITERAL_CSTRING("VEN_"));
|
||||
if (start != -1) {
|
||||
vendor.Cut(0, start + strlen("VEN_"));
|
||||
vendor.Truncate(4);
|
||||
}
|
||||
mAdapterVendorID2 = vendor.ToInteger(&err, 16);
|
||||
|
||||
nsAutoString device(mDeviceID);
|
||||
ToUpperCase(device);
|
||||
start = device.Find(NS_LITERAL_CSTRING("&DEV_"));
|
||||
if (start != -1) {
|
||||
device.Cut(0, start + strlen("&DEV_"));
|
||||
device.Truncate(4);
|
||||
}
|
||||
mAdapterDeviceID = device.ToInteger(&err, 16);
|
||||
|
||||
device = mDeviceID2;
|
||||
ToUpperCase(device);
|
||||
start = device.Find(NS_LITERAL_CSTRING("&DEV_"));
|
||||
if (start != -1) {
|
||||
device.Cut(0, start + strlen("&DEV_"));
|
||||
device.Truncate(4);
|
||||
}
|
||||
mAdapterDeviceID2 = device.ToInteger(&err, 16);
|
||||
|
||||
if (mHasDualGPU) {
|
||||
IdentifyActiveDevice();
|
||||
}
|
||||
|
||||
const char *spoofedDriverVersionString = PR_GetEnv("MOZ_GFX_SPOOF_DRIVER_VERSION");
|
||||
if (spoofedDriverVersionString) {
|
||||
mDriverVersion.AssignASCII(spoofedDriverVersionString);
|
||||
@ -430,16 +544,6 @@ GfxInfo::Init()
|
||||
const char *spoofedVendor = PR_GetEnv("MOZ_GFX_SPOOF_VENDOR_ID");
|
||||
if (spoofedVendor) {
|
||||
PR_sscanf(spoofedVendor, "%x", &mAdapterVendorID);
|
||||
} else {
|
||||
nsAutoString vendor(mDeviceID);
|
||||
ToUpperCase(vendor);
|
||||
PRInt32 start = vendor.Find(NS_LITERAL_CSTRING("VEN_"));
|
||||
if (start != -1) {
|
||||
vendor.Cut(0, start + strlen("VEN_"));
|
||||
vendor.Truncate(4);
|
||||
}
|
||||
nsresult err;
|
||||
mAdapterVendorID = vendor.ToInteger(&err, 16);
|
||||
}
|
||||
|
||||
mHasDriverVersionMismatch = PR_FALSE;
|
||||
@ -468,16 +572,6 @@ GfxInfo::Init()
|
||||
const char *spoofedDevice = PR_GetEnv("MOZ_GFX_SPOOF_DEVICE_ID");
|
||||
if (spoofedDevice) {
|
||||
PR_sscanf(spoofedDevice, "%x", &mAdapterDeviceID);
|
||||
} else {
|
||||
nsAutoString device(mDeviceID);
|
||||
ToUpperCase(device);
|
||||
PRInt32 start = device.Find(NS_LITERAL_CSTRING("&DEV_"));
|
||||
if (start != -1) {
|
||||
device.Cut(0, start + strlen("&DEV_"));
|
||||
device.Truncate(4);
|
||||
}
|
||||
nsresult err;
|
||||
mAdapterDeviceID = device.ToInteger(&err, 16);
|
||||
}
|
||||
|
||||
const char *spoofedWindowsVersion = PR_GetEnv("MOZ_GFX_SPOOF_WINDOWS_VERSION");
|
||||
@ -500,6 +594,14 @@ GfxInfo::GetAdapterDescription(nsAString & aAdapterDescription)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDescription2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDescription2(nsAString & aAdapterDescription)
|
||||
{
|
||||
aAdapterDescription = mDeviceString2;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterRAM; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterRAM(nsAString & aAdapterRAM)
|
||||
@ -509,6 +611,15 @@ GfxInfo::GetAdapterRAM(nsAString & aAdapterRAM)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterRAM2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterRAM2(nsAString & aAdapterRAM)
|
||||
{
|
||||
if (NS_FAILED(GetKeyValue(mDeviceKey2.BeginReading(), L"HardwareInformation.MemorySize", aAdapterRAM, REG_DWORD)))
|
||||
aAdapterRAM = L"Unknown";
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriver; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriver(nsAString & aAdapterDriver)
|
||||
@ -518,6 +629,15 @@ GfxInfo::GetAdapterDriver(nsAString & aAdapterDriver)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriver2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriver2(nsAString & aAdapterDriver)
|
||||
{
|
||||
if (NS_FAILED(GetKeyValue(mDeviceKey2.BeginReading(), L"InstalledDisplayDrivers", aAdapterDriver, REG_MULTI_SZ)))
|
||||
aAdapterDriver = L"Unknown";
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverVersion; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverVersion(nsAString & aAdapterDriverVersion)
|
||||
@ -534,6 +654,22 @@ GfxInfo::GetAdapterDriverDate(nsAString & aAdapterDriverDate)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverVersion2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverVersion2(nsAString & aAdapterDriverVersion)
|
||||
{
|
||||
aAdapterDriverVersion = mDriverVersion2;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverDate2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverDate2(nsAString & aAdapterDriverDate)
|
||||
{
|
||||
aAdapterDriverDate = mDriverDate2;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterVendorID; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterVendorID(PRUint32 *aAdapterVendorID)
|
||||
@ -542,6 +678,14 @@ GfxInfo::GetAdapterVendorID(PRUint32 *aAdapterVendorID)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterVendorID2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterVendorID2(PRUint32 *aAdapterVendorID)
|
||||
{
|
||||
*aAdapterVendorID = mAdapterVendorID2;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterDeviceID; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDeviceID(PRUint32 *aAdapterDeviceID)
|
||||
@ -550,6 +694,22 @@ GfxInfo::GetAdapterDeviceID(PRUint32 *aAdapterDeviceID)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterDeviceID2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDeviceID2(PRUint32 *aAdapterDeviceID)
|
||||
{
|
||||
*aAdapterDeviceID = mAdapterDeviceID2;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute boolean isGPU2Active; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetIsGPU2Active(PRBool* aIsGPU2Active)
|
||||
{
|
||||
*aIsGPU2Active = mIsGPU2Active;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
#if defined(MOZ_CRASHREPORTER)
|
||||
/* Cisco's VPN software can cause corruption of the floating point state.
|
||||
* Make a note of this in our crash reports so that some weird crashes
|
||||
@ -607,6 +767,19 @@ GfxInfo::AddCrashReportAnnotations()
|
||||
}
|
||||
note.Append("\n");
|
||||
|
||||
if (mHasDualGPU) {
|
||||
PRUint32 deviceID2, vendorID2;
|
||||
nsAutoString adapterDriverVersionString2;
|
||||
|
||||
note.Append("Has dual GPUs. GPU #2: ");
|
||||
GetAdapterDeviceID2(&deviceID2);
|
||||
GetAdapterVendorID2(&vendorID2);
|
||||
GetAdapterDriverVersion2(adapterDriverVersionString2);
|
||||
note.AppendPrintf("AdapterVendorID2: %04x, ", vendorID2);
|
||||
note.AppendPrintf("AdapterDeviceID2: %04x, ", deviceID2);
|
||||
note.AppendPrintf("AdapterDriverVersion2: ");
|
||||
note.Append(NS_LossyConvertUTF16toASCII(adapterDriverVersionString2));
|
||||
}
|
||||
CrashReporter::AppendAppNotesToCrashReport(note);
|
||||
|
||||
#endif
|
||||
|
@ -68,6 +68,14 @@ public:
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterRAM(nsAString & aAdapterRAM);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverVersion(nsAString & aAdapterDriverVersion);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverDate(nsAString & aAdapterDriverDate);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDescription2(nsAString & aAdapterDescription);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriver2(nsAString & aAdapterDriver);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterVendorID2(PRUint32 *aAdapterVendorID);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDeviceID2(PRUint32 *aAdapterDeviceID);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterRAM2(nsAString & aAdapterRAM);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverVersion2(nsAString & aAdapterDriverVersion);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverDate2(nsAString & aAdapterDriverDate);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetIsGPU2Active(PRBool *aIsGPU2Active);
|
||||
using GfxInfoBase::GetFeatureStatus;
|
||||
using GfxInfoBase::GetFeatureSuggestedDriverVersion;
|
||||
using GfxInfoBase::GetWebGLParameter;
|
||||
@ -86,6 +94,7 @@ protected:
|
||||
private:
|
||||
|
||||
void AddCrashReportAnnotations();
|
||||
void IdentifyActiveDevice();
|
||||
nsString mDeviceString;
|
||||
nsString mDeviceID;
|
||||
nsString mDriverVersion;
|
||||
@ -94,7 +103,16 @@ private:
|
||||
nsString mDeviceKeyDebug;
|
||||
PRUint32 mAdapterVendorID;
|
||||
PRUint32 mAdapterDeviceID;
|
||||
nsString mDeviceString2;
|
||||
nsString mDriverVersion2;
|
||||
nsString mDeviceID2;
|
||||
nsString mDriverDate2;
|
||||
nsString mDeviceKey2;
|
||||
PRUint32 mAdapterVendorID2;
|
||||
PRUint32 mAdapterDeviceID2;
|
||||
PRUint32 mWindowsVersion;
|
||||
PRBool mHasDualGPU;
|
||||
PRBool mIsGPU2Active;
|
||||
PRBool mHasDriverVersionMismatch;
|
||||
};
|
||||
|
||||
|
@ -343,6 +343,13 @@ GfxInfo::GetAdapterDescription(nsAString & aAdapterDescription)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDescription2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDescription2(nsAString & aAdapterDescription)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterRAM; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterRAM(nsAString & aAdapterRAM)
|
||||
@ -351,6 +358,13 @@ GfxInfo::GetAdapterRAM(nsAString & aAdapterRAM)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterRAM2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterRAM2(nsAString & aAdapterRAM)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriver; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriver(nsAString & aAdapterDriver)
|
||||
@ -359,6 +373,13 @@ GfxInfo::GetAdapterDriver(nsAString & aAdapterDriver)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriver2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriver2(nsAString & aAdapterDriver)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverVersion; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverVersion(nsAString & aAdapterDriverVersion)
|
||||
@ -368,6 +389,13 @@ GfxInfo::GetAdapterDriverVersion(nsAString & aAdapterDriverVersion)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverVersion2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverVersion2(nsAString & aAdapterDriverVersion)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverDate; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverDate(nsAString & aAdapterDriverDate)
|
||||
@ -376,6 +404,13 @@ GfxInfo::GetAdapterDriverDate(nsAString & aAdapterDriverDate)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute DOMString adapterDriverDate2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDriverDate2(nsAString & aAdapterDriverDate)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterVendorID; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterVendorID(PRUint32 *aAdapterVendorID)
|
||||
@ -384,6 +419,13 @@ GfxInfo::GetAdapterVendorID(PRUint32 *aAdapterVendorID)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterVendorID2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterVendorID2(PRUint32 *aAdapterVendorID)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterDeviceID; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDeviceID(PRUint32 *aAdapterDeviceID)
|
||||
@ -392,6 +434,20 @@ GfxInfo::GetAdapterDeviceID(PRUint32 *aAdapterDeviceID)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* readonly attribute unsigned long adapterDeviceID2; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetAdapterDeviceID2(PRUint32 *aAdapterDeviceID)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* readonly attribute boolean isGPU2Active; */
|
||||
NS_IMETHODIMP
|
||||
GfxInfo::GetIsGPU2Active(PRBool* aIsGPU2Active)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
|
||||
} // end namespace widget
|
||||
} // end namespace mozilla
|
||||
|
@ -63,6 +63,14 @@ public:
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterRAM(nsAString & aAdapterRAM);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverVersion(nsAString & aAdapterDriverVersion);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverDate(nsAString & aAdapterDriverDate);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDescription2(nsAString & aAdapterDescription);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriver2(nsAString & aAdapterDriver);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterVendorID2(PRUint32 *aAdapterVendorID);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDeviceID2(PRUint32 *aAdapterDeviceID);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterRAM2(nsAString & aAdapterRAM);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverVersion2(nsAString & aAdapterDriverVersion);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetAdapterDriverDate2(nsAString & aAdapterDriverDate);
|
||||
NS_SCRIPTABLE NS_IMETHOD GetIsGPU2Active(PRBool *aIsGPU2Active);
|
||||
using GfxInfoBase::GetFeatureStatus;
|
||||
using GfxInfoBase::GetFeatureSuggestedDriverVersion;
|
||||
using GfxInfoBase::GetWebGLParameter;
|
||||
|
314
xpcom/idl-parser/typelib.py
Normal file
314
xpcom/idl-parser/typelib.py
Normal file
@ -0,0 +1,314 @@
|
||||
#!/usr/bin/env python
|
||||
# typelib.py - Generate XPCOM typelib files from IDL.
|
||||
#
|
||||
# ***** BEGIN LICENSE BLOCK *****
|
||||
# Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||
#
|
||||
# The contents of this file are subject to the Mozilla Public License Version
|
||||
# 1.1 (the "License"); you may not use this file except in compliance with
|
||||
# the License. You may obtain a copy of the License at
|
||||
# http://www.mozilla.org/MPL/
|
||||
#
|
||||
# Software distributed under the License is distributed on an "AS IS" basis,
|
||||
# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||
# for the specific language governing rights and limitations under the
|
||||
# License.
|
||||
#
|
||||
# The Original Code is pyxpidl.
|
||||
#
|
||||
# The Initial Developer of the Original Code is the Mozilla Foundation.
|
||||
# Portions created by the Initial Developer are Copyright (C) 2011
|
||||
# the Initial Developer. All Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
# Kyle Huey <khuey@kylehuey.com>
|
||||
#
|
||||
# Alternatively, the contents of this file may be used under the terms of
|
||||
# either of the GNU General Public License Version 2 or later (the "GPL"),
|
||||
# or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||
# in which case the provisions of the GPL or the LGPL are applicable instead
|
||||
# of those above. If you wish to allow use of your version of this file only
|
||||
# under the terms of either the GPL or the LGPL, and not to allow others to
|
||||
# use your version of this file under the terms of the MPL, indicate your
|
||||
# decision by deleting the provisions above and replace them with the notice
|
||||
# and other provisions required by the GPL or the LGPL. If you do not delete
|
||||
# the provisions above, a recipient may use your version of this file under
|
||||
# the terms of any one of the MPL, the GPL or the LGPL.
|
||||
#
|
||||
# ***** END LICENSE BLOCK *****
|
||||
|
||||
"""Generate an XPIDL typelib for the IDL files specified on the command line"""
|
||||
|
||||
import xpidl, xpt
|
||||
|
||||
# A map of xpidl.py types to xpt.py types
|
||||
TypeMap = {
|
||||
# nsresult is not strictly an xpidl.py type, but it's useful here
|
||||
'nsresult': xpt.Type.Tags.uint32,
|
||||
# builtins
|
||||
'boolean': xpt.Type.Tags.boolean,
|
||||
'void': xpt.Type.Tags.void,
|
||||
'octet': xpt.Type.Tags.uint8,
|
||||
'short': xpt.Type.Tags.int16,
|
||||
'long': xpt.Type.Tags.int32,
|
||||
'long long': xpt.Type.Tags.int64,
|
||||
'unsigned short': xpt.Type.Tags.uint16,
|
||||
'unsigned long': xpt.Type.Tags.uint32,
|
||||
'unsigned long long': xpt.Type.Tags.uint64,
|
||||
'float': xpt.Type.Tags.float,
|
||||
'double': xpt.Type.Tags.double,
|
||||
'char': xpt.Type.Tags.char,
|
||||
'string': xpt.Type.Tags.char_ptr,
|
||||
'wchar': xpt.Type.Tags.wchar_t,
|
||||
'wstring': xpt.Type.Tags.wchar_t_ptr,
|
||||
# special types
|
||||
'nsid': xpt.Type.Tags.nsIID,
|
||||
'domstring': xpt.Type.Tags.DOMString,
|
||||
'astring': xpt.Type.Tags.AString,
|
||||
'utf8string': xpt.Type.Tags.UTF8String,
|
||||
'cstring': xpt.Type.Tags.CString,
|
||||
'jsval': xpt.Type.Tags.jsval
|
||||
}
|
||||
|
||||
# XXXkhuey dipper types should go away (bug 677784)
|
||||
def isDipperType(type):
|
||||
return type == xpt.Type.Tags.DOMString or type == xpt.Type.Tags.AString or type == xpt.Type.Tags.CString or type == xpt.Type.Tags.UTF8String
|
||||
|
||||
def build_interface(iface, ifaces):
|
||||
def get_type(type, calltype, iid_is=None, size_is=None):
|
||||
""" Return the appropriate xpt.Type object for this param """
|
||||
|
||||
if isinstance(type, xpidl.Typedef):
|
||||
type = type.realtype
|
||||
|
||||
if isinstance(type, xpidl.Builtin):
|
||||
if type.name == 'string' and size_is != None:
|
||||
return xpt.StringWithSizeType(size_is, size_is)
|
||||
elif type.name == 'wstring' and size_is != None:
|
||||
return xpt.WideStringWithSizeType(size_is, size_is)
|
||||
else:
|
||||
tag = TypeMap[type.name]
|
||||
isPtr = (tag == xpt.Type.Tags.char_ptr or tag == xpt.Type.Tags.wchar_t_ptr)
|
||||
return xpt.SimpleType(tag,
|
||||
pointer=isPtr,
|
||||
#XXXkhuey unique_pointer is completely unused (bug 677787.)
|
||||
reference=False)
|
||||
|
||||
if isinstance(type, xpidl.Array):
|
||||
return xpt.ArrayType(get_type(type.type, calltype), size_is,
|
||||
#XXXkhuey length_is duplicates size_is (bug 677788),
|
||||
size_is)
|
||||
|
||||
if isinstance(type, xpidl.Interface) or isinstance(type, xpidl.Forward):
|
||||
xptiface = None
|
||||
for i in ifaces:
|
||||
if i.name == type.name:
|
||||
xptiface = i
|
||||
|
||||
if not xptiface:
|
||||
xptiface = xpt.Interface(name=type.name)
|
||||
ifaces.append(xptiface)
|
||||
|
||||
return xpt.InterfaceType(xptiface)
|
||||
|
||||
if isinstance(type, xpidl.Native):
|
||||
if type.specialtype:
|
||||
# XXXkhuey jsval is marked differently in the typelib and in the headers :-(
|
||||
isPtr = (type.isPtr(calltype) or type.isRef(calltype)) and not type.specialtype == 'jsval'
|
||||
isRef = type.isRef(calltype) and not type.specialtype == 'jsval'
|
||||
return xpt.SimpleType(TypeMap[type.specialtype],
|
||||
pointer=isPtr,
|
||||
#XXXkhuey unique_pointer is completely unused
|
||||
reference=isRef)
|
||||
elif iid_is != None:
|
||||
return xpt.InterfaceIsType(iid_is)
|
||||
else:
|
||||
# void ptr
|
||||
return xpt.SimpleType(TypeMap['void'],
|
||||
pointer=True,
|
||||
#XXXkhuey unique_pointer is completely unused
|
||||
reference=False)
|
||||
|
||||
raise Exception("Unknown type!")
|
||||
|
||||
def get_nsresult():
|
||||
return xpt.SimpleType(TypeMap['nsresult'])
|
||||
|
||||
def build_nsresult_param():
|
||||
return xpt.Param(get_nsresult())
|
||||
|
||||
def get_result_type(m):
|
||||
if not m.notxpcom:
|
||||
return get_nsresult()
|
||||
|
||||
return get_type(m.realtype, '')
|
||||
|
||||
def build_result_param(m):
|
||||
return xpt.Param(get_result_type(m))
|
||||
|
||||
def build_retval_param(m):
|
||||
type = get_type(m.realtype, 'out')
|
||||
if isDipperType(type.tag):
|
||||
# NB: The retval bit needs to be set here, contrary to what the
|
||||
# xpt spec says.
|
||||
return xpt.Param(type, in_=True, retval=True, dipper=True)
|
||||
return xpt.Param(type, in_=False, out=True, retval=True)
|
||||
|
||||
def build_attr_param(a, getter=False, setter=False):
|
||||
if not (getter or setter):
|
||||
raise Exception("Attribute param must be for a getter or a setter!")
|
||||
|
||||
type = get_type(a.realtype, getter and 'out' or 'in')
|
||||
if setter:
|
||||
return xpt.Param(type)
|
||||
else:
|
||||
if isDipperType(type.tag):
|
||||
# NB: The retval bit needs to be set here, contrary to what the
|
||||
# xpt spec says.
|
||||
return xpt.Param(type, in_=True, retval=True, dipper=True)
|
||||
return xpt.Param(type, in_=False, out=True, retval=True)
|
||||
|
||||
if iface.namemap is None:
|
||||
raise Exception("Interface was not resolved.")
|
||||
|
||||
consts = []
|
||||
methods = []
|
||||
|
||||
def build_const(c):
|
||||
consts.append(xpt.Constant(c.name, get_type(c.basetype, ''), c.getValue()))
|
||||
|
||||
def build_method(m):
|
||||
params = []
|
||||
|
||||
def build_param(p):
|
||||
def findattr(p, attr):
|
||||
if hasattr(p, attr) and getattr(p, attr):
|
||||
for i, param in enumerate(m.params):
|
||||
if param.name == getattr(p, attr):
|
||||
return i
|
||||
return None
|
||||
|
||||
iid_is = findattr(p, 'iid_is')
|
||||
size_is = findattr(p, 'size_is')
|
||||
|
||||
in_ = p.paramtype.count("in")
|
||||
out = p.paramtype.count("out")
|
||||
dipper = False
|
||||
type = get_type(p.realtype, p.paramtype, iid_is=iid_is, size_is=size_is)
|
||||
if out and isDipperType(type.tag):
|
||||
out = False
|
||||
dipper = True
|
||||
|
||||
return xpt.Param(type, in_, out, p.retval, p.shared, dipper, p.optional)
|
||||
|
||||
for p in m.params:
|
||||
params.append(build_param(p))
|
||||
|
||||
if not m.notxpcom and m.realtype.name != 'void':
|
||||
params.append(build_retval_param(m))
|
||||
|
||||
methods.append(xpt.Method(m.name, build_result_param(m), params,
|
||||
getter=False, setter=False, notxpcom=m.notxpcom,
|
||||
constructor=False, hidden=m.noscript,
|
||||
optargc=m.optional_argc,
|
||||
implicit_jscontext=m.implicit_jscontext))
|
||||
|
||||
def build_attr(a):
|
||||
# Write the getter
|
||||
methods.append(xpt.Method(a.name, build_nsresult_param(),
|
||||
[build_attr_param(a, getter=True)],
|
||||
getter=True, setter=False, notxpcom=a.notxpcom,
|
||||
constructor=False, hidden=a.noscript,
|
||||
optargc=False,
|
||||
implicit_jscontext=a.implicit_jscontext))
|
||||
|
||||
# And maybe the setter
|
||||
if not a.readonly:
|
||||
methods.append(xpt.Method(a.name, build_nsresult_param(),
|
||||
[build_attr_param(a, setter=True)],
|
||||
getter=False, setter=True, notxpcom=a.notxpcom,
|
||||
constructor=False, hidden=a.noscript,
|
||||
optargc=False,
|
||||
implicit_jscontext=a.implicit_jscontext))
|
||||
|
||||
for member in iface.members:
|
||||
if isinstance(member, xpidl.ConstMember):
|
||||
build_const(member)
|
||||
elif isinstance(member, xpidl.Attribute):
|
||||
build_attr(member)
|
||||
elif isinstance(member, xpidl.Method):
|
||||
build_method(member)
|
||||
elif isinstance(member, xpidl.CDATA):
|
||||
pass
|
||||
else:
|
||||
raise Exception("Unexpected interface member: %s" % member)
|
||||
|
||||
parent = None
|
||||
if iface.base:
|
||||
for i in ifaces:
|
||||
if i.name == iface.base:
|
||||
parent = i
|
||||
if not parent:
|
||||
parent = xpt.Interface(name=iface.base)
|
||||
ifaces.append(parent)
|
||||
|
||||
return xpt.Interface(iface.name, iface.attributes.uuid, methods=methods,
|
||||
constants=consts, resolved=True, parent=parent,
|
||||
scriptable=iface.attributes.scriptable,
|
||||
function=iface.attributes.function,
|
||||
builtinclass=iface.attributes.builtinclass)
|
||||
|
||||
def write_typelib(idl, fd, filename):
|
||||
""" Generate the typelib. """
|
||||
|
||||
# We only care about interfaces
|
||||
ifaces = []
|
||||
for p in idl.productions:
|
||||
if p.kind == 'interface':
|
||||
ifaces.append(build_interface(p, ifaces))
|
||||
|
||||
typelib = xpt.Typelib(interfaces=ifaces)
|
||||
typelib.writefd(fd)
|
||||
|
||||
if __name__ == '__main__':
|
||||
from optparse import OptionParser
|
||||
o = OptionParser()
|
||||
o.add_option('-I', action='append', dest='incdirs', default=['.'],
|
||||
help="Directory to search for imported files")
|
||||
o.add_option('--cachedir', dest='cachedir', default=None,
|
||||
help="Directory in which to cache lex/parse tables.")
|
||||
o.add_option('-o', dest='outfile', default=None,
|
||||
help="Output file")
|
||||
o.add_option('-d', dest='depfile', default=None,
|
||||
help="Generate a make dependency file")
|
||||
options, args = o.parse_args()
|
||||
file, = args
|
||||
|
||||
if options.cachedir is not None:
|
||||
if not os.path.isdir(options.cachedir):
|
||||
os.mkdir(options.cachedir)
|
||||
sys.path.append(options.cachedir)
|
||||
|
||||
if options.depfile is not None and options.outfile is None:
|
||||
print >>sys.stderr, "-d requires -o"
|
||||
sys.exit(1)
|
||||
|
||||
if options.outfile is not None:
|
||||
outfd = open(options.outfile, 'wb')
|
||||
closeoutfd = True
|
||||
else:
|
||||
raise "typelib generation requires an output file"
|
||||
|
||||
p = xpidl.IDLParser(outputdir=options.cachedir)
|
||||
idl = p.parse(open(file).read(), filename=file)
|
||||
idl.resolve(options.incdirs, p)
|
||||
write_typelib(idl, outfd, file)
|
||||
|
||||
if closeoutfd:
|
||||
outfd.close()
|
||||
|
||||
if options.depfile is not None:
|
||||
depfd = open(options.depfile, 'w')
|
||||
deps = [dep.replace('\\', '/') for dep in idl.deps]
|
||||
|
||||
print >>depfd, "%s: %s" % (options.outfile, " ".join(deps))
|
@ -456,6 +456,12 @@ class Native(object):
|
||||
|
||||
return self.modifier == 'ref'
|
||||
|
||||
def isPtr(self, calltype):
|
||||
return self.modifier == 'ptr' or (self.modifier == 'ref' and self.specialtype == 'jsval' and calltype == 'out')
|
||||
|
||||
def isRef(self, calltype):
|
||||
return self.modifier == 'ref' and not (self.specialtype == 'jsval' and calltype == 'out')
|
||||
|
||||
def nativeType(self, calltype, const=False, shared=False):
|
||||
if shared:
|
||||
if calltype != 'out':
|
||||
@ -465,14 +471,10 @@ class Native(object):
|
||||
if self.specialtype is not None and calltype == 'in':
|
||||
const = True
|
||||
|
||||
if self.modifier == 'ptr':
|
||||
m = '*' + (calltype != 'in' and '*' or '')
|
||||
elif self.modifier == 'ref':
|
||||
# jsval outparams are odd, for compatibility with existing code
|
||||
if self.specialtype == 'jsval' and calltype == 'out':
|
||||
m = '*'
|
||||
else:
|
||||
m = '& '
|
||||
if self.isRef(calltype):
|
||||
m = '& '
|
||||
elif self.isPtr(calltype):
|
||||
m = '*' + ((self.modifier == 'ptr' and calltype != 'in') and '*' or '')
|
||||
else:
|
||||
m = calltype != 'in' and '*' or ''
|
||||
return "%s%s %s" % (const and 'const ' or '', self.nativename, m)
|
||||
|
@ -145,6 +145,8 @@ class Type(object):
|
||||
self.pointer = pointer
|
||||
self.unique_pointer = unique_pointer
|
||||
self.reference = reference
|
||||
if reference and not pointer:
|
||||
raise Exception("If reference is True pointer must be True too")
|
||||
|
||||
@staticmethod
|
||||
def decodeflags(byte):
|
||||
@ -517,6 +519,7 @@ class Param(object):
|
||||
flags. Params default to "in".
|
||||
|
||||
"""
|
||||
|
||||
self.type = type
|
||||
self.in_ = in_
|
||||
self.out = out
|
||||
@ -642,6 +645,8 @@ class Method(object):
|
||||
self.optargc = optargc
|
||||
self.implicit_jscontext = implicit_jscontext
|
||||
self.params = list(params)
|
||||
if result and not isinstance(result, Param):
|
||||
raise Exception("result must be a Param!")
|
||||
self.result = result
|
||||
|
||||
def read_params(self, typelib, map, data_pool, offset, num_args):
|
||||
|
Loading…
Reference in New Issue
Block a user