Compare commits
7 Commits
STLPORT_FU
...
PSM_GLUE_J
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
3b8fea000b | ||
|
|
51edbc0433 | ||
|
|
a6665f86d6 | ||
|
|
e1e34537e6 | ||
|
|
9613e128d9 | ||
|
|
1f3f975c7b | ||
|
|
ae4913f28c |
32
mozilla/extensions/psm-glue/Makefile.in
Normal file
32
mozilla/extensions/psm-glue/Makefile.in
Normal file
@@ -0,0 +1,32 @@
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
#
|
||||
|
||||
DEPTH = ../..
|
||||
topsrcdir = @top_srcdir@
|
||||
srcdir = @srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
include $(DEPTH)/config/autoconf.mk
|
||||
|
||||
DIRS = public src res
|
||||
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
||||
BIN
mozilla/extensions/psm-glue/macbuild/PSMGlue.mcp
Normal file
BIN
mozilla/extensions/psm-glue/macbuild/PSMGlue.mcp
Normal file
Binary file not shown.
BIN
mozilla/extensions/psm-glue/macbuild/psmglueIDL.mcp
Normal file
BIN
mozilla/extensions/psm-glue/macbuild/psmglueIDL.mcp
Normal file
Binary file not shown.
27
mozilla/extensions/psm-glue/makefile.win
Normal file
27
mozilla/extensions/psm-glue/makefile.win
Normal file
@@ -0,0 +1,27 @@
|
||||
#!nmake
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
|
||||
DEPTH=..\..
|
||||
include <$(DEPTH)/config/config.mak>
|
||||
|
||||
DIRS = public src res
|
||||
|
||||
include <$(DEPTH)\config\rules.mak>
|
||||
4
mozilla/extensions/psm-glue/public/MANIFEST
Normal file
4
mozilla/extensions/psm-glue/public/MANIFEST
Normal file
@@ -0,0 +1,4 @@
|
||||
nsIPSMComponent.idl
|
||||
nsIPSMUIHandler.idl
|
||||
nsISecureBrowserUI.idl
|
||||
nsISSLSocketProvider.idl
|
||||
45
mozilla/extensions/psm-glue/public/Makefile.in
Normal file
45
mozilla/extensions/psm-glue/public/Makefile.in
Normal file
@@ -0,0 +1,45 @@
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
# Hubbie Shaw
|
||||
# Doug Turner <dougt@netscape.com>
|
||||
# Terry Hayes <thayes@netscape.com>
|
||||
#
|
||||
|
||||
MODULE = psmglue
|
||||
|
||||
DEPTH = ../../..
|
||||
topsrcdir = @top_srcdir@
|
||||
srcdir = @srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
include $(DEPTH)/config/autoconf.mk
|
||||
|
||||
XPIDLSRCS = \
|
||||
nsIPSMComponent.idl \
|
||||
nsIPSMUIHandler.idl \
|
||||
nsISecureBrowserUI.idl \
|
||||
nsIPSMSocketInfo.idl \
|
||||
nsISSLSocketProvider.idl \
|
||||
nsISecretDecoderRing.idl \
|
||||
$(NULL)
|
||||
|
||||
PREF_JS_EXPORTS = $(srcdir)/psm-glue.js
|
||||
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
53
mozilla/extensions/psm-glue/public/makefile.win
Normal file
53
mozilla/extensions/psm-glue/public/makefile.win
Normal file
@@ -0,0 +1,53 @@
|
||||
#!nmake
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
# Hubbie Shaw
|
||||
# Doug Turner <dougt@netscape.com>
|
||||
# Terry Hayes <thayes@netscape.com>
|
||||
#
|
||||
|
||||
MODULE = psmglue
|
||||
|
||||
DEPTH=..\..\..
|
||||
IGNORE_MANIFEST=1
|
||||
|
||||
DLLNAME = psmglue
|
||||
PDBFILE = $(DLLNAME).pdb
|
||||
MAPFILE = $(DLLNAME).map
|
||||
DLL = .\$(OBJDIR)\$(DLLNAME).dll
|
||||
MAKE_OBJ_TYPE = DLL
|
||||
|
||||
include <$(DEPTH)/config/config.mak>
|
||||
|
||||
XPIDL_INCLUDES=-I$(DEPTH)\..\mozilla\dist\idl
|
||||
|
||||
XPIDLSRCS= \
|
||||
.\nsIPSMComponent.idl \
|
||||
.\nsIPSMUIHandler.idl \
|
||||
.\nsISecureBrowserUI.idl \
|
||||
.\nsISSLSocketProvider.idl \
|
||||
.\nsIPSMSocketInfo.idl \
|
||||
.\nsISecretDecoderRing.idl \
|
||||
$(NULL)
|
||||
|
||||
include <$(DEPTH)\config\rules.mak>
|
||||
|
||||
install::
|
||||
$(MAKE_INSTALL) .\psm-glue.js $(DIST)\bin\defaults\pref
|
||||
58
mozilla/extensions/psm-glue/public/nsIPSMComponent.idl
Normal file
58
mozilla/extensions/psm-glue/public/nsIPSMComponent.idl
Normal file
@@ -0,0 +1,58 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
* Mitch Stoltz <mstoltz@netscape.com>
|
||||
*/
|
||||
|
||||
#include "nsISupports.idl"
|
||||
interface nsIPrincipal;
|
||||
|
||||
%{C++
|
||||
#include "cmtcmn.h"
|
||||
%}
|
||||
|
||||
[ptr] native nsCMTControlStar(CMT_CONTROL);
|
||||
|
||||
[scriptable, uuid(9e482670-5412-11d3-bbc8-0000861d1237)]
|
||||
interface nsIPSMComponent : nsISupports
|
||||
{
|
||||
|
||||
[noscript] nsCMTControlStar getControlConnection( );
|
||||
|
||||
/**
|
||||
* Display the Security Advisor. PickledStatus and hostName can be null.
|
||||
* If they are, the "Selected Info" dialog will be empty.
|
||||
*/
|
||||
|
||||
void displaySecurityAdvisor(in string pickledStatus, in string hostName);
|
||||
|
||||
/**
|
||||
* This will send PSM all preferences that we know about.
|
||||
*/
|
||||
void passPrefs();
|
||||
};
|
||||
|
||||
%{C++
|
||||
#define PSM_COMPONENT_PROGID "component://netscape/psm"
|
||||
#define PSM_COMPONENT_CLASSNAME "Mozilla PSM Component"
|
||||
%}
|
||||
|
||||
50
mozilla/extensions/psm-glue/public/nsIPSMSocketInfo.idl
Normal file
50
mozilla/extensions/psm-glue/public/nsIPSMSocketInfo.idl
Normal file
@@ -0,0 +1,50 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#include "nsISupports.idl"
|
||||
|
||||
%{C++
|
||||
#include "cmtcmn.h"
|
||||
#include "nsPSMShimLayer.h"
|
||||
%}
|
||||
|
||||
[ptr] native psmtControlStar(CMT_CONTROL);
|
||||
[ptr] native cmSocketStar(CMSocket);
|
||||
[ptr] native nsFileDescStar(PRFileDesc);
|
||||
|
||||
[noscript, uuid(deeb8dfc-fb7a-11d3-ac84-00c04fa0d26b)]
|
||||
interface nsIPSMSocketInfo : nsISupports {
|
||||
|
||||
readonly attribute string hostName;
|
||||
readonly attribute PRInt32 hostPort;
|
||||
|
||||
readonly attribute string proxyName;
|
||||
readonly attribute PRInt32 proxyPort;
|
||||
|
||||
readonly attribute psmtControlStar controlPtr;
|
||||
readonly attribute cmSocketStar socketPtr;
|
||||
readonly attribute nsFileDescStar fileDescPtr;
|
||||
|
||||
void getPickledStatus(out charPtr pickledStatus);
|
||||
};
|
||||
|
||||
36
mozilla/extensions/psm-glue/public/nsIPSMUIHandler.idl
Normal file
36
mozilla/extensions/psm-glue/public/nsIPSMUIHandler.idl
Normal file
@@ -0,0 +1,36 @@
|
||||
/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 the Mozilla browser.
|
||||
*
|
||||
* The Initial Developer of the Original Code is Netscape
|
||||
* Communications, Inc. Portions created by Netscape are
|
||||
* Copyright (C) 1999, Mozilla. All Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#include "nsISupports.idl"
|
||||
|
||||
[scriptable, uuid(d92be9b0-601b-11d3-8c4a-000064657374)]
|
||||
interface nsIPSMUIHandler : nsISupports
|
||||
{
|
||||
void DisplayURI(in long width, in long height, in PRBool modal, in string urlStr);
|
||||
void PromptForFile(in wstring prompt, in string fileRegEx, in boolean shouldFileExist, out string outFile);
|
||||
};
|
||||
|
||||
%{C++
|
||||
#define PSM_UI_HANLDER_PROGID "component://netscape/psm/ui"
|
||||
#define PSM_UI_HANLDER_CLASSNAME "Mozilla PSM UI Handler"
|
||||
%}
|
||||
35
mozilla/extensions/psm-glue/public/nsISSLSocketProvider.idl
Normal file
35
mozilla/extensions/psm-glue/public/nsISSLSocketProvider.idl
Normal file
@@ -0,0 +1,35 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#include "nsISocketProvider.idl"
|
||||
|
||||
[noscript, uuid(856a93d0-5415-11d3-bbc8-0000861d1237)]
|
||||
interface nsISSLSocketProvider : nsISocketProvider {
|
||||
};
|
||||
|
||||
%{C++
|
||||
#define NS_ISSLSOCKETPROVIDER_PROGID NS_NETWORK_SOCKET_PROGID_PREFIX "ssl"
|
||||
#define NS_ISSLSOCKETPROVIDER_CLASSNAME "Mozilla SSL Socket Provider Component"
|
||||
|
||||
%}
|
||||
63
mozilla/extensions/psm-glue/public/nsISecretDecoderRing.idl
Normal file
63
mozilla/extensions/psm-glue/public/nsISecretDecoderRing.idl
Normal file
@@ -0,0 +1,63 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* The contents of this file are subject to the Netscape 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/NPL/
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* thayes@netscape.com
|
||||
*
|
||||
*/
|
||||
|
||||
#include "nsISupports.idl"
|
||||
|
||||
/* Buffer type - for storing 8-bit octet values */
|
||||
[ptr] native buffer(unsigned char);
|
||||
|
||||
[scriptable, uuid(0EC80360-075C-11d4-9FD4-00C04F1B83D8)]
|
||||
interface nsISecretDecoderRing: nsISupports {
|
||||
|
||||
/* Encrypt a buffer - callable only from C++ */
|
||||
[noscript] long encrypt(in buffer data, in long dataLen, out buffer result);
|
||||
|
||||
/* Decrypt a buffer - callable only from C++ */
|
||||
[noscript] long decrypt(in buffer data, in long dataLen, out buffer result);
|
||||
|
||||
/* Encrypt nul-terminated string to BASE64 output */
|
||||
string encryptString(in string text);
|
||||
|
||||
/* Decrypt BASE64 input to nul-terminated string output */
|
||||
/* There is no check for embedded nul values in the decrypted output */
|
||||
string decryptString(in string crypt);
|
||||
|
||||
/* Prompt the user to change the password on the SDR key */
|
||||
void changePassword();
|
||||
|
||||
/* Logout of the security device that protects the SDR key */
|
||||
void logout();
|
||||
};
|
||||
|
||||
/*
|
||||
* Configuration interface for the Secret Decoder Ring
|
||||
* - this interface allows setting the window that will be
|
||||
* used as parent for dialog windows (such as password prompts)
|
||||
*/
|
||||
[scriptable, uuid(01D8C0F0-0CCC-11d4-9FDD-000064657374)]
|
||||
interface nsISecretDecoderRingConfig: nsISupports {
|
||||
void setWindow(in nsISupports w);
|
||||
};
|
||||
|
||||
|
||||
44
mozilla/extensions/psm-glue/public/nsISecureBrowserUI.idl
Normal file
44
mozilla/extensions/psm-glue/public/nsISecureBrowserUI.idl
Normal file
@@ -0,0 +1,44 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#include "nsISupports.idl"
|
||||
|
||||
interface nsIDOMWindow;
|
||||
interface nsIDOMElement;
|
||||
|
||||
[scriptable, uuid(081e31e0-a144-11d3-8c7c-00609792278c)]
|
||||
interface nsSecureBrowserUI : nsISupports
|
||||
{
|
||||
void init(in nsIDOMWindow window, in nsIDOMElement button);
|
||||
void displayPageInfoUI();
|
||||
};
|
||||
|
||||
%{C++
|
||||
#define NS_SECURE_BROWSER_UI_PROGID "component://netscape/secure_browser_ui"
|
||||
#define NS_SECURE_BROWSER_UI_CLASSNAME "Mozilla Secure Browser UI Handler"
|
||||
|
||||
#define NS_SECURE_BROWSER_UI_CID \
|
||||
{ 0x10fe7ea0, 0xa10a, 0x11d3, {0x8c, 0x7c, 0x00, 0x60, 0x97, 0x92, 0x27, 0x8c}}
|
||||
|
||||
%}
|
||||
11
mozilla/extensions/psm-glue/public/psm-glue.js
Normal file
11
mozilla/extensions/psm-glue/public/psm-glue.js
Normal file
@@ -0,0 +1,11 @@
|
||||
pref("general.useragent.security", "U");
|
||||
|
||||
pref("security.enable_ssl2", true);
|
||||
pref("security.enable_ssl3", true);
|
||||
pref("security.default_personal_cert", "Select Automatically");
|
||||
pref("security.ask_for_password", 0);
|
||||
pref("security.password_lifetime", 30);
|
||||
pref("security.warn_entering_secure", true);
|
||||
pref("security.warn_leaving_secure", true);
|
||||
pref("security.warn_viewing_mixed", true);
|
||||
pref("security.warn_submit_insecure", true);
|
||||
32
mozilla/extensions/psm-glue/res/Makefile.in
Normal file
32
mozilla/extensions/psm-glue/res/Makefile.in
Normal file
@@ -0,0 +1,32 @@
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
#
|
||||
|
||||
DEPTH = ../../..
|
||||
topsrcdir = @top_srcdir@
|
||||
srcdir = @srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
include $(DEPTH)/config/autoconf.mk
|
||||
|
||||
DIRS = content locale
|
||||
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
||||
3
mozilla/extensions/psm-glue/res/content/MANIFEST
Normal file
3
mozilla/extensions/psm-glue/res/content/MANIFEST
Normal file
@@ -0,0 +1,3 @@
|
||||
securityOverlay.xul
|
||||
securityUI.js
|
||||
PSMTaskMenu.xul
|
||||
38
mozilla/extensions/psm-glue/res/content/Makefile.in
Normal file
38
mozilla/extensions/psm-glue/res/content/Makefile.in
Normal file
@@ -0,0 +1,38 @@
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
#
|
||||
|
||||
DEPTH = ../../../..
|
||||
topsrcdir = @top_srcdir@
|
||||
srcdir = @srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
include $(DEPTH)/config/autoconf.mk
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
||||
COMMUNICATOR_CONTENT_DIR = $(DIST)/bin/chrome/packages/core/communicator/content/
|
||||
COMMUNICATOR_EXPORT_CONTENT = \
|
||||
$(srcdir)/securityOverlay.xul \
|
||||
$(srcdir)/securityUI.js \
|
||||
$(srcdir)/PSMTaskMenu.xul \
|
||||
$(NULL)
|
||||
|
||||
install::
|
||||
$(INSTALL) $(COMMUNICATOR_EXPORT_CONTENT) $(COMMUNICATOR_CONTENT_DIR)
|
||||
22
mozilla/extensions/psm-glue/res/content/PSMTaskMenu.xul
Normal file
22
mozilla/extensions/psm-glue/res/content/PSMTaskMenu.xul
Normal file
@@ -0,0 +1,22 @@
|
||||
<?xml version="1.0"?>
|
||||
|
||||
<!DOCTYPE window SYSTEM "chrome://communicator/locale/PSMTaskMenu.dtd" >
|
||||
|
||||
<overlay id="psmTaskMenuID"
|
||||
xmlns:html="http://www.w3.org/1999/xhtml"
|
||||
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
|
||||
|
||||
<script language="JavaScript">
|
||||
function displaySecurityAdvisor()
|
||||
{
|
||||
var psm = Components.classes["component://netscape/psm"].getService();
|
||||
psm = psm.QueryInterface(Components.interfaces.nsIPSMComponent);
|
||||
psm.displaySecurityAdvisor( null, null );
|
||||
}
|
||||
</script>
|
||||
|
||||
<menupopup id="personalManagers">
|
||||
<menuitem id="PSMMentItem" position="1" value="&PSMCmd.label;" oncommand="displaySecurityAdvisor()"/>
|
||||
</menupopup>
|
||||
|
||||
</overlay>
|
||||
35
mozilla/extensions/psm-glue/res/content/makefile.win
Normal file
35
mozilla/extensions/psm-glue/res/content/makefile.win
Normal file
@@ -0,0 +1,35 @@
|
||||
#!nmake
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
|
||||
DEPTH=..\..\..\..
|
||||
include <$(DEPTH)/config/config.mak>
|
||||
include <$(DEPTH)\config\rules.mak>
|
||||
|
||||
install:: $(DLL)
|
||||
$(MAKE_INSTALL) securityOverlay.xul $(DIST)\bin\chrome\packages\core\communicator\content
|
||||
$(MAKE_INSTALL) securityUI.js $(DIST)\bin\chrome\packages\core\communicator\content
|
||||
$(MAKE_INSTALL) PSMTaskMenu.xul $(DIST)\bin\chrome\packages\core\communicator\content
|
||||
|
||||
clobber::
|
||||
$(RM) $(DIST)\bin\chrome\packages\core\communicator\content\securityOverlay.xul
|
||||
$(RM) $(DIST)\bin\chrome\packages\core\communicator\content\securityUI.js
|
||||
$(RM) $(DIST)\bin\chrome\packages\core\communicator\content\PSMTaskMenu.xul
|
||||
|
||||
14
mozilla/extensions/psm-glue/res/content/securityOverlay.xul
Normal file
14
mozilla/extensions/psm-glue/res/content/securityOverlay.xul
Normal file
@@ -0,0 +1,14 @@
|
||||
<?xml version="1.0"?>
|
||||
<?xml-stylesheet href="chrome://communicator/skin/securityOverlay.css" type="text/css"?>
|
||||
|
||||
<!DOCTYPE window SYSTEM "chrome://communicator/locale/securityOverlay.dtd">
|
||||
|
||||
<overlay id="NavSecurityOverlay"
|
||||
xmlns:html="http://www.w3.org/TR/REC-html40"
|
||||
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
|
||||
|
||||
<script language="JavaScript" src="chrome://communicator/content/securityUI.js" />
|
||||
|
||||
<statusbarpanel id="security-button" onclick="displayPageInfo()" tooltip="aToolTip" tooltiptext="&lockIcon.label;"/>
|
||||
|
||||
</overlay>
|
||||
45
mozilla/extensions/psm-glue/res/content/securityUI.js
Normal file
45
mozilla/extensions/psm-glue/res/content/securityUI.js
Normal file
@@ -0,0 +1,45 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*/
|
||||
|
||||
window.addEventListener("load", SetSecurityButton, false);
|
||||
|
||||
var securityUI;
|
||||
|
||||
function SetSecurityButton()
|
||||
{
|
||||
dump("in SetSecurityButton\n");
|
||||
|
||||
var ui = Components.classes["component://netscape/secure_browser_ui"].createInstance();
|
||||
securityUI = ui.QueryInterface(Components.interfaces.nsSecureBrowserUI);
|
||||
|
||||
var button = document.getElementById('security-button');
|
||||
if (button && window.content)
|
||||
securityUI.init(window.content, button);
|
||||
}
|
||||
|
||||
function displayPageInfo()
|
||||
{
|
||||
if (securityUI)
|
||||
securityUI.displayPageInfoUI();
|
||||
}
|
||||
|
||||
|
||||
32
mozilla/extensions/psm-glue/res/locale/Makefile.in
Normal file
32
mozilla/extensions/psm-glue/res/locale/Makefile.in
Normal file
@@ -0,0 +1,32 @@
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
#
|
||||
|
||||
DEPTH = ../../../..
|
||||
topsrcdir = @top_srcdir@
|
||||
srcdir = @srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
include $(DEPTH)/config/autoconf.mk
|
||||
|
||||
DIRS = en-US
|
||||
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
||||
3
mozilla/extensions/psm-glue/res/locale/en-US/MANIFEST
Normal file
3
mozilla/extensions/psm-glue/res/locale/en-US/MANIFEST
Normal file
@@ -0,0 +1,3 @@
|
||||
PSMTaskMenu.dtd
|
||||
securityOverlay.dtd
|
||||
security.properties
|
||||
41
mozilla/extensions/psm-glue/res/locale/en-US/Makefile.in
Normal file
41
mozilla/extensions/psm-glue/res/locale/en-US/Makefile.in
Normal file
@@ -0,0 +1,41 @@
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
#
|
||||
|
||||
DEPTH = ../../../../..
|
||||
topsrcdir = @top_srcdir@
|
||||
srcdir = @srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
include $(DEPTH)/config/autoconf.mk
|
||||
|
||||
COMMUNICATOR_RESOURCE_CONTENT = \
|
||||
$(srcdir)/PSMTaskMenu.dtd \
|
||||
$(srcdir)/security.properties \
|
||||
$(srcdir)/securityOverlay.dtd \
|
||||
$(NULL)
|
||||
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
||||
install::
|
||||
$(INSTALL) $(COMMUNICATOR_RESOURCE_CONTENT) $(DIST)/bin/chrome/locales/en-US/communicator/locale
|
||||
|
||||
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
<!ENTITY PSMCmd.label "Security Manager">
|
||||
37
mozilla/extensions/psm-glue/res/locale/en-US/makefile.win
Normal file
37
mozilla/extensions/psm-glue/res/locale/en-US/makefile.win
Normal file
@@ -0,0 +1,37 @@
|
||||
#!nmake
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
|
||||
DEPTH=..\..\..\..\..
|
||||
|
||||
include <$(DEPTH)\config\rules.mak>
|
||||
|
||||
COMMUNICATOR_DIST=$(DIST)\bin\chrome\locales\en-US\communicator\locale
|
||||
|
||||
|
||||
install::
|
||||
$(MAKE_INSTALL) PSMTaskMenu.dtd $(COMMUNICATOR_DIST)
|
||||
$(MAKE_INSTALL) security.properties $(COMMUNICATOR_DIST)
|
||||
$(MAKE_INSTALL) securityOverlay.dtd $(COMMUNICATOR_DIST)
|
||||
|
||||
clobber::
|
||||
$(RM) -f $(DIST)\bin\chrome\locales\en-US\communicator\locale\PSMTaskMenu.dtd
|
||||
$(RM) -f $(DIST)\bin\chrome\locales\en-US\communicator\locale\security.properties
|
||||
$(RM) -f $(DIST)\bin\chrome\locales\en-US\communicator\locale\securityOverlay.dtd
|
||||
@@ -0,0 +1,29 @@
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
#
|
||||
|
||||
Title=Security Warning
|
||||
MixedContentMessage=You have requested a secure document that contains some insecure information.
|
||||
LeaveSiteMessage=You have requested an insecure document. The document and any information you send back could be observed by a third party while in transit.
|
||||
EnterSiteMessage=You have requested a secure document. The document and any information you send back are encrypted for privacy while in transit.
|
||||
PostToInsecure=Warning! Although this document is secure, the information you have submitted is insecure and could be observed by a third party while in transit. If you are submitting passwords, credit card numbers, or other information you would like to keep private, it would be safer for you to cancel the submission.
|
||||
PostToInsecureFromInsecure=Any information you submit is insecure and could be observed by a third party while in transit. If you are submitting passwords, credit card numbers, or other information you would like to keep private, it would be safer for you to cancel the submission.
|
||||
DontShowAgain=Show Me This Alert Next Time.
|
||||
FindText=Please find the Personal Security Manager application
|
||||
@@ -0,0 +1,2 @@
|
||||
|
||||
<!ENTITY lockIcon.label "Show security information for this window">
|
||||
27
mozilla/extensions/psm-glue/res/locale/makefile.win
Normal file
27
mozilla/extensions/psm-glue/res/locale/makefile.win
Normal file
@@ -0,0 +1,27 @@
|
||||
#!nmake
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
|
||||
DEPTH=..\..\..\..
|
||||
|
||||
DIRS=en-US
|
||||
|
||||
include <$(DEPTH)\config\rules.mak>
|
||||
|
||||
27
mozilla/extensions/psm-glue/res/makefile.win
Normal file
27
mozilla/extensions/psm-glue/res/makefile.win
Normal file
@@ -0,0 +1,27 @@
|
||||
#!nmake
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
|
||||
DEPTH=..\..\..
|
||||
include <$(DEPTH)/config/config.mak>
|
||||
|
||||
DIRS = content locale
|
||||
|
||||
include <$(DEPTH)\config\rules.mak>
|
||||
66
mozilla/extensions/psm-glue/src/Makefile.in
Normal file
66
mozilla/extensions/psm-glue/src/Makefile.in
Normal file
@@ -0,0 +1,66 @@
|
||||
#
|
||||
# The contents of this file are subject to the Netscape 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/NPL/
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
# Hubbie Shaw
|
||||
# Doug Turner <dougt@netscape.com>
|
||||
#
|
||||
|
||||
DEPTH = ../../..
|
||||
topsrcdir = @top_srcdir@
|
||||
srcdir = @srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
include $(DEPTH)/config/autoconf.mk
|
||||
|
||||
MODULE = psmglue
|
||||
|
||||
IS_COMPONENT = 1
|
||||
LIBRARY_NAME = psmglue
|
||||
|
||||
|
||||
CPPSRCS = \
|
||||
nsPSMComponent.cpp \
|
||||
nsPSMUICallbacks.cpp \
|
||||
nsSSLSocketProvider.cpp \
|
||||
nsPSMModule.cpp \
|
||||
nsSSLIOLayer.cpp \
|
||||
nsSecureBrowserUIImpl.cpp \
|
||||
nsSDR.cpp \
|
||||
nsFSDR.cpp \
|
||||
nsCrypto.cpp \
|
||||
nsKeygenHandler.cpp \
|
||||
$(NULL)
|
||||
|
||||
CSRCS = \
|
||||
nsPSMMutex.c \
|
||||
nsPSMShimLayer.c \
|
||||
$(NULL)
|
||||
|
||||
EXTRA_DSO_LDOPTS = \
|
||||
$(MOZ_COMPONENT_LIBS) \
|
||||
-lcmt \
|
||||
-lprotocol \
|
||||
$(MOZ_JS_LIBS) \
|
||||
$(NULL)
|
||||
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
||||
INCLUDES += \
|
||||
-I$(srcdir) \
|
||||
$(NULL)
|
||||
72
mozilla/extensions/psm-glue/src/makefile.win
Normal file
72
mozilla/extensions/psm-glue/src/makefile.win
Normal file
@@ -0,0 +1,72 @@
|
||||
#!nmake
|
||||
#
|
||||
# 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 Netscape
|
||||
# Communications Corporation. Portions created by Netscape are
|
||||
# Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
# Rights Reserved.
|
||||
#
|
||||
# Contributor(s):
|
||||
# Hubbie Shaw
|
||||
# Doug Turner <dougt@netscape.com>
|
||||
#
|
||||
|
||||
MODULE = psmglue
|
||||
|
||||
DEPTH=..\..\..
|
||||
IGNORE_MANIFEST=1
|
||||
|
||||
DLLNAME = psmglue
|
||||
PDBFILE = $(DLLNAME).pdb
|
||||
MAPFILE = $(DLLNAME).map
|
||||
DLL = .\$(OBJDIR)\$(DLLNAME).dll
|
||||
MAKE_OBJ_TYPE = DLL
|
||||
|
||||
include <$(DEPTH)/config/config.mak>
|
||||
|
||||
LINCS = $(LINCS) \
|
||||
-I$(PUBLIC) \
|
||||
-I$(PUBLIC)/security \
|
||||
$(NULL)
|
||||
|
||||
LLIBS = \
|
||||
$(LIBNSPR) \
|
||||
$(DIST)\lib\neckobase_s.lib \
|
||||
$(DIST)\lib\xpcom.lib \
|
||||
$(DIST)\lib\js3250.lib \
|
||||
$(DIST)\lib\cmt.lib \
|
||||
$(DIST)\lib\protocol.lib \
|
||||
$(DIST)\lib\mozreg.lib \
|
||||
$(DIST)\lib\jsdom.lib \
|
||||
$(NULL)
|
||||
|
||||
OBJS = \
|
||||
.\$(OBJDIR)\nsPSMMutex.obj \
|
||||
.\$(OBJDIR)\nsPSMShimLayer.obj \
|
||||
.\$(OBJDIR)\nsPSMComponent.obj \
|
||||
.\$(OBJDIR)\nsPSMUICallbacks.obj \
|
||||
.\$(OBJDIR)\nsPSMModule.obj \
|
||||
.\$(OBJDIR)\nsSecureBrowserUIImpl.obj \
|
||||
.\$(OBJDIR)\nsSSLIOLayer.obj \
|
||||
.\$(OBJDIR)\nsSSLSocketProvider.obj \
|
||||
.\$(OBJDIR)\nsSDR.obj \
|
||||
.\$(OBJDIR)\nsFSDR.obj \
|
||||
.\$(OBJDIR)\nsCrypto.obj \
|
||||
.\$(OBJDIR)\nsKeygenHandler.obj \
|
||||
$(NULL)
|
||||
|
||||
include <$(DEPTH)\config\rules.mak>
|
||||
|
||||
install:: $(DLL)
|
||||
$(MAKE_INSTALL) .\$(OBJDIR)\$(DLLNAME).dll $(DIST)\bin\components
|
||||
1642
mozilla/extensions/psm-glue/src/nsCrypto.cpp
Normal file
1642
mozilla/extensions/psm-glue/src/nsCrypto.cpp
Normal file
File diff suppressed because it is too large
Load Diff
112
mozilla/extensions/psm-glue/src/nsCrypto.h
Normal file
112
mozilla/extensions/psm-glue/src/nsCrypto.h
Normal file
@@ -0,0 +1,112 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* The contents of this file are subject to the Netscape 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/NPL/
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*/
|
||||
#ifndef _nsCrypto_h_
|
||||
#define _nsCrypto_h_
|
||||
#include "nsIDOMCRMFObject.h"
|
||||
#include "nsIDOMCrypto.h"
|
||||
#include "nsIScriptObjectOwner.h"
|
||||
#include "nsIDOMPkcs11.h"
|
||||
|
||||
#define NS_CRYPTO_CLASSNAME "Crypto JavaScript Class"
|
||||
#define NS_CRYPTO_CID \
|
||||
{0x929d9320, 0x251e, 0x11d4, { 0x8a, 0x7c, 0x00, 0x60, 0x08, 0xc8, 0x44, 0xc3} }
|
||||
|
||||
#define NS_PKCS11_CLASSNAME "Pkcs11 JavaScript Class"
|
||||
#define NS_PKCS11_CID \
|
||||
{0x74b7a390, 0x3b41, 0x11d4, { 0x8a, 0x80, 0x00, 0x60, 0x08, 0xc8, 0x44, 0xc3} }
|
||||
|
||||
class nsIPSMComponent;
|
||||
class nsIDOMScriptObjectFactory;
|
||||
|
||||
|
||||
class nsCRMFObject : public nsIDOMCRMFObject,
|
||||
public nsIScriptObjectOwner {
|
||||
public:
|
||||
nsCRMFObject();
|
||||
virtual ~nsCRMFObject();
|
||||
NS_DECL_IDOMCRMFOBJECT
|
||||
NS_DECL_ISUPPORTS
|
||||
|
||||
NS_IMETHOD GetScriptObject(nsIScriptContext *aContext, void** aScriptObject);
|
||||
NS_IMETHOD SetScriptObject(void* aScriptObject);
|
||||
|
||||
nsresult init();
|
||||
|
||||
nsresult SetCRMFRequest(char *inRequest);
|
||||
private:
|
||||
|
||||
nsString mBase64Request;
|
||||
void *mScriptObject;
|
||||
};
|
||||
|
||||
|
||||
class nsCrypto: public nsIDOMCrypto,
|
||||
public nsIScriptObjectOwner {
|
||||
public:
|
||||
nsCrypto();
|
||||
virtual ~nsCrypto();
|
||||
nsresult init();
|
||||
|
||||
NS_IMETHOD GetScriptObject(nsIScriptContext *aContext, void** aScriptObject);
|
||||
NS_IMETHOD SetScriptObject(void* aScriptObject);
|
||||
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_IDOMCRYPTO
|
||||
|
||||
static nsresult GetScriptObjectFactory(nsIDOMScriptObjectFactory **aResult);
|
||||
static nsIDOMScriptObjectFactory *gScriptObjectFactory;
|
||||
static nsIPrincipal* GetScriptPrincipal(JSContext *cx);
|
||||
static const char *kPSMComponentProgID;
|
||||
|
||||
private:
|
||||
|
||||
nsIPSMComponent *mPSM;
|
||||
nsString mVersionString;
|
||||
PRBool mVersionStringSet;
|
||||
void *mScriptObject;
|
||||
};
|
||||
|
||||
class nsPkcs11 : public nsIDOMPkcs11,
|
||||
public nsIScriptObjectOwner {
|
||||
public:
|
||||
nsPkcs11();
|
||||
virtual ~nsPkcs11();
|
||||
|
||||
nsresult init();
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_IDOMPKCS11
|
||||
NS_IMETHOD GetScriptObject(nsIScriptContext *aContext, void** aScriptObject);
|
||||
NS_IMETHOD SetScriptObject(void* aScriptObject);
|
||||
|
||||
private:
|
||||
nsIPSMComponent *mPSM;
|
||||
void *mScriptObject;
|
||||
};
|
||||
|
||||
nsresult
|
||||
getPSMComponent(nsIPSMComponent ** retPSM);
|
||||
|
||||
#endif //_nsCrypto_h_
|
||||
|
||||
|
||||
|
||||
|
||||
1078
mozilla/extensions/psm-glue/src/nsFSDR.cpp
Normal file
1078
mozilla/extensions/psm-glue/src/nsFSDR.cpp
Normal file
File diff suppressed because it is too large
Load Diff
60
mozilla/extensions/psm-glue/src/nsFSDR.h
Normal file
60
mozilla/extensions/psm-glue/src/nsFSDR.h
Normal file
@@ -0,0 +1,60 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Terry Hayes <thayes@netscape.com>
|
||||
* Steve Morse <morse@netscape.com>
|
||||
*/
|
||||
|
||||
#ifndef _NSFSDR_H_
|
||||
#define _NSFSDR_H_
|
||||
|
||||
#include "nsISecretDecoderRing.h"
|
||||
|
||||
// ===============================================
|
||||
// nsFSecretDecoderRing - "fake" implementation of nsISecretDecoderRing
|
||||
// ===============================================
|
||||
|
||||
#define NS_FSDR_CLASSNAME "Fake Secret Decoder Ring"
|
||||
#define NS_FSDR_CID \
|
||||
{ 0x1ee28720, 0x2b93, 0x11d4, { 0xa0, 0xa4, 0x0, 0x0, 0x64, 0x65, 0x73, 0x74 } }
|
||||
|
||||
#define NS_FSDR_PROGID "netscape.security.fsdr"
|
||||
|
||||
class nsFSecretDecoderRing : public nsISecretDecoderRing
|
||||
{
|
||||
public:
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSISECRETDECODERRING
|
||||
|
||||
nsFSecretDecoderRing();
|
||||
virtual ~nsFSecretDecoderRing();
|
||||
|
||||
nsresult init();
|
||||
|
||||
private:
|
||||
nsIPSMComponent *mPSM;
|
||||
|
||||
static const char *kPSMComponentProgID;
|
||||
|
||||
nsresult encode(const unsigned char *data, PRInt32 dataLen, char **_retval);
|
||||
nsresult decode(const char *data, unsigned char **result, PRInt32 * _retval);
|
||||
};
|
||||
|
||||
#endif /* _NSFSDR_H_ */
|
||||
255
mozilla/extensions/psm-glue/src/nsKeygenHandler.cpp
Normal file
255
mozilla/extensions/psm-glue/src/nsKeygenHandler.cpp
Normal file
@@ -0,0 +1,255 @@
|
||||
//For some weird reason, nsProxiedService has to be the first file
|
||||
//included. Don't ask me, I'm just the messenger.
|
||||
#include "nsProxiedService.h"
|
||||
#include "nsKeygenHandler.h"
|
||||
#include "nsVoidArray.h"
|
||||
#include "nsSecureBrowserUIImpl.h"
|
||||
#include "nsIServiceManager.h"
|
||||
#include "nsIDOMHTMLSelectElement.h"
|
||||
#include "nsIContent.h"
|
||||
#include "nsIPSMComponent.h"
|
||||
#include "nsIPSMUIHandler.h"
|
||||
#include "nsPSMUICallbacks.h"
|
||||
#include "nsCrypto.h"
|
||||
#include "cmtcmn.h"
|
||||
#include "cmtjs.h"
|
||||
|
||||
//These defines are taken from the PKCS#11 spec
|
||||
#define CKM_RSA_PKCS_KEY_PAIR_GEN 0x00000000
|
||||
#define CKM_DH_PKCS_KEY_PAIR_GEN 0x00000020
|
||||
#define CKM_DSA_KEY_PAIR_GEN 0x00000010
|
||||
|
||||
static NS_DEFINE_IID(kFormProcessorIID, NS_IFORMPROCESSOR_IID);
|
||||
static NS_DEFINE_IID(kIDOMHTMLSelectElementIID, NS_IDOMHTMLSELECTELEMENT_IID);
|
||||
|
||||
static const char *mozKeyGen = "-mozilla-keygen";
|
||||
|
||||
NS_IMPL_ADDREF(nsKeygenFormProcessor);
|
||||
NS_IMPL_RELEASE(nsKeygenFormProcessor);
|
||||
NS_IMPL_QUERY_INTERFACE(nsKeygenFormProcessor, kFormProcessorIID);
|
||||
|
||||
nsKeygenFormProcessor::nsKeygenFormProcessor()
|
||||
{
|
||||
NS_INIT_REFCNT();
|
||||
getPSMComponent(&mPSM);
|
||||
}
|
||||
|
||||
char *
|
||||
nsKeygenFormProcessor::ChooseToken(PCMT_CONTROL control,
|
||||
CMKeyGenTagArg *psmarg,
|
||||
CMKeyGenTagReq *reason)
|
||||
{
|
||||
CMUint32 resID;
|
||||
CMTStatus crv;
|
||||
CMTItem url;
|
||||
char *keyString = nsnull;
|
||||
nsresult rv = NS_OK;
|
||||
NameList *tokenNames;
|
||||
int i;
|
||||
|
||||
// In this case, PSM provided us with a list of potential tokens to choose
|
||||
// from, but we're gonna make it use it's UI for now, so let's delte the
|
||||
// memory associated with the structure it sent back.
|
||||
tokenNames = (NameList*)psmarg->current;
|
||||
for (i=0; i < tokenNames->numitems; i++) {
|
||||
nsCRT::free(tokenNames->names[i]);
|
||||
}
|
||||
nsCRT::free((char*)tokenNames);
|
||||
resID = psmarg->rid;
|
||||
memset(&url, 0, sizeof(CMTItem));
|
||||
NS_WITH_PROXIED_SERVICE(nsIPSMUIHandler, handler, nsPSMUIHandlerImpl::GetCID(), NS_UI_THREAD_EVENTQ, &rv);
|
||||
crv = CMT_GetStringAttribute(control, resID, SSM_FID_CHOOSE_TOKEN_URL, &url);
|
||||
if (crv != CMTSuccess) {
|
||||
goto loser;
|
||||
}
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
handler->DisplayURI(400, 300, PR_TRUE, (char*)url.data);
|
||||
} else {
|
||||
goto loser;
|
||||
}
|
||||
return CMT_GetGenKeyResponse(control, psmarg, reason);
|
||||
loser:
|
||||
if (keyString)
|
||||
nsCRT::free(keyString);
|
||||
return nsnull;
|
||||
}
|
||||
|
||||
char *
|
||||
nsKeygenFormProcessor::SetUserPassword(PCMT_CONTROL control,
|
||||
CMKeyGenTagArg *psmarg,
|
||||
CMKeyGenTagReq *reason)
|
||||
{
|
||||
nsresult rv;
|
||||
CMTStatus crv;
|
||||
CMTItem url;
|
||||
char *keystring=nsnull;
|
||||
|
||||
// We need to delete the memory the PSM client API allocated for us since
|
||||
// we're just gonna tell it to use it's own UI.
|
||||
nsCRT::free((char*)psmarg->current);
|
||||
NS_WITH_PROXIED_SERVICE(nsIPSMUIHandler, handler, nsPSMUIHandlerImpl::GetCID(), NS_UI_THREAD_EVENTQ, &rv);
|
||||
memset (&url, 0, sizeof(CMTItem));
|
||||
crv = CMT_GetStringAttribute(control,psmarg->rid, SSM_FID_INIT_DB_URL, &url);
|
||||
if (crv != CMTSuccess || NS_FAILED(rv)){
|
||||
goto loser;
|
||||
}
|
||||
|
||||
handler->DisplayURI(500, 450, PR_TRUE, (char*)url.data);
|
||||
|
||||
return CMT_GetGenKeyResponse(control, psmarg, reason);
|
||||
loser:
|
||||
if (keystring)
|
||||
nsCRT::free(keystring);
|
||||
return nsnull;
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsKeygenFormProcessor::GetPublicKey(nsString& value, nsString& challenge,
|
||||
nsString& keyType,
|
||||
nsString& outPublicKey, nsString& pqg)
|
||||
{
|
||||
PCMT_CONTROL control;
|
||||
nsresult rv;
|
||||
CMKeyGenParams *params = nsnull;
|
||||
CMKeyGenTagArg *psmarg = nsnull;
|
||||
CMKeyGenTagReq reason;
|
||||
char *emptyCString = "null";
|
||||
char *keystring = nsnull;
|
||||
|
||||
rv = mPSM->GetControlConnection(&control);
|
||||
if (NS_FAILED(rv)) {
|
||||
goto loser;
|
||||
}
|
||||
params = new CMKeyGenParams;
|
||||
if (params == nsnull) {
|
||||
goto loser;
|
||||
}
|
||||
params->typeString = (keyType.IsEmpty()) ? emptyCString :
|
||||
keyType.ToNewCString();
|
||||
params->challenge = (challenge.IsEmpty()) ? emptyCString :
|
||||
challenge.ToNewCString();
|
||||
params->choiceString = value.ToNewCString();
|
||||
params->pqgString = (pqg.IsEmpty()) ? emptyCString : pqg.ToNewCString();
|
||||
psmarg = new CMKeyGenTagArg;
|
||||
if (psmarg == nsnull) {
|
||||
goto loser;
|
||||
}
|
||||
// ARGH, while this is going on, we need to lock the control
|
||||
// connection so that the event loop doesn't drop our response on
|
||||
// the floor.
|
||||
CMT_LockConnection(control);
|
||||
psmarg->op = CM_KEYGEN_START;
|
||||
psmarg->rid = 0;
|
||||
psmarg->tokenName = NULL;
|
||||
psmarg->current = params;
|
||||
keystring = CMT_GenKeyOldStyle(control, psmarg, &reason);
|
||||
while (!keystring) {
|
||||
psmarg->op = reason;
|
||||
switch (psmarg->op) {
|
||||
case CM_KEYGEN_PICK_TOKEN:
|
||||
keystring = ChooseToken(control, psmarg, &reason);
|
||||
break;
|
||||
case CM_KEYGEN_SET_PASSWORD:
|
||||
keystring = SetUserPassword(control, psmarg, &reason);
|
||||
break;
|
||||
case CM_KEYGEN_ERR:
|
||||
default:
|
||||
goto loser;
|
||||
}
|
||||
}
|
||||
CMT_UnlockConnection(control);
|
||||
outPublicKey.AssignWithConversion(keystring);
|
||||
nsCRT::free(keystring);
|
||||
return NS_OK;
|
||||
loser:
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
NS_METHOD
|
||||
nsKeygenFormProcessor::ProcessValue(nsIDOMHTMLElement *aElement,
|
||||
const nsString& aName,
|
||||
nsString& aValue)
|
||||
{
|
||||
#ifdef DEBUG_javi
|
||||
char *name = aName.ToNewCString();
|
||||
char *value = aValue.ToNewCString();
|
||||
printf("ProcessValue: name %s value %s\n", name, value);
|
||||
delete [] name;
|
||||
delete [] value;
|
||||
#endif
|
||||
nsresult rv = NS_OK;
|
||||
nsCOMPtr<nsIDOMHTMLSelectElement>selectElement;
|
||||
nsresult res = aElement->QueryInterface(kIDOMHTMLSelectElementIID,
|
||||
getter_AddRefs(selectElement));
|
||||
if (NS_SUCCEEDED(res)) {
|
||||
nsAutoString keygenvalue;
|
||||
nsAutoString challengeValue;
|
||||
nsString publicKey;
|
||||
nsString mozillaKeygen;
|
||||
nsString mozType;
|
||||
|
||||
mozType.AssignWithConversion("_moz-type");
|
||||
mozillaKeygen.AssignWithConversion(mozKeyGen);
|
||||
res = selectElement->GetAttribute(mozType, keygenvalue);
|
||||
|
||||
if (NS_CONTENT_ATTR_HAS_VALUE == res && keygenvalue.Equals(mozillaKeygen)) {
|
||||
nsString challenge;
|
||||
nsString keyType;
|
||||
nsString keyTypeValue;
|
||||
nsString pqg, pqgValue;
|
||||
|
||||
challenge.AssignWithConversion("challenge");
|
||||
pqg.AssignWithConversion("pqg");
|
||||
res = selectElement->GetAttribute(pqg, pqgValue);
|
||||
keyType.AssignWithConversion("keytype");
|
||||
res = selectElement->GetAttribute(keyType, keyTypeValue);
|
||||
if (NS_FAILED(res) || keyTypeValue.IsEmpty()) {
|
||||
// If this field is not present, we default to rsa.
|
||||
keyTypeValue.AssignWithConversion("rsa");
|
||||
}
|
||||
res = selectElement->GetAttribute(challenge, challengeValue);
|
||||
rv = GetPublicKey(aValue, challenge, keyTypeValue,
|
||||
publicKey, pqgValue);
|
||||
aValue = publicKey;
|
||||
}
|
||||
}
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
NS_METHOD nsKeygenFormProcessor::ProvideContent(const nsString& aFormType,
|
||||
nsVoidArray& aContent,
|
||||
nsString& aAttribute)
|
||||
{
|
||||
nsString selectString;
|
||||
nsresult rv;
|
||||
PCMT_CONTROL control;
|
||||
PRUint32 i;
|
||||
|
||||
selectString.AssignWithConversion("SELECT");
|
||||
if (aFormType.EqualsIgnoreCase(selectString)) {
|
||||
nsString *selectString;
|
||||
char **result;
|
||||
|
||||
rv = mPSM->GetControlConnection(&control);
|
||||
if (NS_FAILED(rv)) {
|
||||
goto loser;
|
||||
}
|
||||
result = CMT_GetKeyChoiceList(control, "rsa"/*Need to figure out if DSA*/,
|
||||
nsnull);
|
||||
for (i=0; result[i] != nsnull; i++) {
|
||||
selectString = new nsString;
|
||||
selectString->AssignWithConversion(result[i]);
|
||||
aContent.AppendElement(selectString);
|
||||
delete []result[i];
|
||||
}
|
||||
delete []result;
|
||||
aAttribute.AssignWithConversion(mozKeyGen);
|
||||
}
|
||||
return NS_OK;
|
||||
loser:
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
|
||||
|
||||
32
mozilla/extensions/psm-glue/src/nsKeygenHandler.h
Normal file
32
mozilla/extensions/psm-glue/src/nsKeygenHandler.h
Normal file
@@ -0,0 +1,32 @@
|
||||
#ifndef _NSKEYGENHANDLER_H_
|
||||
#define _NSKEYGENHANDLER_H_
|
||||
// Form Processor
|
||||
#include "nsIFormProcessor.h"
|
||||
#include "ssmdefs.h"
|
||||
#include "cmtcmn.h"
|
||||
|
||||
class nsIPSMComponent;
|
||||
|
||||
class nsKeygenFormProcessor : public nsIFormProcessor {
|
||||
public:
|
||||
nsKeygenFormProcessor();
|
||||
NS_IMETHOD ProcessValue(nsIDOMHTMLElement *aElement,
|
||||
const nsString& aName,
|
||||
nsString& aValue);
|
||||
|
||||
NS_IMETHOD ProvideContent(const nsString& aFormType,
|
||||
nsVoidArray& aContent,
|
||||
nsString& aAttribute);
|
||||
NS_DECL_ISUPPORTS
|
||||
protected:
|
||||
nsresult GetPublicKey(nsString& value, nsString& challenge,
|
||||
nsString& keyType, nsString& outPublicKey,
|
||||
nsString& pqg);
|
||||
char * ChooseToken(PCMT_CONTROL control, CMKeyGenTagArg *psmarg,
|
||||
CMKeyGenTagReq *reason);
|
||||
char * SetUserPassword(PCMT_CONTROL control, CMKeyGenTagArg *psmarg,
|
||||
CMKeyGenTagReq *reason);
|
||||
nsIPSMComponent *mPSM;
|
||||
};
|
||||
|
||||
#endif //_NSKEYGENHANDLER_H_
|
||||
935
mozilla/extensions/psm-glue/src/nsPSMComponent.cpp
Normal file
935
mozilla/extensions/psm-glue/src/nsPSMComponent.cpp
Normal file
@@ -0,0 +1,935 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
* Mitch Stoltz <mstoltz@netscape.com>
|
||||
*/
|
||||
|
||||
#include "nsProxiedService.h"
|
||||
#include "nsPSMUICallbacks.h"
|
||||
#include "VerReg.h"
|
||||
|
||||
#include "nspr.h"
|
||||
#include "nsPSMComponent.h"
|
||||
|
||||
#include "nsCRT.h"
|
||||
|
||||
#include "nsNetUtil.h"
|
||||
#include "nsIURI.h"
|
||||
#include "nsIChannel.h"
|
||||
#include "nsIInputStream.h"
|
||||
#include "nsIStreamListener.h"
|
||||
|
||||
#include "nsIPref.h"
|
||||
#include "nsIProfile.h"
|
||||
#include "nsILocalFile.h"
|
||||
|
||||
#include "nsDirectoryService.h"
|
||||
|
||||
#include "rsrcids.h"
|
||||
|
||||
#include "nsPSMMutex.h"
|
||||
#include "nsPSMShimLayer.h"
|
||||
#include "nsPSMUICallbacks.h"
|
||||
|
||||
#include "nsISecureBrowserUI.h"
|
||||
#include "nsIDocumentLoaderObserver.h"
|
||||
#include "nsIScriptSecurityManager.h"
|
||||
#include "nsICertificatePrincipal.h"
|
||||
|
||||
#include "nsIProtocolProxyService.h"
|
||||
|
||||
#define PSM_VERSION_REG_KEY "/Netscape/Personal Security Manager"
|
||||
|
||||
#ifdef WIN32
|
||||
#define PSM_FILE_NAME "psm.exe"
|
||||
#elif XP_UNIX
|
||||
#define PSM_FILE_NAME "start-psm"
|
||||
#else
|
||||
#define PSM_FILE_NAME "psm"
|
||||
#endif
|
||||
|
||||
|
||||
static NS_DEFINE_CID(kCStringBundleServiceCID, NS_STRINGBUNDLESERVICE_CID);
|
||||
static NS_DEFINE_CID(kProfileCID, NS_PROFILE_CID);
|
||||
static NS_DEFINE_CID(kPrefCID, NS_PREF_CID);
|
||||
static NS_DEFINE_CID(kProtocolProxyServiceCID, NS_PROTOCOLPROXYSERVICE_CID);
|
||||
|
||||
nsPSMComponent* nsPSMComponent::mInstance = nsnull;
|
||||
|
||||
nsPSMComponent::nsPSMComponent()
|
||||
{
|
||||
NS_INIT_REFCNT();
|
||||
mControl = nsnull;
|
||||
}
|
||||
|
||||
nsPSMComponent::~nsPSMComponent()
|
||||
{
|
||||
if (mControl)
|
||||
{
|
||||
CMT_CloseControlConnection(mControl);
|
||||
mControl = nsnull;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMComponent::CreatePSMComponent(nsISupports* aOuter, REFNSIID aIID, void **aResult)
|
||||
{
|
||||
if (!aResult) {
|
||||
return NS_ERROR_INVALID_POINTER;
|
||||
}
|
||||
if (aOuter) {
|
||||
*aResult = nsnull;
|
||||
return NS_ERROR_NO_AGGREGATION;
|
||||
}
|
||||
|
||||
if (mInstance == nsnull)
|
||||
{
|
||||
mInstance = new nsPSMComponent();
|
||||
}
|
||||
|
||||
if (mInstance == nsnull)
|
||||
return NS_ERROR_OUT_OF_MEMORY;
|
||||
|
||||
nsresult rv = mInstance->QueryInterface(aIID, aResult);
|
||||
if (NS_FAILED(rv))
|
||||
{
|
||||
*aResult = nsnull;
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
|
||||
/* nsISupports Implementation for the class */
|
||||
NS_IMPL_THREADSAFE_ISUPPORTS3(nsPSMComponent,
|
||||
nsIPSMComponent,
|
||||
nsIContentHandler,
|
||||
nsISignatureVerifier);
|
||||
|
||||
#define INIT_NUM_PREFS 100
|
||||
/* preference types */
|
||||
#define STRING_PREF 0
|
||||
#define BOOL_PREF 1
|
||||
#define INT_PREF 2
|
||||
|
||||
|
||||
/* resizable list struct that contains pref items */
|
||||
typedef struct CMSetPrefList {
|
||||
int n; /* number of filled items */
|
||||
int capacity; /* allocated memory */
|
||||
CMTSetPrefElement* list; /* actual list */
|
||||
} CMSetPrefList;
|
||||
|
||||
static void get_pack_bool_pref(nsIPref *prefManager, char* key, CMTSetPrefElement* list, int* n)
|
||||
{
|
||||
PRBool boolpref;
|
||||
|
||||
list[*n].key = nsCRT::strdup(key);
|
||||
list[*n].type = BOOL_PREF;
|
||||
|
||||
if ((prefManager->GetBoolPref(key, &boolpref) != 0) || boolpref)
|
||||
{
|
||||
list[*n].value = nsCRT::strdup("true");
|
||||
}
|
||||
else
|
||||
{
|
||||
list[*n].value = nsCRT::strdup("false");
|
||||
}
|
||||
|
||||
(*n)++; /* increment the counter after done packing */
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
static void SaveAllPrefs(int number, CMTSetPrefElement* list)
|
||||
{
|
||||
nsCOMPtr<nsIPref> prefManager;
|
||||
|
||||
nsresult res = nsServiceManager::GetService(kPrefCID,
|
||||
nsIPref::GetIID(),
|
||||
getter_AddRefs(prefManager));
|
||||
|
||||
if (NS_FAILED(res) || !prefManager)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
int i;
|
||||
int intval;
|
||||
|
||||
for (i = 0; i < number; i++)
|
||||
{
|
||||
if (list[i].key == nsnull)
|
||||
{
|
||||
/* misconfigured item: next */
|
||||
continue;
|
||||
}
|
||||
|
||||
switch (list[i].type)
|
||||
{
|
||||
case 0: /* string type */
|
||||
prefManager->SetCharPref(list[i].key, list[i].value);
|
||||
break;
|
||||
case 1: /* boolean type */
|
||||
if (strcmp(list[i].value, "true") == 0) {
|
||||
prefManager->SetBoolPref(list[i].key, (PRBool)1);
|
||||
}
|
||||
else if (strcmp(list[i].value, "false") == 0) {
|
||||
prefManager->SetBoolPref(list[i].key, (PRBool)0);
|
||||
}
|
||||
break;
|
||||
case 2:
|
||||
intval = atoi(list[i].value);
|
||||
prefManager->SetIntPref(list[i].key, intval);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMComponent::PassPrefs()
|
||||
{
|
||||
// if we have not passed anything to psm yet, this function can just return.
|
||||
|
||||
if (!mControl)
|
||||
return NS_OK;
|
||||
|
||||
int i;
|
||||
nsresult rv = NS_ERROR_FAILURE;
|
||||
char* strpref = NULL;
|
||||
int intpref;
|
||||
PRBool boolpref;
|
||||
CMSetPrefList prefs = {0};
|
||||
CMTSetPrefElement* list = NULL;
|
||||
|
||||
char* pickAuto = "Select Automatically";
|
||||
char* alwaysAsk = "Ask Every Time";
|
||||
|
||||
nsCOMPtr<nsIPref> prefManager;
|
||||
|
||||
nsresult res = nsServiceManager::GetService(kPrefCID,
|
||||
nsIPref::GetIID(),
|
||||
getter_AddRefs(prefManager));
|
||||
|
||||
if (NS_OK != res)
|
||||
{
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
/* allocate memory for list */
|
||||
prefs.n = 0; /* counter */
|
||||
prefs.capacity = INIT_NUM_PREFS;
|
||||
prefs.list = (CMTSetPrefElement*) new char[(INIT_NUM_PREFS * sizeof(CMTSetPrefElement))];
|
||||
|
||||
if (prefs.list == NULL)
|
||||
{
|
||||
return rv;
|
||||
}
|
||||
|
||||
/* shorthand */
|
||||
list = prefs.list;
|
||||
|
||||
/* get preferences */
|
||||
get_pack_bool_pref(prefManager, "security.enable_ssl2", (CMTSetPrefElement*)list, &(prefs.n));
|
||||
get_pack_bool_pref(prefManager, "security.enable_ssl3", (CMTSetPrefElement*)list, &(prefs.n));
|
||||
|
||||
/* this pref is a boolean pref in nature but a string pref for
|
||||
* historical reason
|
||||
*/
|
||||
|
||||
list[prefs.n].key = nsCRT::strdup("security.default_personal_cert");
|
||||
list[prefs.n].type = STRING_PREF;
|
||||
|
||||
if ((prefManager->CopyCharPref(list[prefs.n].key, &strpref) == 0) && (strcmp(strpref, pickAuto) == 0))
|
||||
{
|
||||
list[prefs.n].value = nsCRT::strdup(pickAuto);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* although one could choose a specific cert for client auth in
|
||||
* Nova, that mode is deprecated with PSM and mapped to ASK
|
||||
*/
|
||||
list[prefs.n].value = nsCRT::strdup(alwaysAsk);
|
||||
}
|
||||
|
||||
prefs.n++;
|
||||
if (strpref != NULL)
|
||||
{
|
||||
nsCRT::free(strpref);
|
||||
}
|
||||
|
||||
list[prefs.n].key = nsCRT::strdup("security.default_mail_cert");
|
||||
list[prefs.n].type = STRING_PREF;
|
||||
if (prefManager->CopyCharPref(list[prefs.n].key, &list[prefs.n].value) != 0)
|
||||
{
|
||||
list[prefs.n].value = NULL;
|
||||
}
|
||||
prefs.n++;
|
||||
|
||||
list[prefs.n].key = nsCRT::strdup("security.ask_for_password");
|
||||
list[prefs.n].type = INT_PREF;
|
||||
if (prefManager->GetIntPref(list[prefs.n].key, &intpref) != 0)
|
||||
{
|
||||
intpref = 0; /* default */
|
||||
}
|
||||
|
||||
list[prefs.n].value = PR_smprintf("%d", intpref);
|
||||
prefs.n++;
|
||||
|
||||
list[prefs.n].key = nsCRT::strdup("security.password_lifetime");
|
||||
list[prefs.n].type = INT_PREF;
|
||||
if (prefManager->GetIntPref(list[prefs.n].key, &intpref) != 0)
|
||||
{
|
||||
intpref = 30; /* default */
|
||||
}
|
||||
|
||||
list[prefs.n].value = PR_smprintf("%d", intpref);
|
||||
prefs.n++;
|
||||
|
||||
/* OCSP preferences */
|
||||
/* XXX since these are the new ones added by PSM, we will be more
|
||||
* error-tolerant in fetching them
|
||||
*/
|
||||
if (prefManager->GetBoolPref("security.OCSP.enabled", &boolpref) == 0)
|
||||
{
|
||||
if (boolpref)
|
||||
{
|
||||
list[prefs.n].value = nsCRT::strdup("true");
|
||||
}
|
||||
else
|
||||
{
|
||||
list[prefs.n].value = nsCRT::strdup("false");
|
||||
}
|
||||
list[prefs.n].key = nsCRT::strdup("security.OCSP.enabled");
|
||||
list[prefs.n].type = BOOL_PREF;
|
||||
prefs.n++;
|
||||
}
|
||||
|
||||
if (prefManager->GetBoolPref("security.OCSP.useDefaultResponder", &boolpref) == 0)
|
||||
{
|
||||
if (boolpref)
|
||||
{
|
||||
list[prefs.n].value = nsCRT::strdup("true");
|
||||
}
|
||||
else
|
||||
{
|
||||
list[prefs.n].value = nsCRT::strdup("false");
|
||||
}
|
||||
list[prefs.n].key = nsCRT::strdup("security.OCSP.useDefaultResponder");
|
||||
list[prefs.n].type = BOOL_PREF;
|
||||
prefs.n++;
|
||||
}
|
||||
|
||||
if (prefManager->CopyCharPref("security.OCSP.URL", &strpref) == 0)
|
||||
{
|
||||
list[prefs.n].value = strpref;
|
||||
list[prefs.n].key = nsCRT::strdup("security.OCSP.URL");
|
||||
list[prefs.n].type = STRING_PREF;
|
||||
prefs.n++;
|
||||
}
|
||||
|
||||
if (prefManager->CopyCharPref("security.OCSP.signingCA", &strpref) == 0)
|
||||
{
|
||||
list[prefs.n].value = strpref;
|
||||
list[prefs.n].key = nsCRT::strdup("security.OCSP.signingCA");
|
||||
list[prefs.n].type = STRING_PREF;
|
||||
prefs.n++;
|
||||
}
|
||||
|
||||
/* now application-specific preferences */
|
||||
/* get navigator preferences */
|
||||
get_pack_bool_pref(prefManager, "security.warn_entering_secure", (CMTSetPrefElement*)list, &prefs.n);
|
||||
get_pack_bool_pref(prefManager, "security.warn_leaving_secure", (CMTSetPrefElement*)list, &prefs.n);
|
||||
get_pack_bool_pref(prefManager, "security.warn_viewing_mixed", (CMTSetPrefElement*)list, &prefs.n);
|
||||
get_pack_bool_pref(prefManager, "security.warn_submit_insecure", (CMTSetPrefElement*)list, &prefs.n);
|
||||
|
||||
// Add any other prefs here such as ldap or mail/news.
|
||||
|
||||
CMT_SetSavePrefsCallback(mControl, (savePrefsCallback_fn)SaveAllPrefs);
|
||||
|
||||
if (CMT_PassAllPrefs(mControl, prefs.n, (CMTSetPrefElement*)prefs.list) != CMTSuccess)
|
||||
{
|
||||
goto loser;
|
||||
}
|
||||
|
||||
rv = NS_OK; /* success */
|
||||
loser:
|
||||
/* clean out memory for prefs */
|
||||
for (i = 0; i < prefs.n; i++)
|
||||
{
|
||||
if (prefs.list[i].key != NULL)
|
||||
{
|
||||
nsCRT::free(prefs.list[i].key);
|
||||
}
|
||||
|
||||
if (prefs.list[i].value != NULL)
|
||||
{
|
||||
nsCRT::free(prefs.list[i].value);
|
||||
}
|
||||
}
|
||||
|
||||
if (prefs.list != NULL)
|
||||
{
|
||||
delete(prefs.list);
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
|
||||
#ifdef XP_MAC
|
||||
extern "C" {
|
||||
void RunMacPSM(void* arg);
|
||||
PRThread* SSM_CreateAndRegisterThread(PRThreadType type, void (*start)(void *arg),
|
||||
void *arg, PRThreadPriority priority,
|
||||
PRThreadScope scope, PRThreadState state,
|
||||
PRUint32 stackSize);
|
||||
void SSM_KillAllThreads(void);
|
||||
}
|
||||
#endif
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMComponent::GetControlConnection( CMT_CONTROL * *_retval )
|
||||
{
|
||||
nsresult rv;
|
||||
*_retval = nsnull;
|
||||
if (mControl)
|
||||
{
|
||||
*_retval = mControl;
|
||||
return NS_OK;
|
||||
}
|
||||
else /* initialize mutex, sock table, etc. */
|
||||
{
|
||||
|
||||
if (nsPSMMutexInit() != PR_SUCCESS)
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
#ifdef XP_MAC
|
||||
/* FIXME: Really need better error handling in PSM, which simply exits on error. */
|
||||
/* use a cached monitor to rendezvous with the PSM thread. */
|
||||
PRMonitor* monitor = PR_CEnterMonitor(this);
|
||||
if (monitor != nsnull) {
|
||||
/* create the Cartman thread, and let it run awhile to get things going. */
|
||||
PRThread* cartmanThread = SSM_CreateAndRegisterThread(PR_USER_THREAD, RunMacPSM,
|
||||
this, PR_PRIORITY_NORMAL,
|
||||
PR_LOCAL_THREAD, PR_UNJOINABLE_THREAD, 0);
|
||||
if (cartmanThread != nsnull) {
|
||||
/* need a good way to rendezvouz with the Cartman thread. */
|
||||
PR_CWait(this, PR_INTERVAL_NO_TIMEOUT);
|
||||
}
|
||||
|
||||
PR_CExitMonitor(this);
|
||||
}
|
||||
#endif
|
||||
|
||||
// Try to see if it is open already
|
||||
mControl = CMT_ControlConnect(&nsPSMMutexTbl, &nsPSMShimTbl);
|
||||
|
||||
// Find the one in the bin directory
|
||||
if (mControl == nsnull)
|
||||
{
|
||||
nsCOMPtr<nsILocalFile> psmAppFile;
|
||||
NS_WITH_SERVICE(nsIProperties, directoryService, NS_DIRECTORY_SERVICE_PROGID, &rv);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
directoryService->Get("system.OS_CurrentProcessDirectory",
|
||||
NS_GET_IID(nsIFile),
|
||||
getter_AddRefs(psmAppFile));
|
||||
|
||||
|
||||
psmAppFile->Append("psm");
|
||||
psmAppFile->Append(PSM_FILE_NAME);
|
||||
|
||||
PRBool isExecutable, exists;
|
||||
psmAppFile->Exists(&exists);
|
||||
psmAppFile->IsExecutable(&isExecutable);
|
||||
if (exists && isExecutable)
|
||||
{
|
||||
nsXPIDLCString path;
|
||||
psmAppFile->GetPath(getter_Copies(path));
|
||||
// FIX THIS. using a file path is totally wrong here.
|
||||
mControl = CMT_EstablishControlConnection((char*)(const char*)path, &nsPSMShimTbl, &nsPSMMutexTbl);
|
||||
}
|
||||
}
|
||||
|
||||
// Get the one in the version registry
|
||||
if (mControl == nsnull)
|
||||
{
|
||||
//Try to find it.
|
||||
int err;
|
||||
char filepath[MAXREGPATHLEN];
|
||||
|
||||
err = VR_GetPath(PSM_VERSION_REG_KEY, sizeof(filepath), filepath);
|
||||
if ( err == REGERR_OK )
|
||||
{
|
||||
nsFileSpec psmSpec(filepath);
|
||||
psmSpec += PSM_FILE_NAME;
|
||||
|
||||
if (psmSpec.Exists())
|
||||
{
|
||||
mControl = CMT_EstablishControlConnection((char *)psmSpec.GetNativePathCString(), &nsPSMShimTbl, &nsPSMMutexTbl);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (!mControl || InitPSMUICallbacks(mControl) != PR_SUCCESS)
|
||||
goto failure;
|
||||
|
||||
nsFileSpec profileSpec;
|
||||
PRUnichar* profileName;
|
||||
|
||||
NS_WITH_SERVICE(nsIProfile, profile, kProfileCID, &rv);
|
||||
if (NS_FAILED(rv)) goto failure;
|
||||
|
||||
rv = profile->GetCurrentProfileDir(&profileSpec);
|
||||
if (NS_FAILED(rv)) goto failure;;
|
||||
|
||||
#ifdef XP_MAC
|
||||
profileSpec += "Security";
|
||||
// make sure the dir exists
|
||||
profileSpec.CreateDirectory();
|
||||
#endif
|
||||
|
||||
rv = profile->GetCurrentProfile(&profileName);
|
||||
if (NS_FAILED(rv)) goto failure;
|
||||
|
||||
CMTStatus psmStatus;
|
||||
nsCAutoString profilenameC;
|
||||
profilenameC.AssignWithConversion(profileName);
|
||||
|
||||
psmStatus = CMT_Hello( mControl,
|
||||
PROTOCOL_VERSION,
|
||||
profilenameC,
|
||||
(char*)profileSpec.GetNativePathCString());
|
||||
|
||||
if (psmStatus == CMTFailure)
|
||||
{
|
||||
PR_FREEIF(profileName);
|
||||
goto failure;
|
||||
}
|
||||
|
||||
if (InitPSMEventLoop(mControl) != PR_SUCCESS)
|
||||
{
|
||||
PR_FREEIF(profileName);
|
||||
goto failure;
|
||||
}
|
||||
|
||||
if (NS_FAILED(PassPrefs()))
|
||||
{
|
||||
PR_FREEIF(profileName);
|
||||
goto failure;
|
||||
}
|
||||
|
||||
PR_FREEIF(profileName);
|
||||
|
||||
nsCOMPtr<nsIProtocolProxyService> proxySvc = do_GetService(kProtocolProxyServiceCID, &rv);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
proxySvc->AddNoProxyFor("127.0.0.1", mControl->port);
|
||||
|
||||
*_retval = mControl;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
failure:
|
||||
#ifdef DEBUG
|
||||
printf("*** Failure setting up Cartman! \n");
|
||||
#endif
|
||||
|
||||
if (mControl)
|
||||
{
|
||||
CMT_CloseControlConnection(mControl);
|
||||
mControl = NULL;
|
||||
}
|
||||
|
||||
// TODO we need to unregister our UI callback BEFORE destroying our mutex.
|
||||
// nsPSMMutexDestroy();
|
||||
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMComponent::DisplaySecurityAdvisor(const char *pickledStatus, const char *hostName)
|
||||
{
|
||||
CMT_CONTROL *controlConnection;
|
||||
GetControlConnection( &controlConnection );
|
||||
if (DisplayPSMUIDialog(controlConnection, pickledStatus, hostName) == PR_SUCCESS)
|
||||
return NS_OK;
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
class CertDownloader : public nsIStreamListener
|
||||
{
|
||||
public:
|
||||
CertDownloader() {NS_ASSERTION(0, "don't use this constructor."); }
|
||||
CertDownloader(PRInt32 type);
|
||||
virtual ~CertDownloader();
|
||||
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSISTREAMOBSERVER
|
||||
NS_DECL_NSISTREAMLISTENER
|
||||
protected:
|
||||
char* mByteData;
|
||||
PRInt32 mBufferOffset;
|
||||
PRInt32 mContentLength;
|
||||
PRInt32 mType;
|
||||
};
|
||||
|
||||
|
||||
CertDownloader::CertDownloader(PRInt32 type)
|
||||
{
|
||||
NS_INIT_REFCNT();
|
||||
mByteData = nsnull;
|
||||
mType = type;
|
||||
}
|
||||
|
||||
CertDownloader::~CertDownloader()
|
||||
{
|
||||
if (mByteData)
|
||||
nsMemory::Free(mByteData);
|
||||
}
|
||||
|
||||
NS_IMPL_ISUPPORTS(CertDownloader,NS_GET_IID(nsIStreamListener));
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
CertDownloader::OnStartRequest(nsIChannel* channel, nsISupports* context)
|
||||
{
|
||||
channel->GetContentLength(&mContentLength);
|
||||
if (mContentLength == -1)
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
mBufferOffset = 0;
|
||||
mByteData = (char*) nsMemory::Alloc(mContentLength);
|
||||
if (!mByteData)
|
||||
return NS_ERROR_OUT_OF_MEMORY;
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
CertDownloader::OnDataAvailable(nsIChannel* channel,
|
||||
nsISupports* context,
|
||||
nsIInputStream *aIStream,
|
||||
PRUint32 aSourceOffset,
|
||||
PRUint32 aLength)
|
||||
{
|
||||
if (!mByteData)
|
||||
return NS_ERROR_OUT_OF_MEMORY;
|
||||
|
||||
PRUint32 amt;
|
||||
nsresult err;
|
||||
|
||||
do
|
||||
{
|
||||
err = aIStream->Read(mByteData+mBufferOffset, mContentLength-mBufferOffset, &amt);
|
||||
if (amt == 0) break;
|
||||
if (NS_FAILED(err)) return err;
|
||||
|
||||
aLength -= amt;
|
||||
mBufferOffset += amt;
|
||||
|
||||
} while (aLength > 0);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
CertDownloader::OnStopRequest(nsIChannel* channel,
|
||||
nsISupports* context,
|
||||
nsresult aStatus,
|
||||
const PRUnichar* aMsg)
|
||||
{
|
||||
|
||||
nsCOMPtr<nsIPSMComponent> psm = do_QueryInterface(context);
|
||||
|
||||
if (!psm) return NS_ERROR_FAILURE;
|
||||
|
||||
CMT_CONTROL *controlConnection;
|
||||
psm->GetControlConnection( &controlConnection );
|
||||
unsigned int certID;
|
||||
|
||||
certID = CMT_DecodeAndCreateTempCert(controlConnection, mByteData, mContentLength, mType);
|
||||
|
||||
if (certID)
|
||||
CMT_DestroyResource(controlConnection, certID, SSM_RESTYPE_CERTIFICATE);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
/* other mime types that we should handle sometime:
|
||||
|
||||
application/x-pkcs7-crl
|
||||
application/x-pkcs7-mime
|
||||
application/pkcs7-signature
|
||||
application/pre-encrypted
|
||||
|
||||
*/
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMComponent::HandleContent(const char * aContentType,
|
||||
const char * aCommand,
|
||||
const char * aWindowTarget,
|
||||
nsISupports* aWindowContext,
|
||||
nsIChannel * aChannel)
|
||||
{
|
||||
// We were called via CI. We better protect ourselves and addref.
|
||||
NS_ADDREF_THIS();
|
||||
|
||||
nsresult rv = NS_OK;
|
||||
if (!aChannel) return NS_ERROR_NULL_POINTER;
|
||||
|
||||
CMUint32 type = -1;
|
||||
|
||||
if ( nsCRT::strcasecmp(aContentType, "application/x-x509-ca-cert") == 0)
|
||||
{
|
||||
type = 1; //CA cert
|
||||
}
|
||||
else if (nsCRT::strcasecmp(aContentType, "application/x-x509-server-cert") == 0)
|
||||
{
|
||||
type = 2; //Server cert
|
||||
}
|
||||
else if (nsCRT::strcasecmp(aContentType, "application/x-x509-user-cert") == 0)
|
||||
{
|
||||
type = 3; //User cert
|
||||
}
|
||||
else if (nsCRT::strcasecmp(aContentType, "application/x-x509-email-cert") == 0)
|
||||
{
|
||||
type = 4; //Someone else's email cert
|
||||
}
|
||||
|
||||
if (type != -1)
|
||||
{
|
||||
// I can't directly open the passed channel cause it fails :-(
|
||||
|
||||
nsCOMPtr<nsIURI> uri;
|
||||
rv = aChannel->GetURI(getter_AddRefs(uri));
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
nsCOMPtr<nsIChannel> channel;
|
||||
rv = NS_OpenURI(getter_AddRefs(channel), uri);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
return channel->AsyncRead(new CertDownloader(type), NS_STATIC_CAST(nsIPSMComponent*,this));
|
||||
}
|
||||
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
|
||||
//---------------------------------------------
|
||||
// Functions Implenenting NSISignatureVerifier
|
||||
//---------------------------------------------
|
||||
NS_IMETHODIMP
|
||||
nsPSMComponent::HashBegin(PRUint32 alg, PRUint32* id)
|
||||
{
|
||||
CMT_CONTROL *controlConnection;
|
||||
if (NS_FAILED(GetControlConnection( &controlConnection )))
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
if(CMT_HashCreate(controlConnection, alg, (CMUint32*)id) != CMTSuccess)
|
||||
return NS_ERROR_FAILURE;
|
||||
if(CMT_HASH_Begin(controlConnection, *id) != CMTSuccess)
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMComponent::HashUpdate(PRUint32 id, const char* buf, PRUint32 buflen)
|
||||
{
|
||||
CMT_CONTROL *controlConnection;
|
||||
|
||||
if (NS_FAILED(GetControlConnection( &controlConnection )))
|
||||
return NS_ERROR_FAILURE;
|
||||
if (CMT_HASH_Update(controlConnection, id,
|
||||
(const unsigned char*)buf, buflen) != CMTSuccess)
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMComponent::HashEnd(PRUint32 id, unsigned char** hash,
|
||||
PRUint32* hashLen, PRUint32 maxLen)
|
||||
{
|
||||
if (!hash)
|
||||
return NS_ERROR_ILLEGAL_VALUE;
|
||||
|
||||
CMT_CONTROL *controlConnection;
|
||||
if (NS_FAILED(GetControlConnection( &controlConnection )))
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
if(CMT_HASH_End(controlConnection, id, *hash,
|
||||
(CMUint32*)hashLen, maxLen) != CMTSuccess)
|
||||
return NS_ERROR_FAILURE;
|
||||
CMT_HASH_Destroy(controlConnection, id);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMComponent::CreatePrincipalFromSignature(const char* aRSABuf, PRUint32 aRSABufLen,
|
||||
nsIPrincipal** aPrincipal)
|
||||
{
|
||||
PRInt32 errorCode;
|
||||
return VerifySignature(aRSABuf, aRSABufLen, nsnull, 0, &errorCode, aPrincipal);
|
||||
}
|
||||
|
||||
PR_STATIC_CALLBACK(void)
|
||||
UselessPK7DataSink(void* arg, const char* buf, CMUint32 len)
|
||||
{
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMComponent::VerifySignature(const char* aRSABuf, PRUint32 aRSABufLen,
|
||||
const char* aPlaintext, PRUint32 aPlaintextLen,
|
||||
PRInt32* aErrorCode,
|
||||
nsIPrincipal** aPrincipal)
|
||||
{
|
||||
if (!aPrincipal || !aErrorCode)
|
||||
return NS_ERROR_NULL_POINTER;
|
||||
*aErrorCode = 0;
|
||||
*aPrincipal = nsnull;
|
||||
|
||||
CMT_CONTROL *controlConnection;
|
||||
if (NS_FAILED(GetControlConnection( &controlConnection )))
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
//-- Decode the signature stream
|
||||
CMUint32 decoderID;
|
||||
CMInt32* blah = nsnull;
|
||||
CMTStatus result = CMT_PKCS7DecoderStart(controlConnection, nsnull,
|
||||
&decoderID, blah,
|
||||
UselessPK7DataSink, nsnull);
|
||||
if (result != CMTSuccess) return NS_ERROR_FAILURE;
|
||||
result = CMT_PKCS7DecoderUpdate(controlConnection, decoderID, aRSABuf, aRSABufLen);
|
||||
if (result != CMTSuccess) return NS_ERROR_FAILURE;
|
||||
CMUint32 contentInfo;
|
||||
result = CMT_PKCS7DecoderFinish(controlConnection,
|
||||
decoderID, &contentInfo);
|
||||
if (result != CMTSuccess) return NS_ERROR_FAILURE;
|
||||
|
||||
CMTItem hashItem;
|
||||
hashItem.data = 0;
|
||||
hashItem.len = 0;
|
||||
//-- If a plaintext was provided, hash it.
|
||||
if (aPlaintext)
|
||||
{
|
||||
CMUint32 hashId;
|
||||
CMT_HashCreate(controlConnection, nsISignatureVerifier::SHA1, &hashId);
|
||||
CMT_HASH_Begin(controlConnection, hashId);
|
||||
CMTStatus result = CMT_HASH_Update(controlConnection, hashId,
|
||||
(const unsigned char*)aPlaintext, aPlaintextLen);
|
||||
if (result != CMTSuccess) return NS_ERROR_FAILURE;
|
||||
|
||||
unsigned char* hash = (unsigned char*)PR_MALLOC(nsISignatureVerifier::SHA1_LENGTH);
|
||||
if (!hash) return NS_ERROR_OUT_OF_MEMORY;
|
||||
CMUint32 hashLen;
|
||||
result = CMT_HASH_End(controlConnection, hashId, hash,
|
||||
&hashLen, nsISignatureVerifier::SHA1_LENGTH);
|
||||
if (result != CMTSuccess)
|
||||
{
|
||||
PR_FREEIF(hash);
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
NS_ASSERTION(hashLen == nsISignatureVerifier::SHA1_LENGTH,
|
||||
"PSMComponent: Hash too short.");
|
||||
CMT_HASH_Destroy(controlConnection, hashId);
|
||||
hashItem.data = hash;
|
||||
hashItem.len = hashLen;
|
||||
}
|
||||
|
||||
//-- Verify signature
|
||||
// We need to call this function even if we're only creating a principal, not
|
||||
// verifying, because PSM won't give us certificate information unless this
|
||||
// function has been called.
|
||||
result = CMT_PKCS7VerifyDetachedSignature(controlConnection, contentInfo,
|
||||
6 /* =Object Signing Cert */,
|
||||
3 /* =SHA1 algorithm (MD5=2)*/,
|
||||
1,/* Save Certificate */
|
||||
&hashItem, (CMInt32*)aErrorCode);
|
||||
|
||||
if (result != CMTSuccess) return NS_ERROR_FAILURE;
|
||||
if (aPlaintext && *aErrorCode != 0) return NS_OK; // Verification failed.
|
||||
|
||||
CMUint32 certID;
|
||||
result = CMT_GetRIDAttribute(controlConnection, contentInfo,
|
||||
SSM_FID_P7CINFO_SIGNER_CERT, &certID);
|
||||
if ((result != CMTSuccess) || !certID) return NS_OK; // No signature present
|
||||
|
||||
CMTItem fingerprint;
|
||||
result = CMT_GetStringAttribute(controlConnection, certID,
|
||||
SSM_FID_CERT_FINGERPRINT, &fingerprint);
|
||||
if (result != CMTSuccess) return NS_ERROR_FAILURE;
|
||||
|
||||
//-- Get a principal
|
||||
nsresult rv;
|
||||
NS_WITH_SERVICE(nsIScriptSecurityManager, secMan,
|
||||
NS_SCRIPTSECURITYMANAGER_PROGID, &rv)
|
||||
if (NS_FAILED(rv)) return NS_ERROR_FAILURE;
|
||||
rv = secMan->GetCertificatePrincipal((char*)fingerprint.data,
|
||||
aPrincipal);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
//-- Get common name and store it in the principal.
|
||||
// Using common name + organizational unit as the user-visible certificate name
|
||||
nsCOMPtr<nsICertificatePrincipal> certificate = do_QueryInterface(*aPrincipal, &rv);
|
||||
if (NS_FAILED(rv)) return NS_ERROR_FAILURE;
|
||||
|
||||
CMTItem common;
|
||||
result = CMT_GetStringAttribute(controlConnection, certID,
|
||||
SSM_FID_CERT_COMMON_NAME, &common);
|
||||
if (result != CMTSuccess) return NS_ERROR_FAILURE;
|
||||
CMTItem subject;
|
||||
result = CMT_GetStringAttribute(controlConnection, certID,
|
||||
SSM_FID_CERT_SUBJECT_NAME, &subject);
|
||||
if (result != CMTSuccess) return NS_ERROR_FAILURE;
|
||||
|
||||
nsCAutoString commonName;
|
||||
commonName = (char*)common.data;
|
||||
static const char orgUnitTag[] = " OU=";
|
||||
char* orgUnitPos = PL_strstr((char*)subject.data, orgUnitTag);
|
||||
if (orgUnitPos)
|
||||
{
|
||||
orgUnitPos += sizeof(orgUnitTag)-1;
|
||||
char* orgUnitEnd = PL_strchr(orgUnitPos, ',');
|
||||
PRInt32 orgUnitLen;
|
||||
if(orgUnitEnd)
|
||||
orgUnitLen = orgUnitEnd - orgUnitPos;
|
||||
else
|
||||
orgUnitLen = PL_strlen(orgUnitPos);
|
||||
commonName.Append(' ');
|
||||
commonName.Append(orgUnitPos, orgUnitLen);
|
||||
}
|
||||
char* commonChar = commonName.ToNewCString();
|
||||
if (!commonChar) return NS_ERROR_OUT_OF_MEMORY;
|
||||
rv = certificate->SetCommonName(commonChar);
|
||||
Recycle(commonChar);
|
||||
return rv;
|
||||
}
|
||||
|
||||
60
mozilla/extensions/psm-glue/src/nsPSMComponent.h
Normal file
60
mozilla/extensions/psm-glue/src/nsPSMComponent.h
Normal file
@@ -0,0 +1,60 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#include "nscore.h"
|
||||
#include "nsIPSMComponent.h"
|
||||
#include "nsISignatureVerifier.h"
|
||||
#include "nsIStringBundle.h"
|
||||
|
||||
#include "nsIContentHandler.h"
|
||||
|
||||
#define SECURITY_STRING_BUNDLE_URL "chrome://communicator/locale/security.properties"
|
||||
|
||||
#define NS_PSMCOMPONENT_CID {0xddcae170, 0x5412, 0x11d3, {0xbb, 0xc8, 0x00, 0x00, 0x86, 0x1d, 0x12, 0x37}}
|
||||
|
||||
// Implementation of the PSM component interface.
|
||||
class nsPSMComponent : public nsIPSMComponent,
|
||||
public nsIContentHandler,
|
||||
public nsISignatureVerifier
|
||||
{
|
||||
public:
|
||||
NS_DEFINE_STATIC_CID_ACCESSOR( NS_PSMCOMPONENT_CID );
|
||||
|
||||
nsPSMComponent();
|
||||
virtual ~nsPSMComponent();
|
||||
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSIPSMCOMPONENT
|
||||
NS_DECL_NSICONTENTHANDLER
|
||||
NS_DECL_NSISIGNATUREVERIFIER
|
||||
|
||||
static NS_METHOD CreatePSMComponent(nsISupports* aOuter, REFNSIID aIID, void **aResult);
|
||||
|
||||
private:
|
||||
|
||||
PCMT_CONTROL mControl;
|
||||
|
||||
nsCOMPtr<nsISupports> mSecureBrowserIU;
|
||||
static nsPSMComponent* mInstance;
|
||||
};
|
||||
178
mozilla/extensions/psm-glue/src/nsPSMModule.cpp
Normal file
178
mozilla/extensions/psm-glue/src/nsPSMModule.cpp
Normal file
@@ -0,0 +1,178 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#include "nsIModule.h"
|
||||
#include "nsIGenericFactory.h"
|
||||
|
||||
#include "nsPSMUICallbacks.h"
|
||||
#include "nsPSMComponent.h"
|
||||
|
||||
#include "nsISecureBrowserUI.h"
|
||||
#include "nsSecureBrowserUIImpl.h"
|
||||
|
||||
#include "nsSSLSocketProvider.h"
|
||||
|
||||
#include "nsSDR.h"
|
||||
#include "nsFSDR.h"
|
||||
#include "nsCrypto.h"
|
||||
#include "nsKeygenHandler.h"
|
||||
//For the NS_CRYPTO_PROGID define
|
||||
#include "nsDOMCID.h"
|
||||
|
||||
#include "nsCURILoader.h"
|
||||
#include "nsISupportsUtils.h"
|
||||
|
||||
// Define SDR object constructor
|
||||
static NS_DEFINE_IID(kISupportsIID, NS_ISUPPORTS_IID);
|
||||
static NS_DEFINE_IID(kFormProcessorCID, NS_IFORMPROCESSOR_CID);
|
||||
|
||||
NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsSecretDecoderRing, init)
|
||||
NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsFSecretDecoderRing, init)
|
||||
NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsCrypto, init)
|
||||
NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsPkcs11, init)
|
||||
|
||||
static nsModuleComponentInfo components[] =
|
||||
{
|
||||
{
|
||||
PSM_COMPONENT_CLASSNAME,
|
||||
NS_PSMCOMPONENT_CID,
|
||||
PSM_COMPONENT_PROGID,
|
||||
nsPSMComponent::CreatePSMComponent
|
||||
},
|
||||
|
||||
{
|
||||
"PSM Content Handler - application/x-x509-ca-cert",
|
||||
NS_PSMCOMPONENT_CID,
|
||||
NS_CONTENT_HANDLER_PROGID_PREFIX"application/x-x509-ca-cert",
|
||||
nsPSMComponent::CreatePSMComponent
|
||||
},
|
||||
|
||||
{
|
||||
"PSM Content Handler - application/x-x509-server-cert",
|
||||
NS_PSMCOMPONENT_CID,
|
||||
NS_CONTENT_HANDLER_PROGID_PREFIX"application/x-x509-server-cert",
|
||||
nsPSMComponent::CreatePSMComponent
|
||||
},
|
||||
|
||||
{
|
||||
"PSM Content Handler - application/x-x509-user-cert",
|
||||
NS_PSMCOMPONENT_CID,
|
||||
NS_CONTENT_HANDLER_PROGID_PREFIX"application/x-x509-user-cert",
|
||||
nsPSMComponent::CreatePSMComponent
|
||||
},
|
||||
|
||||
{
|
||||
"PSM Content Handler - application/x-x509-email-cert",
|
||||
NS_PSMCOMPONENT_CID,
|
||||
NS_CONTENT_HANDLER_PROGID_PREFIX"application/x-x509-email-cert",
|
||||
nsPSMComponent::CreatePSMComponent
|
||||
},
|
||||
|
||||
|
||||
{
|
||||
PSM_UI_HANLDER_CLASSNAME,
|
||||
NS_PSMUIHANDLER_CID,
|
||||
PSM_UI_HANLDER_PROGID,
|
||||
nsPSMUIHandlerImpl::CreatePSMUIHandler
|
||||
},
|
||||
|
||||
{
|
||||
NS_SECURE_BROWSER_UI_CLASSNAME,
|
||||
NS_SECURE_BROWSER_UI_CID,
|
||||
NS_SECURE_BROWSER_UI_PROGID,
|
||||
nsSecureBrowserUIImpl::Create
|
||||
},
|
||||
|
||||
{
|
||||
NS_SECURE_BROWSER_DOCOBSERVER_CLASSNAME,
|
||||
NS_SECURE_BROWSER_DOCOBSERVER_CID,
|
||||
NS_SECURE_BROWSER_DOCOBSERVER_PROGID,
|
||||
nsSecureBrowserUIImpl::Create
|
||||
},
|
||||
|
||||
{
|
||||
NS_ISSLSOCKETPROVIDER_CLASSNAME,
|
||||
NS_SSLSOCKETPROVIDER_CID,
|
||||
NS_ISSLSOCKETPROVIDER_PROGID,
|
||||
nsSSLSocketProvider::Create
|
||||
},
|
||||
|
||||
{
|
||||
NS_SDR_CLASSNAME,
|
||||
NS_SDR_CID,
|
||||
NS_SDR_PROGID,
|
||||
nsSecretDecoderRingConstructor
|
||||
},
|
||||
|
||||
{
|
||||
NS_FSDR_CLASSNAME,
|
||||
NS_FSDR_CID,
|
||||
NS_FSDR_PROGID,
|
||||
nsFSecretDecoderRingConstructor
|
||||
},
|
||||
|
||||
{
|
||||
NS_CRYPTO_CLASSNAME,
|
||||
NS_CRYPTO_CID,
|
||||
NS_CRYPTO_PROGID,
|
||||
nsCryptoConstructor
|
||||
},
|
||||
{
|
||||
NS_PKCS11_CLASSNAME,
|
||||
NS_PKCS11_CID,
|
||||
NS_PKCS11_PROGID,
|
||||
nsPkcs11Constructor
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
#if 0
|
||||
NS_IMPL_NSGETMODULE("PSMComponent", components);
|
||||
#endif
|
||||
|
||||
extern "C" NS_EXPORT nsresult NSGetModule(nsIComponentManager *servMgr,
|
||||
nsIFile* location,
|
||||
nsIModule** result)
|
||||
{
|
||||
nsresult rv;
|
||||
// Put in code to register KEYGEN form input handler.
|
||||
rv= NS_NewGenericModule("PSMComponent",
|
||||
sizeof(components) / sizeof(components[0]),
|
||||
components, nsnull, result);
|
||||
// Register a form processor. The form processor has the opportunity to
|
||||
// modify the value's passed during form submission.
|
||||
nsKeygenFormProcessor* testFormProcessor = new nsKeygenFormProcessor();
|
||||
nsCOMPtr<nsISupports> formProcessor;
|
||||
rv = testFormProcessor->QueryInterface(kISupportsIID,
|
||||
getter_AddRefs(formProcessor));
|
||||
if (NS_SUCCEEDED(rv) && formProcessor) {
|
||||
rv = nsServiceManager::RegisterService(kFormProcessorCID, formProcessor);
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
72
mozilla/extensions/psm-glue/src/nsPSMMutex.c
Normal file
72
mozilla/extensions/psm-glue/src/nsPSMMutex.c
Normal file
@@ -0,0 +1,72 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#include "prmon.h"
|
||||
#include "prtypes.h"
|
||||
|
||||
#include "nsPSMMutex.h"
|
||||
|
||||
static PRMonitor *_nsPSMMutexVar;
|
||||
|
||||
PRStatus
|
||||
nsPSMMutexInit()
|
||||
{
|
||||
if (!_nsPSMMutexVar)
|
||||
_nsPSMMutexVar = PR_NewMonitor();
|
||||
|
||||
return _nsPSMMutexVar ? PR_SUCCESS : PR_FAILURE;
|
||||
}
|
||||
|
||||
PRStatus
|
||||
nsPSMMutexDestroy()
|
||||
{
|
||||
if (!_nsPSMMutexVar)
|
||||
return PR_FAILURE;
|
||||
|
||||
PR_Wait(_nsPSMMutexVar, PR_INTERVAL_NO_TIMEOUT);
|
||||
|
||||
PR_DestroyMonitor(_nsPSMMutexVar);
|
||||
return PR_SUCCESS;
|
||||
}
|
||||
|
||||
static void
|
||||
nsPSMMutexLock(CMTMutexPointer *p)
|
||||
{
|
||||
PR_EnterMonitor(*(PRMonitor **)p);
|
||||
return;
|
||||
}
|
||||
|
||||
static void
|
||||
nsPSMMutexUnlock(CMTMutexPointer *p)
|
||||
{
|
||||
PR_ExitMonitor(*(PRMonitor **)p);
|
||||
return;
|
||||
}
|
||||
|
||||
CMT_MUTEX nsPSMMutexTbl =
|
||||
{
|
||||
&_nsPSMMutexVar,
|
||||
(CMTMutexFunction)nsPSMMutexLock,
|
||||
(CMTMutexFunction)nsPSMMutexUnlock
|
||||
};
|
||||
39
mozilla/extensions/psm-glue/src/nsPSMMutex.h
Normal file
39
mozilla/extensions/psm-glue/src/nsPSMMutex.h
Normal file
@@ -0,0 +1,39 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#ifndef _NSPSMMUTEX_H
|
||||
#define _NSPSMMUTEX_H
|
||||
|
||||
#include "cmtcmn.h"
|
||||
|
||||
PR_BEGIN_EXTERN_C
|
||||
|
||||
PR_EXTERN(CMT_MUTEX) nsPSMMutexTbl;
|
||||
|
||||
PR_EXTERN(PRStatus) nsPSMMutexInit(void);
|
||||
PR_EXTERN(PRStatus) nsPSMMutexDestroy(void);
|
||||
|
||||
PR_END_EXTERN_C
|
||||
|
||||
#endif
|
||||
293
mozilla/extensions/psm-glue/src/nsPSMShimLayer.c
Normal file
293
mozilla/extensions/psm-glue/src/nsPSMShimLayer.c
Normal file
@@ -0,0 +1,293 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#include "nspr.h"
|
||||
#include "nsPSMShimLayer.h"
|
||||
|
||||
#ifdef XP_UNIX
|
||||
#include <sys/stat.h>
|
||||
#include <unistd.h>
|
||||
#include "private/pprio.h" /* for PR_Socket */
|
||||
#endif
|
||||
|
||||
#define PSM_TIMEOUT_IN_SEC 300
|
||||
|
||||
#define NSPSMSHIMMAXFD 50
|
||||
|
||||
|
||||
static PRIntervalTime gTimeout = PR_INTERVAL_NO_TIMEOUT;
|
||||
|
||||
CMT_SocketFuncs nsPSMShimTbl =
|
||||
{
|
||||
nsPSMShimGetSocket,
|
||||
nsPSMShimConnect,
|
||||
nsPSMShimVerifyUnixSocket,
|
||||
nsPSMShimSend,
|
||||
nsPSMShimSelect,
|
||||
nsPSMShimReceive,
|
||||
nsPSMShimShutdown,
|
||||
nsPSMShimClose
|
||||
};
|
||||
|
||||
|
||||
CMTSocket
|
||||
nsPSMShimGetSocket(int unixSock)
|
||||
{
|
||||
PRStatus rv;
|
||||
PRFileDesc *fd;
|
||||
CMSocket *sock;
|
||||
PRSocketOptionData sockopt;
|
||||
|
||||
/*
|
||||
if (PR_INTERVAL_NO_WAIT == gTimeout)
|
||||
{
|
||||
gTimeout = PR_SecondsToInterval(PSM_TIMEOUT_IN_SEC);
|
||||
}
|
||||
*/
|
||||
|
||||
if (unixSock)
|
||||
{
|
||||
#ifndef XP_UNIX
|
||||
return NULL;
|
||||
#else
|
||||
fd = PR_Socket(PR_AF_LOCAL, PR_SOCK_STREAM, 0);
|
||||
PR_ASSERT(fd);
|
||||
#endif
|
||||
}
|
||||
else
|
||||
{
|
||||
fd = PR_NewTCPSocket();
|
||||
PR_ASSERT(fd);
|
||||
|
||||
/* disable Nagle algorithm delay for control sockets */
|
||||
sockopt.option = PR_SockOpt_NoDelay;
|
||||
sockopt.value.no_delay = PR_TRUE;
|
||||
rv = PR_SetSocketOption(fd, &sockopt);
|
||||
PR_ASSERT(PR_SUCCESS == rv);
|
||||
}
|
||||
|
||||
sock = (CMSocket *)PR_Malloc(sizeof(CMSocket));
|
||||
|
||||
if (sock == NULL)
|
||||
return sock;
|
||||
|
||||
sock->fd = fd;
|
||||
sock->isUnix = unixSock;
|
||||
|
||||
memset(&sock->netAddr, 0, sizeof(PRNetAddr));
|
||||
|
||||
return (CMTSocket)sock;
|
||||
}
|
||||
|
||||
CMTStatus
|
||||
nsPSMShimConnect(CMTSocket sock, short port, char *path)
|
||||
{
|
||||
CMTStatus rv = CMTSuccess;
|
||||
PRStatus err;
|
||||
PRErrorCode errcode;
|
||||
PRSocketOptionData sockopt;
|
||||
PRBool nonBlocking;
|
||||
CMSocket *cmSock = (CMSocket *)sock;
|
||||
|
||||
if (!sock) return CMTFailure;
|
||||
|
||||
if (cmSock->isUnix)
|
||||
{
|
||||
#ifndef XP_UNIX
|
||||
return CMTFailure;
|
||||
#else
|
||||
int pathLen;
|
||||
if (!path)
|
||||
{
|
||||
return CMTFailure;
|
||||
}
|
||||
|
||||
/* check buffer overrun */
|
||||
pathLen = strlen(path)+1;
|
||||
|
||||
pathLen = pathLen < sizeof(cmSock->netAddr.local.path)
|
||||
? pathLen : sizeof(cmSock->netAddr.local.path);
|
||||
|
||||
memcpy(&cmSock->netAddr.local.path, path, pathLen);
|
||||
cmSock->netAddr.local.family = PR_AF_LOCAL;
|
||||
#endif
|
||||
}
|
||||
else /* cmSock->isUnix */
|
||||
{
|
||||
cmSock->netAddr.inet.family = PR_AF_INET;
|
||||
cmSock->netAddr.inet.port = PR_htons(port);
|
||||
cmSock->netAddr.inet.ip = PR_htonl(PR_INADDR_LOOPBACK);
|
||||
}
|
||||
|
||||
/* Save non-blocking status */
|
||||
sockopt.option = PR_SockOpt_Nonblocking;
|
||||
err = PR_GetSocketOption(cmSock->fd, &sockopt);
|
||||
PR_ASSERT(PR_SUCCESS == err);
|
||||
|
||||
nonBlocking = sockopt.value.non_blocking;
|
||||
|
||||
/* make connect blocking for now */
|
||||
sockopt.option = PR_SockOpt_Nonblocking;
|
||||
sockopt.value.non_blocking = PR_FALSE;
|
||||
err = PR_SetSocketOption(cmSock->fd, &sockopt);
|
||||
PR_ASSERT(PR_SUCCESS == err);
|
||||
|
||||
err = PR_Connect( cmSock->fd, &cmSock->netAddr, PR_INTERVAL_MAX );
|
||||
|
||||
if (err == PR_FAILURE)
|
||||
{
|
||||
errcode = PR_GetError();
|
||||
|
||||
if (PR_IS_CONNECTED_ERROR != errcode)
|
||||
rv = CMTFailure;
|
||||
}
|
||||
|
||||
/* restore nonblock status */
|
||||
if (nonBlocking) {
|
||||
sockopt.option = PR_SockOpt_Nonblocking;
|
||||
sockopt.value.non_blocking = nonBlocking;
|
||||
err = PR_SetSocketOption(cmSock->fd, &sockopt);
|
||||
PR_ASSERT(PR_SUCCESS == err);
|
||||
}
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
CMTStatus
|
||||
nsPSMShimVerifyUnixSocket(CMTSocket sock)
|
||||
{
|
||||
#ifndef XP_UNIX
|
||||
return CMTFailure;
|
||||
#else
|
||||
|
||||
int rv;
|
||||
CMSocket *cmSock;
|
||||
struct stat statbuf;
|
||||
|
||||
cmSock = (CMSocket *)sock;
|
||||
|
||||
if (!cmSock || !cmSock->isUnix)
|
||||
return CMTFailure;
|
||||
|
||||
rv = stat(cmSock->netAddr.local.path, &statbuf);
|
||||
if (rv < 0 || statbuf.st_uid != geteuid() )
|
||||
{
|
||||
PR_Close(cmSock->fd);
|
||||
cmSock->fd = NULL;
|
||||
PR_Free(cmSock);
|
||||
return CMTFailure;
|
||||
}
|
||||
return CMTSuccess;
|
||||
#endif
|
||||
}
|
||||
|
||||
size_t
|
||||
nsPSMShimSend(CMTSocket sock, void *buffer, size_t length)
|
||||
{
|
||||
CMSocket *cmSock = (CMSocket *)sock;
|
||||
|
||||
if (!sock) return CMTFailure;
|
||||
|
||||
return PR_Send(cmSock->fd, buffer, length, 0, gTimeout);
|
||||
}
|
||||
|
||||
size_t
|
||||
nsPSMShimReceive(CMTSocket sock, void *buffer, size_t bufSize)
|
||||
{
|
||||
CMSocket *cmSock = (CMSocket *)sock;
|
||||
|
||||
if (!sock) return CMTFailure;
|
||||
|
||||
return PR_Recv(cmSock->fd, buffer, bufSize, 0, gTimeout);
|
||||
}
|
||||
|
||||
|
||||
CMTSocket
|
||||
nsPSMShimSelect(CMTSocket *socks, int numsocks, int poll)
|
||||
{
|
||||
CMSocket **sockArr = (CMSocket **)socks;
|
||||
PRPollDesc readPDs[NSPSMSHIMMAXFD];
|
||||
PRIntervalTime timeout;
|
||||
PRInt32 cnt;
|
||||
int i;
|
||||
|
||||
if (!socks) return NULL;
|
||||
|
||||
memset(readPDs, 0, sizeof(readPDs));
|
||||
|
||||
PR_ASSERT(NSPSMSHIMMAXFD >= numsocks);
|
||||
|
||||
for (i=0; i<numsocks; i++)
|
||||
{
|
||||
readPDs[i].fd = sockArr[i]->fd;
|
||||
readPDs[i].in_flags = PR_POLL_READ;
|
||||
}
|
||||
|
||||
timeout = poll ? PR_INTERVAL_NO_WAIT : PR_INTERVAL_NO_TIMEOUT;
|
||||
|
||||
cnt = PR_Poll(readPDs, numsocks, timeout);
|
||||
|
||||
/* Figure out which socket was selected */
|
||||
if (cnt > 0)
|
||||
{
|
||||
for (i=0; i<numsocks; i++)
|
||||
{
|
||||
if (readPDs[i].out_flags & PR_POLL_READ)
|
||||
{
|
||||
return (CMTSocket)sockArr[i];
|
||||
}
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
CMTStatus
|
||||
nsPSMShimShutdown(CMTSocket sock)
|
||||
{
|
||||
CMSocket *cmSock = (CMSocket*)sock;
|
||||
PRStatus rv;
|
||||
|
||||
if (!sock) return CMTFailure;
|
||||
|
||||
rv = PR_Shutdown(cmSock->fd, PR_SHUTDOWN_SEND);
|
||||
return (PR_SUCCESS == rv) ? CMTSuccess : CMTFailure;
|
||||
}
|
||||
|
||||
CMTStatus
|
||||
nsPSMShimClose(CMTSocket sock)
|
||||
{
|
||||
CMSocket *cmSock = (CMSocket*)sock;
|
||||
PRStatus rv = PR_SUCCESS;
|
||||
PR_ASSERT(cmSock);
|
||||
|
||||
if (!sock) return CMTFailure;
|
||||
|
||||
rv = PR_Close(cmSock->fd);
|
||||
cmSock->fd = NULL;
|
||||
|
||||
PR_Free(cmSock);
|
||||
|
||||
return (PR_SUCCESS == rv) ? CMTSuccess : CMTFailure;
|
||||
}
|
||||
67
mozilla/extensions/psm-glue/src/nsPSMShimLayer.h
Normal file
67
mozilla/extensions/psm-glue/src/nsPSMShimLayer.h
Normal file
@@ -0,0 +1,67 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#ifndef _NSPSMSHIMLAYER_H_
|
||||
#define _NSPSMSHIMLAYER_H_
|
||||
|
||||
#include "cmtcmn.h"
|
||||
#include "prio.h"
|
||||
|
||||
PR_BEGIN_EXTERN_C
|
||||
|
||||
typedef struct CMSocket {
|
||||
PRFileDesc *fd;
|
||||
PRBool isUnix;
|
||||
PRNetAddr netAddr;
|
||||
} CMSocket;
|
||||
|
||||
PR_EXTERN(CMT_SocketFuncs) nsPSMShimTbl;
|
||||
|
||||
PR_EXTERN(CMTSocket)
|
||||
nsPSMShimGetSocket(int unixSock);
|
||||
|
||||
PR_EXTERN(CMTStatus)
|
||||
nsPSMShimConnect(CMTSocket sock, short port, char *path);
|
||||
|
||||
PR_EXTERN(CMTStatus)
|
||||
nsPSMShimVerifyUnixSocket(CMTSocket sock);
|
||||
|
||||
PR_EXTERN(size_t)
|
||||
nsPSMShimSend(CMTSocket sock, void *buffer, size_t length);
|
||||
|
||||
PR_EXTERN(CMTSocket)
|
||||
nsPSMShimSelect(CMTSocket *socks, int numsocks, int poll);
|
||||
|
||||
PR_EXTERN(size_t)
|
||||
nsPSMShimReceive(CMTSocket sock, void *buffer, size_t bufSize);
|
||||
|
||||
PR_EXTERN(CMTStatus)
|
||||
nsPSMShimShutdown(CMTSocket sock);
|
||||
|
||||
PR_EXTERN(CMTStatus)
|
||||
nsPSMShimClose(CMTSocket sock);
|
||||
|
||||
PR_END_EXTERN_C
|
||||
|
||||
#endif /* _NSPSMSHIMLAYER_H_ */
|
||||
348
mozilla/extensions/psm-glue/src/nsPSMUICallbacks.cpp
Normal file
348
mozilla/extensions/psm-glue/src/nsPSMUICallbacks.cpp
Normal file
@@ -0,0 +1,348 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#include "nsProxiedService.h"
|
||||
#include "nsIEventQueueService.h"
|
||||
#include "nsPSMUICallbacks.h"
|
||||
#include "nsINetSupportDialogService.h"
|
||||
#include "nsIFilePicker.h"
|
||||
|
||||
#include "nsAppShellCIDs.h"
|
||||
#include "prprf.h"
|
||||
#include "prmem.h"
|
||||
|
||||
#include "nsSSLIOLayer.h" // for SSMSTRING_PADDED_LENGTH
|
||||
#include "ssmdefs.h"
|
||||
#include "rsrcids.h"
|
||||
|
||||
// Interfaces Needed
|
||||
#include "nsIAppShellService.h"
|
||||
#include "nsIDocShell.h"
|
||||
#include "nsIDOMWindow.h"
|
||||
#include "nsIInterfaceRequestor.h"
|
||||
#include "nsIPrompt.h"
|
||||
#include "nsIScriptGlobalObject.h"
|
||||
#include "nsIURL.h"
|
||||
#include "nsIXULWindow.h"
|
||||
|
||||
static NS_DEFINE_IID(kAppShellServiceCID, NS_APPSHELL_SERVICE_CID);
|
||||
static NS_DEFINE_CID(kNetSupportDialogCID, NS_NETSUPPORTDIALOG_CID);
|
||||
|
||||
|
||||
// Happy callbacks
|
||||
static char * PromptUserCallback(void *arg, char *prompt, int isPasswd);
|
||||
static char * FilePathPromptCallback(void *arg, char *prompt, char *fileRegEx, CMUint32 shouldFileExist);
|
||||
static void ApplicationFreeCallback(char *userInput);
|
||||
|
||||
static void * CartmanUIHandler(uint32 resourceID, void* clientContext, uint32 width, uint32 height,
|
||||
CMBool isModal, char* urlStr, void *data);
|
||||
|
||||
extern "C" void CARTMAN_UIEventLoop(void *data);
|
||||
|
||||
|
||||
/* nsISupports Implementation for the class */
|
||||
NS_IMPL_THREADSAFE_ISUPPORTS1(nsPSMUIHandlerImpl, nsIPSMUIHandler)
|
||||
|
||||
NS_METHOD
|
||||
nsPSMUIHandlerImpl::DisplayURI(PRInt32 width, PRInt32 height, PRBool modal, const char *urlStr)
|
||||
{
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsIDOMWindow> hiddenWindow;
|
||||
JSContext *jsContext;
|
||||
|
||||
NS_WITH_SERVICE(nsIAppShellService, appShell, kAppShellServiceCID, &rv);
|
||||
if (NS_SUCCEEDED(rv))
|
||||
{
|
||||
rv = appShell->GetHiddenWindowAndJSContext( getter_AddRefs( hiddenWindow ),
|
||||
&jsContext );
|
||||
|
||||
if ( NS_SUCCEEDED( rv ) )
|
||||
{
|
||||
// Set up arguments for "window.open"
|
||||
void *stackPtr;
|
||||
char params[36];
|
||||
|
||||
if (modal) // if you change this, remember to change the buffer size above.
|
||||
strcpy(params, "menubar=no,height=%d,width=%d,modal");
|
||||
else
|
||||
strcpy(params, "menubar=no,height=%d,width=%d");
|
||||
|
||||
char buffer[256];
|
||||
PR_snprintf(buffer,
|
||||
sizeof(buffer),
|
||||
params,
|
||||
height,
|
||||
width );
|
||||
|
||||
jsval *argv = JS_PushArguments(jsContext, &stackPtr, "sss", urlStr, "_blank", buffer);
|
||||
if (argv)
|
||||
{
|
||||
// open the window
|
||||
nsIDOMWindow *newWindow;
|
||||
hiddenWindow->Open(jsContext, argv, 3, &newWindow);
|
||||
newWindow->ResizeTo(width, height);
|
||||
JS_PopArguments(jsContext, stackPtr);
|
||||
}
|
||||
}
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMUIHandlerImpl::PromptForFile(const PRUnichar *prompt, const char *fileRegEx, PRBool shouldFileExist, char **outFile)
|
||||
{
|
||||
NS_ENSURE_ARG_POINTER(outFile);
|
||||
nsCOMPtr<nsIFilePicker> fp = do_CreateInstance("component://mozilla/filepicker");
|
||||
|
||||
if (!fp)
|
||||
return NS_ERROR_NULL_POINTER;
|
||||
|
||||
|
||||
fp->Init(nsnull, prompt, nsIFilePicker::modeOpen);
|
||||
fp->AppendFilter(NS_ConvertASCIItoUCS2(fileRegEx).GetUnicode(), NS_ConvertASCIItoUCS2(fileRegEx).GetUnicode());
|
||||
fp->AppendFilters(nsIFilePicker::filterAll);
|
||||
PRInt16 mode;
|
||||
nsresult rv = fp->Show(&mode);
|
||||
|
||||
if (NS_FAILED(rv) || (mode == nsIFilePicker::returnCancel))
|
||||
return rv;
|
||||
|
||||
nsCOMPtr<nsILocalFile> file;
|
||||
rv = fp->GetFile(getter_AddRefs(file));
|
||||
|
||||
if (file)
|
||||
file->GetPath(outFile);
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
NS_METHOD
|
||||
nsPSMUIHandlerImpl::CreatePSMUIHandler(nsISupports* aOuter, REFNSIID aIID, void **aResult)
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
if ( aResult )
|
||||
{
|
||||
/* Allocate new find component object. */
|
||||
nsPSMUIHandlerImpl *component = new nsPSMUIHandlerImpl();
|
||||
if ( component )
|
||||
{
|
||||
/* Allocated OK, do query interface to get proper */
|
||||
/* pointer and increment refcount. */
|
||||
rv = component->QueryInterface( aIID, aResult );
|
||||
if ( NS_FAILED( rv ) )
|
||||
{
|
||||
/* refcount still at zero, delete it here. */
|
||||
delete component;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
rv = NS_ERROR_OUT_OF_MEMORY;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
rv = NS_ERROR_NULL_POINTER;
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
||||
|
||||
extern "C" void CARTMAN_UIEventLoop(void *data)
|
||||
{
|
||||
CMT_EventLoop((PCMT_CONTROL)data);
|
||||
}
|
||||
|
||||
PRStatus InitPSMEventLoop(PCMT_CONTROL control)
|
||||
{
|
||||
PR_CreateThread(PR_USER_THREAD,
|
||||
CARTMAN_UIEventLoop,
|
||||
control,
|
||||
PR_PRIORITY_NORMAL,
|
||||
PR_GLOBAL_THREAD,
|
||||
PR_UNJOINABLE_THREAD,
|
||||
0);
|
||||
|
||||
return PR_SUCCESS;
|
||||
}
|
||||
|
||||
PRStatus InitPSMUICallbacks(PCMT_CONTROL control)
|
||||
{
|
||||
if (!control)
|
||||
return PR_FAILURE;
|
||||
|
||||
CMT_SetPromptCallback(control, (promptCallback_fn)PromptUserCallback, nsnull);
|
||||
CMT_SetAppFreeCallback(control, (applicationFreeCallback_fn) ApplicationFreeCallback);
|
||||
CMT_SetFilePathPromptCallback(control, (filePathPromptCallback_fn) FilePathPromptCallback, nsnull);
|
||||
|
||||
if (CMT_SetUIHandlerCallback(control, (uiHandlerCallback_fn) CartmanUIHandler, NULL) != CMTSuccess)
|
||||
return PR_FAILURE;
|
||||
|
||||
return PR_SUCCESS;
|
||||
}
|
||||
|
||||
PRStatus DisplayPSMUIDialog(PCMT_CONTROL control, const char *pickledStatus, const char *hostName)
|
||||
{
|
||||
CMUint32 advRID = 0;
|
||||
CMInt32 width = 0;
|
||||
CMInt32 height = 0;
|
||||
CMTItem urlItem = {0, NULL, 0};
|
||||
CMTStatus rv = CMTSuccess;
|
||||
CMTItem advisorContext = {0, NULL, 0};
|
||||
void * pwin;
|
||||
|
||||
CMTSecurityAdvisorData data;
|
||||
memset(&data, '\0', sizeof(CMTSecurityAdvisorData));
|
||||
|
||||
if (hostName)
|
||||
{
|
||||
// if there is a hostName, than this request is about
|
||||
// a webpage.
|
||||
data.hostname = (char*) hostName;
|
||||
data.infoContext = SSM_BROWSER;
|
||||
|
||||
if (pickledStatus)
|
||||
{
|
||||
CMTItem pickledResource = {0, NULL, 0};
|
||||
CMUint32 socketStatus = 0;
|
||||
|
||||
pickledResource.len = *(int*)(pickledStatus);
|
||||
pickledResource.data = (unsigned char*) PR_Malloc(SSMSTRING_PADDED_LENGTH(pickledResource.len));
|
||||
|
||||
if (! pickledResource.data) return PR_FAILURE;
|
||||
|
||||
memcpy(pickledResource.data, pickledStatus+sizeof(int), pickledResource.len);
|
||||
|
||||
/* Unpickle the SSL Socket Status */
|
||||
if (CMT_UnpickleResource( control,
|
||||
SSM_RESTYPE_SSL_SOCKET_STATUS,
|
||||
pickledResource,
|
||||
&socketStatus) == CMTSuccess)
|
||||
{
|
||||
data.infoContext = SSM_BROWSER;
|
||||
data.resID = socketStatus;
|
||||
}
|
||||
|
||||
PR_FREEIF(pickledResource.data);
|
||||
}
|
||||
}
|
||||
|
||||
/* Create a Security Advisor context object. */
|
||||
rv = CMT_SecurityAdvisor(control, &data, &advRID);
|
||||
|
||||
if (rv != CMTSuccess)
|
||||
return PR_FAILURE;
|
||||
|
||||
/* Get the URL, width, height, etc. from the advisor context. */
|
||||
rv = CMT_GetStringAttribute(control,
|
||||
advRID,
|
||||
SSM_FID_SECADVISOR_URL,
|
||||
&urlItem);
|
||||
|
||||
if ((rv != CMTSuccess) || (!urlItem.data))
|
||||
return PR_FAILURE;
|
||||
|
||||
rv = CMT_GetNumericAttribute(control,
|
||||
advRID,
|
||||
SSM_FID_SECADVISOR_WIDTH,
|
||||
&width);
|
||||
if (rv != CMTSuccess)
|
||||
return PR_FAILURE;
|
||||
|
||||
rv = CMT_GetNumericAttribute(control,
|
||||
advRID,
|
||||
SSM_FID_SECADVISOR_HEIGHT,
|
||||
&height);
|
||||
if (rv != CMTSuccess)
|
||||
return PR_FAILURE;
|
||||
|
||||
/* Fire the URL up in a window of its own. */
|
||||
pwin = CartmanUIHandler(advRID, nsnull, width, height, CM_FALSE, (char*)urlItem.data, NULL);
|
||||
|
||||
//allocated by cmt, we can free with free:
|
||||
free(urlItem.data);
|
||||
|
||||
return PR_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void* CartmanUIHandler(uint32 resourceID, void* clientContext, uint32 width, uint32 height, CMBool isModal, char* urlStr, void *data)
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
|
||||
NS_WITH_PROXIED_SERVICE(nsIPSMUIHandler, handler, nsPSMUIHandlerImpl::GetCID(), NS_UI_THREAD_EVENTQ, &rv);
|
||||
|
||||
if(NS_SUCCEEDED(rv))
|
||||
handler->DisplayURI(width, height, isModal, urlStr);
|
||||
|
||||
return nsnull;
|
||||
}
|
||||
|
||||
|
||||
|
||||
char * PromptUserCallback(void *arg, char *prompt, int isPasswd)
|
||||
{
|
||||
|
||||
nsresult rv = NS_OK;
|
||||
PRUnichar *password;
|
||||
PRBool value;
|
||||
|
||||
NS_WITH_PROXIED_SERVICE(nsIPrompt, dialog, kNetSupportDialogCID, NS_UI_THREAD_EVENTQ, &rv);
|
||||
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
rv = dialog->PromptPassword(nsnull, NS_ConvertASCIItoUCS2(prompt).GetUnicode(),
|
||||
NS_ConvertASCIItoUCS2(" ").GetUnicode(), // hostname
|
||||
PR_TRUE, &password, &value);
|
||||
|
||||
if (NS_SUCCEEDED(rv) && value) {
|
||||
nsString a(password);
|
||||
char* str = a.ToNewCString();
|
||||
Recycle(password);
|
||||
return str;
|
||||
}
|
||||
}
|
||||
|
||||
return nsnull;
|
||||
}
|
||||
|
||||
void ApplicationFreeCallback(char *userInput)
|
||||
{
|
||||
nsMemory::Free(userInput);
|
||||
}
|
||||
|
||||
char * FilePathPromptCallback(void *arg, char *prompt, char *fileRegEx, CMUint32 shouldFileExist)
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
|
||||
char* filePath = nsnull;
|
||||
|
||||
NS_WITH_PROXIED_SERVICE(nsIPSMUIHandler, handler, nsPSMUIHandlerImpl::GetCID(), NS_UI_THREAD_EVENTQ, &rv);
|
||||
|
||||
if(NS_SUCCEEDED(rv))
|
||||
handler->PromptForFile(NS_ConvertASCIItoUCS2(prompt).GetUnicode(), fileRegEx, (PRBool)shouldFileExist, &filePath);
|
||||
|
||||
return filePath;
|
||||
}
|
||||
56
mozilla/extensions/psm-glue/src/nsPSMUICallbacks.h
Normal file
56
mozilla/extensions/psm-glue/src/nsPSMUICallbacks.h
Normal file
@@ -0,0 +1,56 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#ifndef _NSPSMUICALLBACKS_H
|
||||
#define _NSPSMUICALLBACKS_H
|
||||
|
||||
#include "prtypes.h"
|
||||
#include "cmtcmn.h"
|
||||
|
||||
#include "nsIPSMUIHandler.h"
|
||||
|
||||
PRStatus InitPSMUICallbacks(PCMT_CONTROL gControl);
|
||||
PRStatus InitPSMEventLoop(PCMT_CONTROL gControl);
|
||||
PRStatus DisplayPSMUIDialog(PCMT_CONTROL control, const char* pickledStatus, const char *hostName);
|
||||
|
||||
|
||||
#define NS_PSMUIHANDLER_CID {0x15944e30, 0x601e, 0x11d3, {0x8c, 0x4a, 0x00, 0x00, 0x64, 0x65, 0x73, 0x74}}
|
||||
|
||||
class nsPSMUIHandlerImpl : public nsIPSMUIHandler
|
||||
{
|
||||
public:
|
||||
|
||||
NS_DEFINE_STATIC_CID_ACCESSOR( NS_PSMUIHANDLER_CID );
|
||||
|
||||
/* ctor/dtor */
|
||||
nsPSMUIHandlerImpl() { NS_INIT_REFCNT(); }
|
||||
virtual ~nsPSMUIHandlerImpl() { }
|
||||
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSIPSMUIHANDLER
|
||||
|
||||
static NS_METHOD CreatePSMUIHandler(nsISupports* aOuter, REFNSIID aIID, void **aResult);
|
||||
};
|
||||
|
||||
#endif
|
||||
320
mozilla/extensions/psm-glue/src/nsSDR.cpp
Normal file
320
mozilla/extensions/psm-glue/src/nsSDR.cpp
Normal file
@@ -0,0 +1,320 @@
|
||||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
||||
*
|
||||
* The contents of this file are subject to the Netscape 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/NPL/
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* thayes@netscape.com
|
||||
*/
|
||||
|
||||
#include "stdlib.h"
|
||||
#include "plstr.h"
|
||||
#include "nsMemory.h"
|
||||
#include "nsIServiceManager.h"
|
||||
|
||||
#include "plbase64.h"
|
||||
|
||||
#include "nsISecretDecoderRing.h"
|
||||
|
||||
#include "cmtcmn.h"
|
||||
#include "nsIPSMComponent.h"
|
||||
|
||||
#include "nsSDR.h"
|
||||
|
||||
NS_IMPL_ISUPPORTS1(nsSecretDecoderRing, nsISecretDecoderRing)
|
||||
|
||||
nsSecretDecoderRing::nsSecretDecoderRing()
|
||||
{
|
||||
NS_INIT_ISUPPORTS();
|
||||
|
||||
mPSM = NULL;
|
||||
}
|
||||
|
||||
nsSecretDecoderRing::~nsSecretDecoderRing()
|
||||
{
|
||||
if (mPSM) mPSM->Release();
|
||||
}
|
||||
|
||||
/* Init the new instance */
|
||||
nsresult nsSecretDecoderRing::
|
||||
init()
|
||||
{
|
||||
nsresult rv;
|
||||
nsISupports *psm;
|
||||
|
||||
rv = nsServiceManager::GetService(kPSMComponentProgID, NS_GET_IID(nsIPSMComponent),
|
||||
&psm);
|
||||
if (rv != NS_OK) goto loser; /* Should promote error */
|
||||
|
||||
mPSM = (nsIPSMComponent *)psm;
|
||||
|
||||
loser:
|
||||
return rv;
|
||||
}
|
||||
|
||||
/* [noscript] long encrypt (in buffer data, in long dataLen, out buffer result); */
|
||||
NS_IMETHODIMP nsSecretDecoderRing::
|
||||
Encrypt(unsigned char * data, PRInt32 dataLen, unsigned char * *result, PRInt32 *_retval)
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
unsigned char *r = 0;
|
||||
CMT_CONTROL *control;
|
||||
CMTStatus status;
|
||||
CMUint32 cLen;
|
||||
|
||||
if (data == nsnull || result == nsnull || _retval == nsnull) {
|
||||
rv = NS_ERROR_INVALID_POINTER;
|
||||
goto loser;
|
||||
}
|
||||
|
||||
/* Check object initialization */
|
||||
NS_ASSERTION(mPSM != nsnull, "SDR object not initialized");
|
||||
if (mPSM == nsnull) { rv = NS_ERROR_NOT_INITIALIZED; goto loser; }
|
||||
|
||||
/* Get the control connect to use for the request */
|
||||
rv = mPSM->GetControlConnection(&control);
|
||||
if (rv != NS_OK) { rv = NS_ERROR_NOT_AVAILABLE; goto loser; }
|
||||
|
||||
status = CMT_SDREncrypt(control, (void *)0, (const unsigned char *)0, 0,
|
||||
data, dataLen, result, &cLen);
|
||||
if (status != CMTSuccess) { rv = NS_ERROR_FAILURE; goto loser; } /* XXX */
|
||||
|
||||
/* Copy returned data to nsMemory buffer ? */
|
||||
*_retval = cLen;
|
||||
|
||||
loser:
|
||||
return rv;
|
||||
}
|
||||
|
||||
/* [noscript] long decrypt (in buffer data, in long dataLen, out buffer result); */
|
||||
NS_IMETHODIMP nsSecretDecoderRing::
|
||||
Decrypt(unsigned char * data, PRInt32 dataLen, unsigned char * *result, PRInt32 *_retval)
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
CMTStatus status;
|
||||
CMT_CONTROL *control;
|
||||
CMUint32 len;
|
||||
|
||||
if (data == nsnull || result == nsnull || _retval == nsnull) {
|
||||
rv = NS_ERROR_INVALID_POINTER;
|
||||
goto loser;
|
||||
}
|
||||
|
||||
/* Check object initialization */
|
||||
NS_ASSERTION(mPSM != nsnull, "SDR object not initialized");
|
||||
if (mPSM == nsnull) { rv = NS_ERROR_NOT_INITIALIZED; goto loser; }
|
||||
|
||||
/* Get the control connection */
|
||||
rv = mPSM->GetControlConnection(&control);
|
||||
if (rv != NS_OK) { rv = NS_ERROR_NOT_AVAILABLE; goto loser; }
|
||||
|
||||
/* Call PSM to decrypt the value */
|
||||
status = CMT_SDRDecrypt(control, (void *)0, data, dataLen, result, &len);
|
||||
if (status != CMTSuccess) { rv = NS_ERROR_FAILURE; goto loser; } /* Promote? */
|
||||
|
||||
/* Copy returned data to nsMemory buffer ? */
|
||||
*_retval = len;
|
||||
|
||||
loser:
|
||||
return rv;
|
||||
}
|
||||
|
||||
/* string encryptString (in string text); */
|
||||
NS_IMETHODIMP nsSecretDecoderRing::
|
||||
EncryptString(const char *text, char **_retval)
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
unsigned char *encrypted = 0;
|
||||
PRInt32 eLen;
|
||||
|
||||
if (text == nsnull || _retval == nsnull) {
|
||||
rv = NS_ERROR_INVALID_POINTER;
|
||||
goto loser;
|
||||
}
|
||||
|
||||
rv = Encrypt((unsigned char *)text, PL_strlen(text), &encrypted, &eLen);
|
||||
if (rv != NS_OK) { goto loser; }
|
||||
|
||||
rv = encode(encrypted, eLen, _retval);
|
||||
|
||||
loser:
|
||||
if (encrypted) nsMemory::Free(encrypted);
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
/* string decryptString (in string crypt); */
|
||||
NS_IMETHODIMP nsSecretDecoderRing::
|
||||
DecryptString(const char *crypt, char **_retval)
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
char *r = 0;
|
||||
unsigned char *decoded = 0;
|
||||
PRInt32 decodedLen;
|
||||
unsigned char *decrypted = 0;
|
||||
PRInt32 decryptedLen;
|
||||
|
||||
if (crypt == nsnull || _retval == nsnull) {
|
||||
rv = NS_ERROR_INVALID_POINTER;
|
||||
goto loser;
|
||||
}
|
||||
|
||||
rv = decode(crypt, &decoded, &decodedLen);
|
||||
if (rv != NS_OK) goto loser;
|
||||
|
||||
rv = Decrypt(decoded, decodedLen, &decrypted, &decryptedLen);
|
||||
if (rv != NS_OK) goto loser;
|
||||
|
||||
// Convert to NUL-terminated string
|
||||
r = (char *)nsMemory::Alloc(decryptedLen+1);
|
||||
if (!r) { rv = NS_ERROR_OUT_OF_MEMORY; goto loser; }
|
||||
|
||||
memcpy(r, decrypted, decryptedLen);
|
||||
r[decryptedLen] = 0;
|
||||
|
||||
*_retval = r;
|
||||
r = 0;
|
||||
|
||||
loser:
|
||||
if (r) nsMemory::Free(r);
|
||||
if (decrypted) nsMemory::Free(decrypted);
|
||||
if (decoded) nsMemory::Free(decoded);
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
/* void changePassword(); */
|
||||
NS_IMETHODIMP nsSecretDecoderRing::
|
||||
ChangePassword()
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
CMTStatus status;
|
||||
CMT_CONTROL *control;
|
||||
|
||||
rv = mPSM->GetControlConnection(&control);
|
||||
if (rv != NS_OK) { rv = NS_ERROR_NOT_AVAILABLE; goto loser; }
|
||||
|
||||
status = CMT_SDRChangePassword(control, (void*)0);
|
||||
|
||||
loser:
|
||||
return rv;
|
||||
}
|
||||
|
||||
/* void logout(); */
|
||||
NS_IMETHODIMP nsSecretDecoderRing::
|
||||
Logout()
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
CMTStatus status;
|
||||
CMT_CONTROL *control;
|
||||
|
||||
/* Check object initialization */
|
||||
NS_ASSERTION(mPSM != nsnull, "SDR object not initialized");
|
||||
if (mPSM == nsnull) { rv = NS_ERROR_NOT_INITIALIZED; goto loser; }
|
||||
|
||||
/* Get the control connection */
|
||||
rv = mPSM->GetControlConnection(&control);
|
||||
if (rv != NS_OK) { rv = NS_ERROR_NOT_AVAILABLE; goto loser; }
|
||||
|
||||
/* Call PSM to decrypt the value */
|
||||
status = CMT_LogoutAllTokens(control);
|
||||
if (status != CMTSuccess) { rv = NS_ERROR_FAILURE; goto loser; } /* Promote? */
|
||||
|
||||
loser:
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
||||
// Support routines
|
||||
|
||||
nsresult nsSecretDecoderRing::
|
||||
encode(const unsigned char *data, PRInt32 dataLen, char **_retval)
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
|
||||
*_retval = PL_Base64Encode((const char *)data, dataLen, NULL);
|
||||
if (!*_retval) { rv = NS_ERROR_OUT_OF_MEMORY; goto loser; }
|
||||
|
||||
loser:
|
||||
return rv;
|
||||
|
||||
#if 0
|
||||
nsresult rv = NS_OK;
|
||||
char *r = 0;
|
||||
|
||||
// Allocate space for encoded string (with NUL)
|
||||
r = (char *)nsMemory::Alloc(dataLen+1);
|
||||
if (!r) { rv = NS_ERROR_OUT_OF_MEMORY; goto loser; }
|
||||
|
||||
memcpy(r, data, dataLen);
|
||||
r[dataLen] = 0;
|
||||
|
||||
*_retval = r;
|
||||
r = 0;
|
||||
|
||||
loser:
|
||||
if (r) nsMemory::Free(r);
|
||||
|
||||
return rv;
|
||||
#endif
|
||||
}
|
||||
|
||||
nsresult nsSecretDecoderRing::
|
||||
decode(const char *data, unsigned char **result, PRInt32 * _retval)
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
PRUint32 len = PL_strlen(data);
|
||||
int adjust = 0;
|
||||
|
||||
/* Compute length adjustment */
|
||||
if (data[len-1] == '=') {
|
||||
adjust++;
|
||||
if (data[len-2] == '=') adjust++;
|
||||
}
|
||||
|
||||
*result = (unsigned char *)PL_Base64Decode(data, len, NULL);
|
||||
if (!*result) { rv = NS_ERROR_ILLEGAL_VALUE; goto loser; }
|
||||
|
||||
*_retval = (len*3)/4 - adjust;
|
||||
|
||||
loser:
|
||||
return rv;
|
||||
|
||||
#if 0
|
||||
nsresult rv = NS_OK;
|
||||
unsigned char *r = 0;
|
||||
PRInt32 rLen;
|
||||
|
||||
// Allocate space for decoded string (missing NUL)
|
||||
rLen = PL_strlen(data);
|
||||
r = (unsigned char *)nsMemory::Alloc(rLen);
|
||||
if (!r) { rv = NS_ERROR_OUT_OF_MEMORY; goto loser; }
|
||||
|
||||
memcpy(r, data, rLen);
|
||||
|
||||
*result = r;
|
||||
r = 0;
|
||||
*_retval = rLen;
|
||||
|
||||
loser:
|
||||
if (r) nsMemory::Free(r);
|
||||
|
||||
return rv;
|
||||
#endif
|
||||
}
|
||||
|
||||
const char * nsSecretDecoderRing::kPSMComponentProgID = PSM_COMPONENT_PROGID;
|
||||
58
mozilla/extensions/psm-glue/src/nsSDR.h
Normal file
58
mozilla/extensions/psm-glue/src/nsSDR.h
Normal file
@@ -0,0 +1,58 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Terry Hayes <thayes@netscape.com>
|
||||
*/
|
||||
|
||||
#ifndef _NSSDR_H_
|
||||
#define _NSSDR_H_
|
||||
|
||||
#include "nsISecretDecoderRing.h"
|
||||
|
||||
// ===============================================
|
||||
// nsSecretDecoderRing - implementation of nsISecretDecoderRing
|
||||
// ===============================================
|
||||
|
||||
#define NS_SDR_CLASSNAME "Secret Decoder Ring"
|
||||
#define NS_SDR_CID \
|
||||
{ 0xd9a0341, 0xce7, 0x11d4, { 0x9f, 0xdd, 0x0, 0x0, 0x64, 0x65, 0x73, 0x74 } }
|
||||
#define NS_SDR_PROGID "netscape.security.sdr"
|
||||
|
||||
class nsSecretDecoderRing : public nsISecretDecoderRing
|
||||
{
|
||||
public:
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSISECRETDECODERRING
|
||||
|
||||
nsSecretDecoderRing();
|
||||
virtual ~nsSecretDecoderRing();
|
||||
|
||||
nsresult init();
|
||||
|
||||
private:
|
||||
nsIPSMComponent *mPSM;
|
||||
|
||||
static const char *kPSMComponentProgID;
|
||||
|
||||
nsresult encode(const unsigned char *data, PRInt32 dataLen, char **_retval);
|
||||
nsresult decode(const char *data, unsigned char **result, PRInt32 * _retval);
|
||||
};
|
||||
|
||||
#endif /* _NSSDR_H_ */
|
||||
550
mozilla/extensions/psm-glue/src/nsSSLIOLayer.cpp
Normal file
550
mozilla/extensions/psm-glue/src/nsSSLIOLayer.cpp
Normal file
@@ -0,0 +1,550 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*/
|
||||
|
||||
#include "nspr.h"
|
||||
#include "nsString.h"
|
||||
#include "cmtcmn.h"
|
||||
|
||||
#include "nsIPSMComponent.h"
|
||||
#include "nsIPSMSocketInfo.h"
|
||||
#include "nsIServiceManager.h"
|
||||
#include "nsPSMShimLayer.h"
|
||||
#include "nsSSLIOLayer.h"
|
||||
|
||||
static PRDescIdentity nsSSLIOLayerIdentity;
|
||||
static PRIOMethods nsSSLIOLayerMethods;
|
||||
static nsIPSMComponent* gPSMService = nsnull;
|
||||
|
||||
|
||||
|
||||
class nsPSMSocketInfo : public nsIPSMSocketInfo
|
||||
{
|
||||
public:
|
||||
nsPSMSocketInfo();
|
||||
virtual ~nsPSMSocketInfo();
|
||||
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSIPSMSOCKETINFO
|
||||
|
||||
// internal functions to psm-glue.
|
||||
nsresult SetSocketPtr(CMSocket *socketPtr);
|
||||
nsresult SetControlPtr(CMT_CONTROL *aControlPtr);
|
||||
nsresult SetFileDescPtr(PRFileDesc *aControlPtr);
|
||||
nsresult SetHostName(char *aHostName);
|
||||
nsresult SetProxyName(char *aName);
|
||||
|
||||
nsresult SetHostPort(PRInt32 aPort);
|
||||
nsresult SetProxyPort(PRInt32 aPort);
|
||||
nsresult SetPickledStatus();
|
||||
|
||||
protected:
|
||||
CMT_CONTROL* mControl;
|
||||
CMSocket* mSocket;
|
||||
PRFileDesc* mFd;
|
||||
|
||||
nsString mHostName;
|
||||
PRInt32 mHostPort;
|
||||
|
||||
nsString mProxyName;
|
||||
PRInt32 mProxyPort;
|
||||
|
||||
unsigned char* mPickledStatus;
|
||||
};
|
||||
|
||||
|
||||
static PRStatus PR_CALLBACK
|
||||
nsSSLIOLayerConnect(PRFileDesc *fd, const PRNetAddr *addr, PRIntervalTime timeout)
|
||||
{
|
||||
nsresult result;
|
||||
PRStatus rv = PR_SUCCESS;
|
||||
CMTStatus status = CMTFailure;
|
||||
|
||||
/* Set the error in case of failure. */
|
||||
|
||||
PR_SetError(PR_UNKNOWN_ERROR, status);
|
||||
|
||||
if (!fd || !addr || !fd->secret || !gPSMService)
|
||||
return PR_FAILURE;
|
||||
|
||||
char ipBuffer[PR_NETDB_BUF_SIZE];
|
||||
rv = PR_NetAddrToString(addr, (char*)&ipBuffer, PR_NETDB_BUF_SIZE);
|
||||
if (rv != PR_SUCCESS)
|
||||
return PR_FAILURE;
|
||||
|
||||
if (addr->raw.family == PR_AF_INET6 && PR_IsNetAddrType(addr, PR_IpAddrV4Mapped))
|
||||
{
|
||||
/* Chop off the leading "::ffff:" */
|
||||
strcpy(ipBuffer, ipBuffer + 7);
|
||||
}
|
||||
|
||||
|
||||
CMT_CONTROL *control;
|
||||
result = gPSMService->GetControlConnection(&control);
|
||||
if (result != PR_SUCCESS)
|
||||
return PR_FAILURE;
|
||||
|
||||
CMSocket* cmsock = (CMSocket *)PR_Malloc(sizeof(CMSocket));
|
||||
if (!cmsock)
|
||||
return PR_FAILURE;
|
||||
|
||||
memset(cmsock, 0, sizeof(CMSocket));
|
||||
|
||||
cmsock->fd = fd->lower;
|
||||
cmsock->isUnix = PR_FALSE;
|
||||
|
||||
nsPSMSocketInfo *infoObject = (nsPSMSocketInfo *)fd->secret;
|
||||
|
||||
infoObject->SetControlPtr(control);
|
||||
infoObject->SetSocketPtr(cmsock);
|
||||
|
||||
char* proxyName;
|
||||
char* hostName;
|
||||
infoObject->GetProxyName(&proxyName);
|
||||
infoObject->GetHostName(&hostName);
|
||||
|
||||
if (!proxyName)
|
||||
{
|
||||
// Direct connection
|
||||
status = CMT_OpenSSLConnection(control,
|
||||
cmsock,
|
||||
SSM_REQUEST_SSL_DATA_SSL,
|
||||
PR_ntohs(addr->inet.port),
|
||||
ipBuffer,
|
||||
(hostName ? hostName : ipBuffer),
|
||||
CM_FALSE,
|
||||
nsnull);
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
// not supported yet.
|
||||
|
||||
return PR_FAILURE;
|
||||
#if 0
|
||||
PRInt32 destPort;
|
||||
|
||||
infoObject->GetProxyPort(&destPort);
|
||||
|
||||
status = CMT_OpenSSLProxyConnection(control,
|
||||
cmsock,
|
||||
destPort,
|
||||
proxyName, // wants IP
|
||||
hostName);
|
||||
#endif
|
||||
}
|
||||
|
||||
if (hostName) Recycle(hostName);
|
||||
if (proxyName) Recycle(proxyName);
|
||||
|
||||
if (CMTSuccess == status)
|
||||
{
|
||||
// since our stuff can block, what we want to do is return PR_FAILURE,
|
||||
// but set the nspr ERROR to BLOCK. This will put us into a select
|
||||
// q.
|
||||
PR_SetError(PR_WOULD_BLOCK_ERROR, status);
|
||||
return PR_FAILURE;
|
||||
}
|
||||
|
||||
return PR_FAILURE;
|
||||
}
|
||||
|
||||
/* CMT_DestroyDataConnection(ctrl, sock); */
|
||||
/* need to strip our layer, pass result to DestroyDataConnection */
|
||||
/* which will clean up the CMT accounting of sock, then call our */
|
||||
/* shim layer to translate back to NSPR */
|
||||
|
||||
static PRStatus PR_CALLBACK
|
||||
nsSSLIOLayerClose(PRFileDesc *fd)
|
||||
{
|
||||
nsPSMSocketInfo *infoObject = (nsPSMSocketInfo *)fd->secret;
|
||||
PRDescIdentity id = PR_GetLayersIdentity(fd);
|
||||
|
||||
if (infoObject && id == nsSSLIOLayerIdentity)
|
||||
{
|
||||
CMInt32 errorCode = PR_FAILURE;
|
||||
CMT_CONTROL* control;
|
||||
CMSocket* socket;
|
||||
|
||||
PR_Shutdown(fd, PR_SHUTDOWN_BOTH);
|
||||
|
||||
infoObject->GetControlPtr(&control);
|
||||
infoObject->GetSocketPtr(&socket);
|
||||
infoObject->SetPickledStatus();
|
||||
|
||||
CMT_GetSSLDataErrorCode(control, socket, &errorCode);
|
||||
CMT_DestroyDataConnection(control, socket);
|
||||
NS_RELEASE(infoObject); // if someone is interested in us, the better have an addref.
|
||||
fd->identity = PR_INVALID_IO_LAYER;
|
||||
|
||||
return (PRStatus)errorCode;
|
||||
}
|
||||
|
||||
return PR_FAILURE;
|
||||
}
|
||||
|
||||
static PRInt32 PR_CALLBACK
|
||||
nsSSLIOLayerRead( PRFileDesc *fd, void *buf, PRInt32 amount)
|
||||
{
|
||||
if (!fd)
|
||||
return PR_FAILURE;
|
||||
|
||||
PRInt32 result = PR_Recv(fd, buf, amount, 0, PR_INTERVAL_MIN);
|
||||
|
||||
if (result > 0)
|
||||
return result;
|
||||
|
||||
if (result == -1)
|
||||
{
|
||||
PRErrorCode code = PR_GetError();
|
||||
|
||||
if (code == PR_IO_TIMEOUT_ERROR )
|
||||
PR_SetError(PR_WOULD_BLOCK_ERROR, PR_WOULD_BLOCK_ERROR);
|
||||
return PR_FAILURE;
|
||||
}
|
||||
|
||||
if (result == 0)
|
||||
{
|
||||
nsPSMSocketInfo *infoObject = (nsPSMSocketInfo *)fd->secret;
|
||||
PRDescIdentity id = PR_GetLayersIdentity(fd);
|
||||
|
||||
if (infoObject && id == nsSSLIOLayerIdentity)
|
||||
{
|
||||
CMInt32 errorCode = PR_FAILURE;
|
||||
|
||||
CMT_CONTROL* control;
|
||||
CMSocket* socket;
|
||||
|
||||
infoObject->GetControlPtr(&control);
|
||||
infoObject->GetSocketPtr(&socket);
|
||||
|
||||
CMT_GetSSLDataErrorCode(control, socket, &errorCode);
|
||||
|
||||
if (errorCode == PR_IO_TIMEOUT_ERROR)
|
||||
{
|
||||
PR_SetError(PR_WOULD_BLOCK_ERROR, PR_WOULD_BLOCK_ERROR);
|
||||
return PR_FAILURE;
|
||||
}
|
||||
|
||||
PR_SetError(0, 0);
|
||||
return errorCode;
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
static PRInt32 PR_CALLBACK
|
||||
nsSSLIOLayerWrite( PRFileDesc *fd, const void *buf, PRInt32 amount)
|
||||
{
|
||||
if (!fd)
|
||||
return PR_FAILURE;
|
||||
|
||||
PRInt32 result = PR_Send(fd, buf, amount, 0, PR_INTERVAL_MIN);
|
||||
|
||||
if (result > 0)
|
||||
return result;
|
||||
|
||||
if (result == -1)
|
||||
{
|
||||
PRErrorCode code = PR_GetError();
|
||||
|
||||
if (code == PR_IO_TIMEOUT_ERROR )
|
||||
PR_SetError(PR_WOULD_BLOCK_ERROR, PR_WOULD_BLOCK_ERROR);
|
||||
return PR_FAILURE;
|
||||
}
|
||||
|
||||
if (result == 0)
|
||||
{
|
||||
nsPSMSocketInfo *infoObject = (nsPSMSocketInfo *)fd->secret;
|
||||
PRDescIdentity id = PR_GetLayersIdentity(fd);
|
||||
|
||||
if (infoObject && id == nsSSLIOLayerIdentity)
|
||||
{
|
||||
CMInt32 errorCode = PR_FAILURE;
|
||||
CMT_CONTROL* control;
|
||||
CMSocket* socket;
|
||||
|
||||
infoObject->GetControlPtr(&control);
|
||||
infoObject->GetSocketPtr(&socket);
|
||||
|
||||
CMT_GetSSLDataErrorCode(control, socket, &errorCode);
|
||||
PR_SetError(0, 0);
|
||||
return errorCode;
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
|
||||
nsPSMSocketInfo::nsPSMSocketInfo()
|
||||
{
|
||||
NS_INIT_REFCNT();
|
||||
mControl = nsnull;
|
||||
mSocket = nsnull;
|
||||
mPickledStatus = nsnull;
|
||||
}
|
||||
|
||||
nsPSMSocketInfo::~nsPSMSocketInfo()
|
||||
{
|
||||
PR_FREEIF(mPickledStatus);
|
||||
}
|
||||
|
||||
NS_IMPL_THREADSAFE_ISUPPORTS1(nsPSMSocketInfo, nsIPSMSocketInfo);
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMSocketInfo::GetControlPtr(CMT_CONTROL * *aControlPtr)
|
||||
{
|
||||
*aControlPtr = mControl;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsPSMSocketInfo::SetControlPtr(CMT_CONTROL *aControlPtr)
|
||||
{
|
||||
mControl = aControlPtr;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMSocketInfo::GetSocketPtr(CMSocket * *socketPtr)
|
||||
{
|
||||
*socketPtr = mSocket;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsPSMSocketInfo::SetSocketPtr(CMSocket *socketPtr)
|
||||
{
|
||||
mSocket = socketPtr;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMSocketInfo::GetFileDescPtr(PRFileDesc * *aFilePtr)
|
||||
{
|
||||
*aFilePtr = mFd;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
nsresult
|
||||
nsPSMSocketInfo::SetFileDescPtr(PRFileDesc *aFilePtr)
|
||||
{
|
||||
mFd = aFilePtr;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMSocketInfo::GetHostName(char * *aHostName)
|
||||
{
|
||||
if (mHostName.IsEmpty())
|
||||
*aHostName = nsnull;
|
||||
else
|
||||
*aHostName = mHostName.ToNewCString();
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
nsresult
|
||||
nsPSMSocketInfo::SetHostName(char *aHostName)
|
||||
{
|
||||
mHostName.AssignWithConversion(aHostName);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMSocketInfo::GetHostPort(PRInt32 *aPort)
|
||||
{
|
||||
*aPort = mHostPort;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsPSMSocketInfo::SetHostPort(PRInt32 aPort)
|
||||
{
|
||||
mHostPort = aPort;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMSocketInfo::GetProxyName(char * *aName)
|
||||
{
|
||||
if (mProxyName.IsEmpty())
|
||||
*aName = nsnull;
|
||||
else
|
||||
*aName = mProxyName.ToNewCString();
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
nsresult
|
||||
nsPSMSocketInfo::SetProxyName(char *aName)
|
||||
{
|
||||
mProxyName.AssignWithConversion(aName);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMSocketInfo::GetProxyPort(PRInt32 *aPort)
|
||||
{
|
||||
*aPort = mProxyPort;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsPSMSocketInfo::SetProxyPort(PRInt32 aPort)
|
||||
{
|
||||
mProxyPort = aPort;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
|
||||
nsresult
|
||||
nsPSMSocketInfo::SetPickledStatus()
|
||||
{
|
||||
PR_FREEIF(mPickledStatus);
|
||||
|
||||
long level;
|
||||
CMTItem pickledStatus = {0, nsnull, 0};
|
||||
unsigned char* ret = nsnull;
|
||||
|
||||
if (CMT_GetSSLSocketStatus(mControl, mSocket, &pickledStatus, &level) != PR_FAILURE)
|
||||
{
|
||||
ret = (unsigned char*) PR_Malloc( (SSMSTRING_PADDED_LENGTH(pickledStatus.len) + sizeof(int)) );
|
||||
if (ret)
|
||||
{
|
||||
*(int*)ret = pickledStatus.len;
|
||||
memcpy(ret+sizeof(int), pickledStatus.data, *(int*)ret);
|
||||
}
|
||||
|
||||
PR_FREEIF(pickledStatus.data);
|
||||
mPickledStatus = ret;
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsPSMSocketInfo::GetPickledStatus(char * *pickledStatusString)
|
||||
{
|
||||
if (!mPickledStatus)
|
||||
SetPickledStatus();
|
||||
|
||||
if (mPickledStatus)
|
||||
{
|
||||
PRInt32 len = *(int*)mPickledStatus;
|
||||
char *out = (char *)nsMemory::Alloc(len);
|
||||
memcpy(out, mPickledStatus, len);
|
||||
*pickledStatusString = out;
|
||||
return NS_OK;
|
||||
}
|
||||
*pickledStatusString = nsnull;
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsSSLIOLayerNewSocket( const char *host,
|
||||
PRInt32 port,
|
||||
const char *proxyHost,
|
||||
PRInt32 proxyPort,
|
||||
PRFileDesc **fd,
|
||||
nsISupports** info)
|
||||
{
|
||||
static PRBool firstTime = PR_TRUE;
|
||||
if (firstTime)
|
||||
{
|
||||
nsSSLIOLayerIdentity = PR_GetUniqueIdentity("Cartman layer");
|
||||
nsSSLIOLayerMethods = *PR_GetDefaultIOMethods();
|
||||
|
||||
nsSSLIOLayerMethods.connect = nsSSLIOLayerConnect;
|
||||
nsSSLIOLayerMethods.close = nsSSLIOLayerClose;
|
||||
nsSSLIOLayerMethods.read = nsSSLIOLayerRead;
|
||||
nsSSLIOLayerMethods.write = nsSSLIOLayerWrite;
|
||||
|
||||
|
||||
nsresult result = nsServiceManager::GetService( PSM_COMPONENT_PROGID,
|
||||
NS_GET_IID(nsIPSMComponent),
|
||||
(nsISupports**)&gPSMService);
|
||||
if (NS_FAILED(result))
|
||||
return PR_FAILURE;
|
||||
|
||||
firstTime = PR_FALSE;
|
||||
|
||||
}
|
||||
|
||||
|
||||
PRFileDesc * sock;
|
||||
PRFileDesc * layer;
|
||||
PRStatus rv;
|
||||
|
||||
/* Get a normal NSPR socket */
|
||||
sock = PR_NewTCPSocket();
|
||||
if (! sock) return NS_ERROR_OUT_OF_MEMORY;
|
||||
|
||||
/* disable Nagle algorithm delay for control sockets */
|
||||
PRSocketOptionData sockopt;
|
||||
sockopt.option = PR_SockOpt_NoDelay;
|
||||
sockopt.value.no_delay = PR_TRUE;
|
||||
rv = PR_SetSocketOption(sock, &sockopt);
|
||||
PR_ASSERT(PR_SUCCESS == rv);
|
||||
|
||||
|
||||
layer = PR_CreateIOLayerStub(nsSSLIOLayerIdentity, &nsSSLIOLayerMethods);
|
||||
if (! layer)
|
||||
{
|
||||
PR_Close(sock);
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
nsPSMSocketInfo *infoObject = new nsPSMSocketInfo();
|
||||
if (!infoObject)
|
||||
{
|
||||
PR_Close(sock);
|
||||
// clean up IOLayerStub.
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
NS_ADDREF(infoObject);
|
||||
|
||||
infoObject->SetHostName((char*)host);
|
||||
infoObject->SetHostPort(port);
|
||||
infoObject->SetProxyName((char*)proxyHost);
|
||||
infoObject->SetProxyPort(proxyPort);
|
||||
|
||||
layer->secret = (PRFilePrivate*) infoObject;
|
||||
rv = PR_PushIOLayer(sock, PR_GetLayersIdentity(sock), layer);
|
||||
|
||||
if (rv == PR_SUCCESS)
|
||||
{
|
||||
*fd = sock;
|
||||
*info = infoObject;
|
||||
NS_ADDREF(*info);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
PR_Close(sock);
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
39
mozilla/extensions/psm-glue/src/nsSSLIOLayer.h
Normal file
39
mozilla/extensions/psm-glue/src/nsSSLIOLayer.h
Normal file
@@ -0,0 +1,39 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*/
|
||||
|
||||
#ifndef _NSSSLIOLAYER_H
|
||||
#define _NSSSLIOLAYER_H
|
||||
|
||||
#include "prtypes.h"
|
||||
#include "prio.h"
|
||||
#include "nsIPSMSocketInfo.h"
|
||||
|
||||
// define taken from 4.x cartman glue code.
|
||||
#define SSMSTRING_PADDED_LENGTH(x) ((((x)+3)/4)*4)
|
||||
|
||||
nsresult nsSSLIOLayerNewSocket(const char *host,
|
||||
PRInt32 port,
|
||||
const char *proxyHost,
|
||||
PRInt32 proxyPort,
|
||||
PRFileDesc **fd,
|
||||
nsISupports **securityInfo);
|
||||
#endif /* _NSSSLIOLAYER_H */
|
||||
94
mozilla/extensions/psm-glue/src/nsSSLSocketProvider.cpp
Normal file
94
mozilla/extensions/psm-glue/src/nsSSLSocketProvider.cpp
Normal file
@@ -0,0 +1,94 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*/
|
||||
|
||||
#include "nsIComponentManager.h"
|
||||
#include "nsIServiceManager.h"
|
||||
#include "nsSSLSocketProvider.h"
|
||||
#include "nsSSLIOLayer.h"
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
nsSSLSocketProvider::nsSSLSocketProvider()
|
||||
{
|
||||
NS_INIT_REFCNT();
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsSSLSocketProvider::Init()
|
||||
{
|
||||
nsresult rv = NS_OK;
|
||||
return rv;
|
||||
}
|
||||
|
||||
nsSSLSocketProvider::~nsSSLSocketProvider()
|
||||
{
|
||||
}
|
||||
|
||||
NS_IMPL_THREADSAFE_ISUPPORTS2(nsSSLSocketProvider, nsISocketProvider, nsISSLSocketProvider);
|
||||
|
||||
NS_METHOD
|
||||
nsSSLSocketProvider::Create(nsISupports *aOuter, REFNSIID aIID, void **aResult)
|
||||
{
|
||||
nsresult rv;
|
||||
|
||||
nsSSLSocketProvider * inst;
|
||||
|
||||
if (NULL == aResult) {
|
||||
rv = NS_ERROR_NULL_POINTER;
|
||||
return rv;
|
||||
}
|
||||
*aResult = NULL;
|
||||
if (NULL != aOuter) {
|
||||
rv = NS_ERROR_NO_AGGREGATION;
|
||||
return rv;
|
||||
}
|
||||
|
||||
NS_NEWXPCOM(inst, nsSSLSocketProvider);
|
||||
if (NULL == inst) {
|
||||
rv = NS_ERROR_OUT_OF_MEMORY;
|
||||
return rv;
|
||||
}
|
||||
NS_ADDREF(inst);
|
||||
rv = inst->QueryInterface(aIID, aResult);
|
||||
NS_RELEASE(inst);
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsSSLSocketProvider::NewSocket(const char *host,
|
||||
PRInt32 port,
|
||||
const char *proxyHost,
|
||||
PRInt32 proxyPort,
|
||||
PRFileDesc **_result,
|
||||
nsISupports **securityInfo)
|
||||
{
|
||||
nsresult rv = nsSSLIOLayerNewSocket(host,
|
||||
port,
|
||||
proxyHost,
|
||||
proxyPort,
|
||||
_result,
|
||||
securityInfo);
|
||||
|
||||
return (NS_FAILED(rv)) ? NS_ERROR_SOCKET_CREATE_FAILED : NS_OK;
|
||||
}
|
||||
54
mozilla/extensions/psm-glue/src/nsSSLSocketProvider.h
Normal file
54
mozilla/extensions/psm-glue/src/nsSSLSocketProvider.h
Normal file
@@ -0,0 +1,54 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*/
|
||||
|
||||
#ifndef _NSSSLSOCKETPROVIDER_H_
|
||||
#define _NSSSLSOCKETPROVIDER_H_
|
||||
|
||||
#include "nsISSLSocketProvider.h"
|
||||
|
||||
|
||||
/* 274418d0-5437-11d3-bbc8-0000861d1237 */
|
||||
#define NS_SSLSOCKETPROVIDER_CID { 0x274418d0, 0x5437, 0x11d3, {0xbb, 0xc8, 0x00, 0x00, 0x86, 0x1d, 0x12, 0x37}}
|
||||
|
||||
|
||||
class nsSSLSocketProvider : public nsISSLSocketProvider
|
||||
{
|
||||
public:
|
||||
NS_DECL_ISUPPORTS
|
||||
|
||||
NS_DECL_NSISOCKETPROVIDER
|
||||
|
||||
NS_DECL_NSISSLSOCKETPROVIDER
|
||||
|
||||
// nsSSLSocketProvider methods:
|
||||
nsSSLSocketProvider();
|
||||
virtual ~nsSSLSocketProvider();
|
||||
|
||||
static NS_METHOD
|
||||
Create(nsISupports *aOuter, REFNSIID aIID, void **aResult);
|
||||
|
||||
nsresult Init();
|
||||
|
||||
protected:
|
||||
};
|
||||
|
||||
#endif /* _NSSSLSOCKETPROVIDER_H_ */
|
||||
654
mozilla/extensions/psm-glue/src/nsSecureBrowserUIImpl.cpp
Normal file
654
mozilla/extensions/psm-glue/src/nsSecureBrowserUIImpl.cpp
Normal file
@@ -0,0 +1,654 @@
|
||||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998-2000 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
* Stuart Parmenter <pavlov@netscape.com>
|
||||
*/
|
||||
|
||||
#include "nspr.h"
|
||||
#include "prlog.h"
|
||||
|
||||
#include "nsISecureBrowserUI.h"
|
||||
#include "nsSecureBrowserUIImpl.h"
|
||||
#include "nsIPSMComponent.h"
|
||||
#include "nsPSMComponent.h"
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsIInterfaceRequestor.h"
|
||||
#include "nsIServiceManager.h"
|
||||
|
||||
#include "nsIScriptGlobalObject.h"
|
||||
#include "nsIObserverService.h"
|
||||
#include "nsIDocumentLoader.h"
|
||||
#include "nsCURILoader.h"
|
||||
#include "nsIDocShell.h"
|
||||
#include "nsIDocumentViewer.h"
|
||||
#include "nsCURILoader.h"
|
||||
#include "nsIDocument.h"
|
||||
#include "nsIDOMHTMLDocument.h"
|
||||
#include "nsIDOMXULDocument.h"
|
||||
#include "nsIDOMElement.h"
|
||||
#include "nsIDOMWindow.h"
|
||||
#include "nsIContent.h"
|
||||
#include "nsIWebProgress.h"
|
||||
#include "nsIChannel.h"
|
||||
#include "nsIPSMSocketInfo.h"
|
||||
|
||||
#include "nsIURI.h"
|
||||
|
||||
#include "prmem.h"
|
||||
|
||||
#include "nsINetSupportDialogService.h"
|
||||
#include "nsIPrompt.h"
|
||||
#include "nsICommonDialogs.h"
|
||||
#include "nsIPref.h"
|
||||
|
||||
#include "nsIFormSubmitObserver.h"
|
||||
|
||||
static NS_DEFINE_CID(kCStringBundleServiceCID, NS_STRINGBUNDLESERVICE_CID);
|
||||
static NS_DEFINE_CID(kCommonDialogsCID, NS_CommonDialog_CID );
|
||||
static NS_DEFINE_CID(kPrefCID, NS_PREF_CID);
|
||||
|
||||
#define ENTER_SITE_PREF "security.warn_entering_secure"
|
||||
#define LEAVE_SITE_PREF "security.warn_leaving_secure"
|
||||
#define MIXEDCONTENT_PREF "security.warn_viewing_mixed"
|
||||
#define INSECURE_SUBMIT_PREF "security.warn_submit_insecure"
|
||||
|
||||
#if defined(PR_LOGGING)
|
||||
//
|
||||
// Log module for nsSecureBroswerUI logging...
|
||||
//
|
||||
// To enable logging (see prlog.h for full details):
|
||||
//
|
||||
// set NSPR_LOG_MODULES=nsSecureBroswerUI:5
|
||||
// set NSPR_LOG_FILE=nspr.log
|
||||
//
|
||||
// this enables PR_LOG_DEBUG level information and places all output in
|
||||
// the file nspr.log
|
||||
//
|
||||
PRLogModuleInfo* gSecureDocLog = nsnull;
|
||||
#endif /* PR_LOGGING */
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsSecureBrowserUIImpl::Create(nsISupports *aOuter, REFNSIID aIID, void **aResult)
|
||||
{
|
||||
nsresult rv;
|
||||
|
||||
nsSecureBrowserUIImpl * inst;
|
||||
|
||||
if (NULL == aResult) {
|
||||
rv = NS_ERROR_NULL_POINTER;
|
||||
return rv;
|
||||
}
|
||||
*aResult = NULL;
|
||||
if (NULL != aOuter) {
|
||||
rv = NS_ERROR_NO_AGGREGATION;
|
||||
return rv;
|
||||
}
|
||||
|
||||
NS_NEWXPCOM(inst, nsSecureBrowserUIImpl);
|
||||
if (NULL == inst) {
|
||||
rv = NS_ERROR_OUT_OF_MEMORY;
|
||||
return rv;
|
||||
}
|
||||
NS_ADDREF(inst);
|
||||
rv = inst->QueryInterface(aIID, aResult);
|
||||
NS_RELEASE(inst);
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
nsSecureBrowserUIImpl::nsSecureBrowserUIImpl()
|
||||
{
|
||||
NS_INIT_REFCNT();
|
||||
|
||||
#if defined(PR_LOGGING)
|
||||
if (nsnull == gSecureDocLog) {
|
||||
gSecureDocLog = PR_NewLogModule("nsSecureBroswerUI");
|
||||
}
|
||||
#endif /* PR_LOGGING */
|
||||
|
||||
|
||||
mIsSecureDocument = mMixContentAlertShown = mIsDocumentBroken = PR_FALSE;
|
||||
mLastPSMStatus = nsnull;
|
||||
mCurrentURI = nsnull;
|
||||
mSecurityButton = nsnull;
|
||||
}
|
||||
|
||||
nsSecureBrowserUIImpl::~nsSecureBrowserUIImpl()
|
||||
{
|
||||
PR_FREEIF(mLastPSMStatus);
|
||||
}
|
||||
|
||||
NS_IMPL_ISUPPORTS4(nsSecureBrowserUIImpl,
|
||||
nsSecureBrowserUI,
|
||||
nsIWebProgressListener,
|
||||
nsIFormSubmitObserver,
|
||||
nsIObserver);
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsSecureBrowserUIImpl::Init(nsIDOMWindow *window, nsIDOMElement *button)
|
||||
{
|
||||
mSecurityButton = button;
|
||||
mWindow = window;
|
||||
|
||||
nsresult rv = nsServiceManager::GetService( kPrefCID,
|
||||
NS_GET_IID(nsIPref),
|
||||
getter_AddRefs(mPref));
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
NS_WITH_SERVICE(nsIStringBundleService, service, kCStringBundleServiceCID, &rv);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
nsILocale* locale = nsnull;
|
||||
rv = service->CreateBundle(SECURITY_STRING_BUNDLE_URL, locale, getter_AddRefs(mStringBundle));
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
// hook up to the form post notifications:
|
||||
nsIObserverService *svc = 0;
|
||||
rv = nsServiceManager::GetService(NS_OBSERVERSERVICE_PROGID,
|
||||
NS_GET_IID(nsIObserverService),
|
||||
(nsISupports**)&svc );
|
||||
if (NS_SUCCEEDED(rv) && svc) {
|
||||
nsString topic; topic.AssignWithConversion(NS_FORMSUBMIT_SUBJECT);
|
||||
rv = svc->AddObserver( this, topic.GetUnicode());
|
||||
nsServiceManager::ReleaseService( NS_OBSERVERSERVICE_PROGID, svc );
|
||||
}
|
||||
|
||||
// hook up to the webprogress notifications.
|
||||
nsCOMPtr<nsIDocShell> docShell;
|
||||
|
||||
nsCOMPtr<nsIScriptGlobalObject> sgo = do_QueryInterface(window);
|
||||
if (!sgo) return NS_ERROR_NULL_POINTER;
|
||||
|
||||
sgo->GetDocShell(getter_AddRefs(docShell));
|
||||
if (!docShell) return NS_ERROR_NULL_POINTER;
|
||||
|
||||
nsCOMPtr<nsIWebProgress> wp = do_GetInterface(docShell);
|
||||
if (!wp) return NS_ERROR_NULL_POINTER;
|
||||
|
||||
wp->AddProgressListener(NS_STATIC_CAST(nsIWebProgressListener*,this));
|
||||
|
||||
mInitByLocationChange = PR_TRUE;
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsSecureBrowserUIImpl::DisplayPageInfoUI()
|
||||
{
|
||||
nsresult res;
|
||||
NS_WITH_SERVICE(nsIPSMComponent, psm, PSM_COMPONENT_PROGID, &res);
|
||||
if (NS_FAILED(res))
|
||||
return res;
|
||||
|
||||
nsXPIDLCString host;
|
||||
if (mCurrentURI)
|
||||
mCurrentURI->GetHost(getter_Copies(host));
|
||||
|
||||
return psm->DisplaySecurityAdvisor(mLastPSMStatus, host);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsSecureBrowserUIImpl::Observe(nsISupports*, const PRUnichar*, const PRUnichar*)
|
||||
{
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
|
||||
static nsresult IsChildOfDomWindow(nsIDOMWindow *parent, nsIDOMWindow *child, PRBool* value)
|
||||
{
|
||||
*value = PR_FALSE;
|
||||
|
||||
if (parent == child)
|
||||
{
|
||||
*value = PR_TRUE;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIDOMWindow> childsParent;
|
||||
child->GetParent(getter_AddRefs(childsParent));
|
||||
|
||||
if (childsParent && childsParent.get() != child)
|
||||
IsChildOfDomWindow(parent, childsParent, value);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsSecureBrowserUIImpl::Notify(nsIContent* formNode, nsIDOMWindow* window, nsIURI* actionURL)
|
||||
{
|
||||
// Return NS_OK unless we want to prevent this form from submitting.
|
||||
|
||||
if (!window || !actionURL || !formNode) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIDocument> document;
|
||||
formNode->GetDocument(*getter_AddRefs(document));
|
||||
if (!document) return NS_OK;
|
||||
|
||||
nsCOMPtr<nsIScriptGlobalObject> globalObject;
|
||||
document->GetScriptGlobalObject(getter_AddRefs(globalObject));
|
||||
nsCOMPtr<nsIDOMWindow> postingWindow = do_QueryInterface(globalObject);
|
||||
|
||||
PRBool isChild;
|
||||
IsChildOfDomWindow(mWindow, postingWindow, &isChild);
|
||||
|
||||
if (!isChild)
|
||||
return NS_OK;
|
||||
|
||||
PRBool okayToPost;
|
||||
nsresult res = CheckPost(actionURL, &okayToPost);
|
||||
|
||||
if (NS_SUCCEEDED(res) && okayToPost)
|
||||
return NS_OK;
|
||||
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
// nsIWebProgressListener
|
||||
NS_IMETHODIMP
|
||||
nsSecureBrowserUIImpl::OnProgressChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
PRInt32 aCurSelfProgress,
|
||||
PRInt32 aMaxSelfProgress,
|
||||
PRInt32 aCurTotalProgress,
|
||||
PRInt32 aMaxTotalProgress)
|
||||
{
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsSecureBrowserUIImpl::OnStateChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
PRInt32 aProgressStateFlags,
|
||||
nsresult aStatus)
|
||||
{
|
||||
nsresult res = NS_OK;
|
||||
|
||||
if (aRequest == nsnull || !mSecurityButton || !mPref)
|
||||
return NS_ERROR_NULL_POINTER;
|
||||
|
||||
// Get the channel from the request...
|
||||
// If the request is not network based, then ignore it.
|
||||
nsCOMPtr<nsIChannel> channel;
|
||||
channel = do_QueryInterface(aRequest, &res);
|
||||
if (NS_FAILED(res))
|
||||
return NS_OK;
|
||||
|
||||
nsCOMPtr<nsIURI> loadingURI;
|
||||
channel->GetURI(getter_AddRefs(loadingURI));
|
||||
|
||||
#if defined(DEBUG)
|
||||
nsXPIDLCString temp;
|
||||
loadingURI->GetSpec(getter_Copies(temp));
|
||||
PR_LOG(gSecureDocLog, PR_LOG_DEBUG, ("SecureUI:%p: OnStateChange: %x :%s\n", this, aProgressStateFlags,(const char*)temp));
|
||||
#endif
|
||||
|
||||
// A Document is starting to load...
|
||||
if ((aProgressStateFlags & flag_start) &&
|
||||
(aProgressStateFlags & flag_is_network))
|
||||
{
|
||||
// starting to load a webpage
|
||||
PR_FREEIF(mLastPSMStatus); mLastPSMStatus = nsnull;
|
||||
|
||||
mIsSecureDocument = mMixContentAlertShown = mIsDocumentBroken = PR_FALSE;
|
||||
|
||||
res = CheckProtocolContextSwitch( loadingURI, mCurrentURI);
|
||||
return res;
|
||||
}
|
||||
|
||||
// A document has finished loading
|
||||
if ((aProgressStateFlags & flag_stop) &&
|
||||
(aProgressStateFlags & flag_is_network) &&
|
||||
mIsSecureDocument)
|
||||
{
|
||||
if (!mIsDocumentBroken) // and status is okay FIX
|
||||
{
|
||||
// qi for the psm information about this channel load.
|
||||
nsCOMPtr<nsISupports> info;
|
||||
channel->GetSecurityInfo(getter_AddRefs(info));
|
||||
nsCOMPtr<nsIPSMSocketInfo> psmInfo = do_QueryInterface(info);
|
||||
if (psmInfo)
|
||||
{
|
||||
// Everything looks okay. Lets stash the picked status.
|
||||
PR_FREEIF(mLastPSMStatus);
|
||||
res = psmInfo->GetPickledStatus(&mLastPSMStatus);
|
||||
|
||||
if (NS_SUCCEEDED(res)) {
|
||||
PR_LOG(gSecureDocLog, PR_LOG_DEBUG, ("SecureUI:%p: Icon set to lock\n", this));
|
||||
res = mSecurityButton->SetAttribute( NS_ConvertASCIItoUCS2("level"), NS_ConvertASCIItoUCS2("high") );
|
||||
return res;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
PR_LOG(gSecureDocLog, PR_LOG_DEBUG, ("SecureUI:%p: Icon set to broken\n", this));
|
||||
mIsDocumentBroken = PR_TRUE;
|
||||
res = mSecurityButton->SetAttribute( NS_ConvertASCIItoUCS2("level"), NS_ConvertASCIItoUCS2("broken"));
|
||||
return res;
|
||||
}
|
||||
|
||||
/// if (aProgressStateFlags == nsIWebProgress::flag_net_redirecting)
|
||||
/// {
|
||||
/// // need to implmentent.
|
||||
/// }
|
||||
|
||||
// don't need to do anything more if the page is broken or not secure...
|
||||
|
||||
if (!mIsSecureDocument || mIsDocumentBroken)
|
||||
return NS_OK;
|
||||
|
||||
// A URL is starting to load...
|
||||
if ((aProgressStateFlags & flag_start) &&
|
||||
(aProgressStateFlags & flag_is_request))
|
||||
{ // check to see if we are going to mix content.
|
||||
return CheckMixedContext(loadingURI);
|
||||
}
|
||||
|
||||
// A URL has finished loading...
|
||||
if ((aProgressStateFlags & flag_stop) &&
|
||||
(aProgressStateFlags & flag_is_request))
|
||||
{
|
||||
if (1) // FIX status from the flag...
|
||||
{
|
||||
nsCOMPtr<nsISupports> info;
|
||||
channel->GetSecurityInfo(getter_AddRefs(info));
|
||||
nsCOMPtr<nsIPSMSocketInfo> psmInfo = do_QueryInterface(info, &res);
|
||||
|
||||
// qi for the psm information about this channel load.
|
||||
if (psmInfo) {
|
||||
return NS_OK;
|
||||
}
|
||||
}
|
||||
|
||||
PR_LOG(gSecureDocLog, PR_LOG_DEBUG, ("SecureUI:%p: OnStateChange - Icon set to broken\n", this));
|
||||
mSecurityButton->SetAttribute( NS_ConvertASCIItoUCS2("level"), NS_ConvertASCIItoUCS2("broken") );
|
||||
mIsDocumentBroken = PR_TRUE;
|
||||
}
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsSecureBrowserUIImpl::OnLocationChange(nsIURI* aLocation)
|
||||
{
|
||||
mCurrentURI = aLocation;
|
||||
|
||||
if (mInitByLocationChange)
|
||||
{
|
||||
IsURLHTTPS(mCurrentURI, &mIsSecureDocument);
|
||||
mInitByLocationChange = PR_FALSE;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
nsresult
|
||||
nsSecureBrowserUIImpl::IsURLHTTPS(nsIURI* aURL, PRBool* value)
|
||||
{
|
||||
*value = PR_FALSE;
|
||||
|
||||
if (!aURL)
|
||||
return NS_OK;
|
||||
|
||||
char* scheme;
|
||||
aURL->GetScheme(&scheme);
|
||||
|
||||
if (scheme == nsnull)
|
||||
return NS_ERROR_NULL_POINTER;
|
||||
|
||||
if ( PL_strncasecmp(scheme, "https", 5) == 0 )
|
||||
*value = PR_TRUE;
|
||||
|
||||
nsMemory::Free(scheme);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void nsSecureBrowserUIImpl::GetBundleString(const nsString& name, nsString &outString)
|
||||
{
|
||||
if (mStringBundle && name.Length() > 0) {
|
||||
PRUnichar *ptrv = nsnull;
|
||||
if (NS_SUCCEEDED(mStringBundle->GetStringFromName(name.GetUnicode(), &ptrv)))
|
||||
outString = ptrv;
|
||||
else
|
||||
outString.SetLength(0);;
|
||||
|
||||
nsMemory::Free(ptrv);
|
||||
|
||||
} else {
|
||||
outString.SetLength(0);;
|
||||
}
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsSecureBrowserUIImpl::CheckProtocolContextSwitch( nsIURI* newURI, nsIURI* oldURI)
|
||||
{
|
||||
nsresult res;
|
||||
PRBool isNewSchemeSecure, isOldSchemeSecure, boolpref;
|
||||
|
||||
res = IsURLHTTPS(oldURI, &isOldSchemeSecure);
|
||||
if (NS_FAILED(res))
|
||||
return res;
|
||||
res = IsURLHTTPS(newURI, &isNewSchemeSecure);
|
||||
if (NS_FAILED(res))
|
||||
return res;
|
||||
|
||||
// Check to see if we are going from a secure page to and insecure page
|
||||
if ( !isNewSchemeSecure && isOldSchemeSecure)
|
||||
{
|
||||
mSecurityButton->RemoveAttribute( NS_ConvertASCIItoUCS2("level") );
|
||||
|
||||
if ((mPref->GetBoolPref(LEAVE_SITE_PREF, &boolpref) != 0))
|
||||
boolpref = PR_TRUE;
|
||||
|
||||
if (boolpref)
|
||||
{
|
||||
NS_WITH_SERVICE(nsICommonDialogs, dialog, kCommonDialogsCID, &res);
|
||||
if (NS_FAILED(res))
|
||||
return res;
|
||||
|
||||
nsAutoString windowTitle, message, dontShowAgain;
|
||||
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("Title"), windowTitle);
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("LeaveSiteMessage"), message);
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("DontShowAgain"), dontShowAgain);
|
||||
|
||||
PRBool outCheckValue = PR_TRUE;
|
||||
dialog->AlertCheck(mWindow,
|
||||
windowTitle.GetUnicode(),
|
||||
message.GetUnicode(),
|
||||
dontShowAgain.GetUnicode(),
|
||||
&outCheckValue);
|
||||
|
||||
if (!outCheckValue) {
|
||||
mPref->SetBoolPref(LEAVE_SITE_PREF, PR_FALSE);
|
||||
NS_WITH_SERVICE(nsIPSMComponent, psm, PSM_COMPONENT_PROGID, &res);
|
||||
if (NS_FAILED(res))
|
||||
return res;
|
||||
psm->PassPrefs();
|
||||
}
|
||||
}
|
||||
}
|
||||
// check to see if we are going from an insecure page to a secure one.
|
||||
else if (isNewSchemeSecure && !isOldSchemeSecure)
|
||||
{
|
||||
if ((mPref->GetBoolPref(ENTER_SITE_PREF, &boolpref) != 0))
|
||||
boolpref = PR_TRUE;
|
||||
|
||||
if (boolpref)
|
||||
{
|
||||
NS_WITH_SERVICE(nsICommonDialogs, dialog, kCommonDialogsCID, &res);
|
||||
if (NS_FAILED(res))
|
||||
return res;
|
||||
|
||||
nsAutoString windowTitle, message, dontShowAgain;
|
||||
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("Title"), windowTitle);
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("EnterSiteMessage"), message);
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("DontShowAgain"), dontShowAgain);
|
||||
|
||||
PRBool outCheckValue = PR_TRUE;
|
||||
dialog->AlertCheck(mWindow,
|
||||
windowTitle.GetUnicode(),
|
||||
message.GetUnicode(),
|
||||
dontShowAgain.GetUnicode(),
|
||||
&outCheckValue);
|
||||
|
||||
if (!outCheckValue)
|
||||
{
|
||||
mPref->SetBoolPref(ENTER_SITE_PREF, PR_FALSE);
|
||||
NS_WITH_SERVICE(nsIPSMComponent, psm, PSM_COMPONENT_PROGID, &res);
|
||||
if (NS_FAILED(res))
|
||||
return res;
|
||||
psm->PassPrefs();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
mIsSecureDocument = isNewSchemeSecure;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
nsresult
|
||||
nsSecureBrowserUIImpl::CheckMixedContext(nsIURI* nextURI)
|
||||
{
|
||||
PRBool secure;
|
||||
|
||||
nsresult rv = IsURLHTTPS(nextURI, &secure);
|
||||
if (NS_FAILED(rv))
|
||||
return rv;
|
||||
|
||||
if (!secure && mIsSecureDocument)
|
||||
{
|
||||
mIsDocumentBroken = PR_TRUE;
|
||||
mSecurityButton->SetAttribute( NS_ConvertASCIItoUCS2("level"), NS_ConvertASCIItoUCS2("broken") );
|
||||
|
||||
if (!mPref) return NS_ERROR_NULL_POINTER;
|
||||
|
||||
PRBool boolpref;
|
||||
if ((mPref->GetBoolPref(MIXEDCONTENT_PREF, &boolpref) != 0))
|
||||
boolpref = PR_TRUE;
|
||||
|
||||
if (boolpref && !mMixContentAlertShown)
|
||||
{
|
||||
NS_WITH_SERVICE(nsICommonDialogs, dialog, kCommonDialogsCID, &rv);
|
||||
if (NS_FAILED(rv))
|
||||
return rv;
|
||||
|
||||
nsAutoString windowTitle, message, dontShowAgain;
|
||||
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("Title"), windowTitle);
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("MixedContentMessage"), message);
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("DontShowAgain"), dontShowAgain);
|
||||
|
||||
PRBool outCheckValue = PR_TRUE;
|
||||
|
||||
dialog->AlertCheck(mWindow,
|
||||
windowTitle.GetUnicode(),
|
||||
message.GetUnicode(),
|
||||
dontShowAgain.GetUnicode(),
|
||||
&outCheckValue);
|
||||
|
||||
if (!outCheckValue) {
|
||||
mPref->SetBoolPref(MIXEDCONTENT_PREF, PR_FALSE);
|
||||
NS_WITH_SERVICE(nsIPSMComponent, psm, PSM_COMPONENT_PROGID, &rv);
|
||||
if (NS_FAILED(rv))
|
||||
return rv;
|
||||
psm->PassPrefs();
|
||||
}
|
||||
|
||||
mMixContentAlertShown = PR_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsSecureBrowserUIImpl::CheckPost(nsIURI *actionURL, PRBool *okayToPost)
|
||||
{
|
||||
PRBool secure;
|
||||
|
||||
nsresult rv = IsURLHTTPS(actionURL, &secure);
|
||||
if (NS_FAILED(rv))
|
||||
return rv;
|
||||
|
||||
// if we are posting to a secure link from a secure page, all is okay.
|
||||
if (secure && mIsSecureDocument)
|
||||
return NS_OK;
|
||||
|
||||
|
||||
PRBool boolpref;
|
||||
|
||||
// posting to a non https URL.
|
||||
if ((mPref->GetBoolPref(INSECURE_SUBMIT_PREF, &boolpref) != 0))
|
||||
boolpref = PR_TRUE;
|
||||
|
||||
if (boolpref) {
|
||||
NS_WITH_SERVICE(nsICommonDialogs, dialog, kCommonDialogsCID, &rv);
|
||||
if (NS_FAILED(rv))
|
||||
return rv;
|
||||
|
||||
nsAutoString windowTitle, message, dontShowAgain;
|
||||
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("Title"), windowTitle);
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("DontShowAgain"), dontShowAgain);
|
||||
|
||||
// posting to insecure webpage from a secure webpage.
|
||||
if (!secure && mIsSecureDocument && !mIsDocumentBroken) {
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("PostToInsecure"), message);
|
||||
} else { // anything else, post generic warning
|
||||
GetBundleString(NS_ConvertASCIItoUCS2("PostToInsecureFromInsecure"), message);
|
||||
}
|
||||
|
||||
PRBool outCheckValue = PR_TRUE;
|
||||
dialog->ConfirmCheck(mWindow,
|
||||
windowTitle.GetUnicode(),
|
||||
message.GetUnicode(),
|
||||
dontShowAgain.GetUnicode(),
|
||||
&outCheckValue,
|
||||
okayToPost);
|
||||
|
||||
if (!outCheckValue) {
|
||||
mPref->SetBoolPref(INSECURE_SUBMIT_PREF, PR_FALSE);
|
||||
NS_WITH_SERVICE(nsIPSMComponent, psm, PSM_COMPONENT_PROGID, &rv);
|
||||
if (NS_FAILED(rv))
|
||||
return rv;
|
||||
psm->PassPrefs();
|
||||
}
|
||||
} else {
|
||||
*okayToPost = PR_TRUE;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
108
mozilla/extensions/psm-glue/src/nsSecureBrowserUIImpl.h
Normal file
108
mozilla/extensions/psm-glue/src/nsSecureBrowserUIImpl.h
Normal file
@@ -0,0 +1,108 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* 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 Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Hubbie Shaw
|
||||
* Doug Turner <dougt@netscape.com>
|
||||
*/
|
||||
|
||||
#ifndef nsSecureBrowserUIImpl_h_
|
||||
#define nsSecureBrowserUIImpl_h_
|
||||
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsXPIDLString.h"
|
||||
#include "nsString.h"
|
||||
#include "nsIObserver.h"
|
||||
#include "nsIDocumentLoaderObserver.h"
|
||||
#include "nsIDOMElement.h"
|
||||
#include "nsIDOMWindow.h"
|
||||
#include "nsIStringBundle.h"
|
||||
#include "nsISecureBrowserUI.h"
|
||||
#include "nsIDocShell.h"
|
||||
#include "nsIPref.h"
|
||||
#include "nsIWebProgressListener.h"
|
||||
#include "nsIFormSubmitObserver.h"
|
||||
#include "nsIURI.h"
|
||||
|
||||
#define NS_SECURE_BROWSER_DOCOBSERVER_CLASSNAME "Mozilla Secure Browser Doc Observer"
|
||||
|
||||
#define NS_SECURE_BROWSER_DOCOBSERVER_CID \
|
||||
{0x97c06c30, 0xa145, 0x11d3, \
|
||||
{0x8c, 0x7c, 0x00, 0x60, 0x97, 0x92, 0x27, 0x8c}}
|
||||
|
||||
#define NS_SECURE_BROWSER_DOCOBSERVER_PROGID "component://netscape/secure_browser_docobserver"
|
||||
|
||||
|
||||
class nsSecureBrowserUIImpl : public nsSecureBrowserUI,
|
||||
public nsIWebProgressListener,
|
||||
public nsIFormSubmitObserver,
|
||||
public nsIObserver
|
||||
{
|
||||
public:
|
||||
|
||||
nsSecureBrowserUIImpl();
|
||||
virtual ~nsSecureBrowserUIImpl();
|
||||
|
||||
static NS_METHOD Create(nsISupports *aOuter, REFNSIID aIID, void **aResult);
|
||||
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSIWEBPROGRESSLISTENER
|
||||
NS_DECL_NSSECUREBROWSERUI
|
||||
|
||||
|
||||
// nsIObserver
|
||||
NS_DECL_NSIOBSERVER
|
||||
NS_IMETHOD Notify(nsIContent* formNode, nsIDOMWindow* window, nsIURI *actionURL);
|
||||
|
||||
protected:
|
||||
|
||||
nsCOMPtr<nsIDOMWindow> mWindow;
|
||||
nsCOMPtr<nsIDOMElement> mSecurityButton;
|
||||
nsCOMPtr<nsIDocumentLoaderObserver> mOldWebShellObserver;
|
||||
nsCOMPtr<nsIPref> mPref;
|
||||
nsCOMPtr<nsIStringBundle> mStringBundle;
|
||||
|
||||
nsCOMPtr<nsIURI> mCurrentURI;
|
||||
|
||||
PRBool mIsSecureDocument; // is https loaded
|
||||
PRBool mIsDocumentBroken; //
|
||||
PRBool mMixContentAlertShown;
|
||||
|
||||
PRBool mInitByLocationChange;
|
||||
|
||||
char* mLastPSMStatus;
|
||||
|
||||
|
||||
void GetBundleString(const nsString& name, nsString &outString);
|
||||
nsresult LoadStringBundle();
|
||||
|
||||
nsresult CheckProtocolContextSwitch( nsIURI* newURI, nsIURI* oldURI);
|
||||
nsresult CheckMixedContext(nsIURI* nextURI);
|
||||
nsresult CheckPost(nsIURI *actionURL, PRBool *okayToPost);
|
||||
nsresult IsURLHTTPS(nsIURI* aURL, PRBool *value);
|
||||
};
|
||||
|
||||
|
||||
#endif /* nsSecureBrowserUIImpl_h_ */
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,44 +0,0 @@
|
||||
STLPORT = /usr/local/include/stlport
|
||||
|
||||
CC = gcc
|
||||
CFLAGS = -g -ggdb -DDEBUG -DXP_UNIX -Wall -W -Wpointer-arith \
|
||||
-Wbad-function-cast -Wstrict-prototypes -Wmissing-prototypes \
|
||||
-Wno-non-virtual-dtor -I$(STLPORT)
|
||||
|
||||
objs = hash.o \
|
||||
icodegenerator.o \
|
||||
interpreter.o \
|
||||
js2.o \
|
||||
jsmath.o \
|
||||
jstypes.o \
|
||||
numerics.o \
|
||||
parser.o \
|
||||
utilities.o \
|
||||
world.o \
|
||||
vmtypes.o \
|
||||
debugger.o
|
||||
|
||||
gc_path = ../../gc/boehm/
|
||||
|
||||
libs = gc.a -lstdc++ -lm
|
||||
|
||||
%.o : %.cpp
|
||||
$(CC) -c $(CFLAGS) $< -o $@
|
||||
|
||||
js2: $(objs) gc.a
|
||||
$(CC) -o $@ -ggdb $(objs) $(libs)
|
||||
|
||||
gc.a:
|
||||
(cd $(gc_path) ; ln -f -s Makefile.unix Makefile ; make gc.a)
|
||||
ln -f -s $(gc_path)gc.a ./gc.a
|
||||
|
||||
gctest: gc_allocator.o
|
||||
$(CC) -o $@ -ggdb $^ $(libs)
|
||||
|
||||
clean:
|
||||
rm -f $(objs)
|
||||
|
||||
depend:
|
||||
gcc -MM *.cpp > dependencies
|
||||
|
||||
include dependencies
|
||||
@@ -1,111 +0,0 @@
|
||||
# Microsoft Developer Studio Project File - Name="CPlusPlusTests" - Package Owner=<4>
|
||||
# Microsoft Developer Studio Generated Build File, Format Version 6.00
|
||||
# ** DO NOT EDIT **
|
||||
|
||||
# TARGTYPE "Win32 (x86) Console Application" 0x0103
|
||||
|
||||
CFG=CPlusPlusTests - Win32 Debug
|
||||
!MESSAGE This is not a valid makefile. To build this project using NMAKE,
|
||||
!MESSAGE use the Export Makefile command and run
|
||||
!MESSAGE
|
||||
!MESSAGE NMAKE /f "CPlusPlusTests.mak".
|
||||
!MESSAGE
|
||||
!MESSAGE You can specify a configuration when running NMAKE
|
||||
!MESSAGE by defining the macro CFG on the command line. For example:
|
||||
!MESSAGE
|
||||
!MESSAGE NMAKE /f "CPlusPlusTests.mak" CFG="CPlusPlusTests - Win32 Debug"
|
||||
!MESSAGE
|
||||
!MESSAGE Possible choices for configuration are:
|
||||
!MESSAGE
|
||||
!MESSAGE "CPlusPlusTests - Win32 Release" (based on "Win32 (x86) Console Application")
|
||||
!MESSAGE "CPlusPlusTests - Win32 Debug" (based on "Win32 (x86) Console Application")
|
||||
!MESSAGE
|
||||
|
||||
# Begin Project
|
||||
# PROP AllowPerConfigDependencies 0
|
||||
# PROP Scc_ProjName ""
|
||||
# PROP Scc_LocalPath ""
|
||||
CPP=cl.exe
|
||||
RSC=rc.exe
|
||||
|
||||
!IF "$(CFG)" == "CPlusPlusTests - Win32 Release"
|
||||
|
||||
# PROP BASE Use_MFC 0
|
||||
# PROP BASE Use_Debug_Libraries 0
|
||||
# PROP BASE Output_Dir "Release"
|
||||
# PROP BASE Intermediate_Dir "Release"
|
||||
# PROP BASE Target_Dir ""
|
||||
# PROP Use_MFC 0
|
||||
# PROP Use_Debug_Libraries 0
|
||||
# PROP Output_Dir "Release"
|
||||
# PROP Intermediate_Dir "Release"
|
||||
# PROP Target_Dir ""
|
||||
# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
|
||||
# ADD CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
|
||||
# ADD BASE RSC /l 0x409 /d "NDEBUG"
|
||||
# ADD RSC /l 0x409 /d "NDEBUG"
|
||||
BSC32=bscmake.exe
|
||||
# ADD BASE BSC32 /nologo
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=link.exe
|
||||
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386
|
||||
|
||||
!ELSEIF "$(CFG)" == "CPlusPlusTests - Win32 Debug"
|
||||
|
||||
# PROP BASE Use_MFC 0
|
||||
# PROP BASE Use_Debug_Libraries 1
|
||||
# PROP BASE Output_Dir "Debug"
|
||||
# PROP BASE Intermediate_Dir "Debug"
|
||||
# PROP BASE Target_Dir ""
|
||||
# PROP Use_MFC 0
|
||||
# PROP Use_Debug_Libraries 1
|
||||
# PROP Output_Dir "Debug"
|
||||
# PROP Intermediate_Dir "Debug"
|
||||
# PROP Ignore_Export_Lib 0
|
||||
# PROP Target_Dir ""
|
||||
# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /GZ /c
|
||||
# ADD CPP /nologo /W3 /Gm /GX /Zi /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /GZ /c
|
||||
# ADD BASE RSC /l 0x409 /d "_DEBUG"
|
||||
# ADD RSC /l 0x409 /d "_DEBUG"
|
||||
BSC32=bscmake.exe
|
||||
# ADD BASE BSC32 /nologo
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=link.exe
|
||||
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept
|
||||
|
||||
!ENDIF
|
||||
|
||||
# Begin Target
|
||||
|
||||
# Name "CPlusPlusTests - Win32 Release"
|
||||
# Name "CPlusPlusTests - Win32 Debug"
|
||||
# Begin Group "Source Files"
|
||||
|
||||
# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\cplusplustests.cpp
|
||||
|
||||
!IF "$(CFG)" == "CPlusPlusTests - Win32 Release"
|
||||
|
||||
!ELSEIF "$(CFG)" == "CPlusPlusTests - Win32 Debug"
|
||||
|
||||
# ADD CPP /Ob1 /FR
|
||||
# SUBTRACT CPP /O<none> /YX
|
||||
|
||||
!ENDIF
|
||||
|
||||
# End Source File
|
||||
# End Group
|
||||
# Begin Group "Header Files"
|
||||
|
||||
# PROP Default_Filter "h;hpp;hxx;hm;inl"
|
||||
# End Group
|
||||
# Begin Group "Resource Files"
|
||||
|
||||
# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
|
||||
# End Group
|
||||
# End Target
|
||||
# End Project
|
||||
@@ -1,29 +0,0 @@
|
||||
Microsoft Developer Studio Workspace File, Format Version 6.00
|
||||
# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE!
|
||||
|
||||
###############################################################################
|
||||
|
||||
Project: "CPlusPlusTests"=.\CPlusPlusTests.dsp - Package Owner=<4>
|
||||
|
||||
Package=<5>
|
||||
{{{
|
||||
}}}
|
||||
|
||||
Package=<4>
|
||||
{{{
|
||||
}}}
|
||||
|
||||
###############################################################################
|
||||
|
||||
Global:
|
||||
|
||||
Package=<5>
|
||||
{{{
|
||||
}}}
|
||||
|
||||
Package=<3>
|
||||
{{{
|
||||
}}}
|
||||
|
||||
###############################################################################
|
||||
|
||||
Binary file not shown.
@@ -1,129 +0,0 @@
|
||||
#include <cstddef>
|
||||
#include <cstdio>
|
||||
#include <cstdlib>
|
||||
#include <new>
|
||||
|
||||
using namespace std;
|
||||
|
||||
struct Arena {
|
||||
const char *name;
|
||||
|
||||
Arena(const char *name): name(name) {}
|
||||
};
|
||||
|
||||
|
||||
void *operator new(size_t size, Arena &arena);
|
||||
void operator delete(void *p);
|
||||
|
||||
void *operator new(size_t size, Arena &arena)
|
||||
{
|
||||
void *p = malloc(size);
|
||||
printf("Allocating %d bytes at %p using arena \"%s\"\n", size, p, arena.name);
|
||||
return p;
|
||||
}
|
||||
|
||||
#ifndef __MWERKS__
|
||||
void operator delete(void *p, Arena &arena)
|
||||
{
|
||||
printf("Deleting object at %p using arena \"%s\"\n", p, arena.name);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
void operator delete(void *p)
|
||||
{
|
||||
printf("Deleting object at %p\n", p);
|
||||
}
|
||||
|
||||
|
||||
struct C {
|
||||
int n;
|
||||
|
||||
C(int n, bool bad = false);
|
||||
~C();
|
||||
};
|
||||
|
||||
struct Exception {
|
||||
int num;
|
||||
|
||||
explicit Exception(int n): num(n) {}
|
||||
};
|
||||
|
||||
|
||||
C::C(int n, bool bad): n(n)
|
||||
{
|
||||
printf("Constructing C #%d at %p\n", n, this);
|
||||
if (bad) {
|
||||
printf("Throwing %d; constructor aborted\n", n);
|
||||
throw Exception(n);
|
||||
}
|
||||
}
|
||||
|
||||
C::~C()
|
||||
{
|
||||
printf("Destroying C #%d at %p\n", n, this);
|
||||
}
|
||||
|
||||
|
||||
static void constructorTest1(int n, bool bad)
|
||||
{
|
||||
try {
|
||||
printf("Calling C(%d,%d)\n", n, (int)bad);
|
||||
{
|
||||
C c(n, bad);
|
||||
printf("We have C #%d\n", c.n);
|
||||
}
|
||||
printf("C is out of scope\n");
|
||||
} catch (Exception &e) {
|
||||
printf("Caught exception %d\n", e.num);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
|
||||
static void constructorTest2(int n, bool bad)
|
||||
{
|
||||
try {
|
||||
printf("Calling new C(%d,%d)\n", n, (int)bad);
|
||||
{
|
||||
C *c = new C(n, bad);
|
||||
printf("We have C #%d\n", c->n);
|
||||
delete c;
|
||||
}
|
||||
printf("C is out of scope\n");
|
||||
} catch (Exception &e) {
|
||||
printf("Caught exception %d\n", e.num);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
|
||||
static void constructorTest3(int n, bool bad)
|
||||
{
|
||||
try {
|
||||
printf("Calling new(arena) C(%d,%d)\n", n, (int)bad);
|
||||
{
|
||||
Arena arena("My arena");
|
||||
C *c = new(arena) C(n, bad);
|
||||
printf("We have C #%d\n", c->n);
|
||||
}
|
||||
printf("C is out of scope\n");
|
||||
} catch (Exception &e) {
|
||||
printf("Caught exception %d\n", e.num);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
|
||||
int main()
|
||||
{
|
||||
printf("Beginning constructor tests\n\n");
|
||||
constructorTest1(1, false);
|
||||
constructorTest1(2, true);
|
||||
constructorTest2(3, false);
|
||||
constructorTest2(4, true);
|
||||
constructorTest3(5, false);
|
||||
constructorTest3(6, true);
|
||||
printf("Ending constructor tests\n");
|
||||
return 0;
|
||||
}
|
||||
@@ -1,191 +0,0 @@
|
||||
/* -*- Mode: C; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
||||
*
|
||||
* The contents of this file are subject to the Netscape 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/NPL/
|
||||
*
|
||||
* Software distributed under the License is distributed on an "AS
|
||||
* IS" basis, WITHOUT WARRANTY OF ANY KIND, either express oqr
|
||||
* implied. See the License for the specific language governing
|
||||
* rights and limitations under the License.
|
||||
*
|
||||
* The Original Code is Mozilla Communicator client code, released
|
||||
* March 31, 1998.
|
||||
*
|
||||
* The Initial Developer of the Original Code is Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*
|
||||
* Alternatively, the contents of this file may be used under the
|
||||
* terms of the GNU Public License (the "GPL"), in which case the
|
||||
* provisions of the GPL are applicable instead of those above.
|
||||
* If you wish to allow use of your version of this file only
|
||||
* under the terms of the GPL and not to allow others to use your
|
||||
* version of this file under the NPL, indicate your decision by
|
||||
* deleting the provisions above and replace them with the notice
|
||||
* and other provisions required by the GPL. If you do not delete
|
||||
* the provisions above, a recipient may use your version of this
|
||||
* file under either the NPL or the GPL.
|
||||
*/
|
||||
|
||||
#ifndef cpucfg_h
|
||||
#define cpucfg_h
|
||||
|
||||
#define JS_HAVE_LONG_LONG
|
||||
|
||||
#ifdef XP_MAC
|
||||
#undef IS_LITTLE_ENDIAN
|
||||
#define IS_BIG_ENDIAN 1
|
||||
|
||||
#define JS_BYTES_PER_BYTE 1L
|
||||
#define JS_BYTES_PER_SHORT 2L
|
||||
#define JS_BYTES_PER_INT 4L
|
||||
#define JS_BYTES_PER_INT64 8L
|
||||
#define JS_BYTES_PER_LONG 4L
|
||||
#define JS_BYTES_PER_FLOAT 4L
|
||||
#define JS_BYTES_PER_DOUBLE 8L
|
||||
#define JS_BYTES_PER_WORD 4L
|
||||
#define JS_BYTES_PER_DWORD 8L
|
||||
|
||||
#define JS_BITS_PER_BYTE 8L
|
||||
#define JS_BITS_PER_SHORT 16L
|
||||
#define JS_BITS_PER_INT 32L
|
||||
#define JS_BITS_PER_INT64 64L
|
||||
#define JS_BITS_PER_LONG 32L
|
||||
#define JS_BITS_PER_FLOAT 32L
|
||||
#define JS_BITS_PER_DOUBLE 64L
|
||||
#define JS_BITS_PER_WORD 32L
|
||||
|
||||
#define JS_BITS_PER_BYTE_LOG2 3L
|
||||
#define JS_BITS_PER_SHORT_LOG2 4L
|
||||
#define JS_BITS_PER_INT_LOG2 5L
|
||||
#define JS_BITS_PER_INT64_LOG2 6L
|
||||
#define JS_BITS_PER_LONG_LOG2 5L
|
||||
#define JS_BITS_PER_FLOAT_LOG2 5L
|
||||
#define JS_BITS_PER_DOUBLE_LOG2 6L
|
||||
#define JS_BITS_PER_WORD_LOG2 5L
|
||||
|
||||
#define JS_ALIGN_OF_SHORT 2L
|
||||
#define JS_ALIGN_OF_INT 4L
|
||||
#define JS_ALIGN_OF_LONG 4L
|
||||
#define JS_ALIGN_OF_INT64 2L
|
||||
#define JS_ALIGN_OF_FLOAT 4L
|
||||
#define JS_ALIGN_OF_DOUBLE 4L
|
||||
#define JS_ALIGN_OF_POINTER 4L
|
||||
#define JS_ALIGN_OF_WORD 4L
|
||||
|
||||
#define JS_BYTES_PER_WORD_LOG2 2L
|
||||
#define JS_BYTES_PER_DWORD_LOG2 3L
|
||||
#define PR_WORDS_PER_DWORD_LOG2 1L
|
||||
|
||||
#elif defined(XP_PC)
|
||||
|
||||
#ifdef _WIN32
|
||||
#define IS_LITTLE_ENDIAN 1
|
||||
#undef IS_BIG_ENDIAN
|
||||
|
||||
#define JS_BYTES_PER_BYTE 1L
|
||||
#define JS_BYTES_PER_SHORT 2L
|
||||
#define JS_BYTES_PER_INT 4L
|
||||
#define JS_BYTES_PER_INT64 8L
|
||||
#define JS_BYTES_PER_LONG 4L
|
||||
#define JS_BYTES_PER_FLOAT 4L
|
||||
#define JS_BYTES_PER_DOUBLE 8L
|
||||
#define JS_BYTES_PER_WORD 4L
|
||||
#define JS_BYTES_PER_DWORD 8L
|
||||
|
||||
#define JS_BITS_PER_BYTE 8L
|
||||
#define JS_BITS_PER_SHORT 16L
|
||||
#define JS_BITS_PER_INT 32L
|
||||
#define JS_BITS_PER_INT64 64L
|
||||
#define JS_BITS_PER_LONG 32L
|
||||
#define JS_BITS_PER_FLOAT 32L
|
||||
#define JS_BITS_PER_DOUBLE 64L
|
||||
#define JS_BITS_PER_WORD 32L
|
||||
|
||||
#define JS_BITS_PER_BYTE_LOG2 3L
|
||||
#define JS_BITS_PER_SHORT_LOG2 4L
|
||||
#define JS_BITS_PER_INT_LOG2 5L
|
||||
#define JS_BITS_PER_INT64_LOG2 6L
|
||||
#define JS_BITS_PER_LONG_LOG2 5L
|
||||
#define JS_BITS_PER_FLOAT_LOG2 5L
|
||||
#define JS_BITS_PER_DOUBLE_LOG2 6L
|
||||
#define JS_BITS_PER_WORD_LOG2 5L
|
||||
|
||||
#define JS_ALIGN_OF_SHORT 2L
|
||||
#define JS_ALIGN_OF_INT 4L
|
||||
#define JS_ALIGN_OF_LONG 4L
|
||||
#define JS_ALIGN_OF_INT64 8L
|
||||
#define JS_ALIGN_OF_FLOAT 4L
|
||||
#define JS_ALIGN_OF_DOUBLE 4L
|
||||
#define JS_ALIGN_OF_POINTER 4L
|
||||
#define JS_ALIGN_OF_WORD 4L
|
||||
|
||||
#define JS_BYTES_PER_WORD_LOG2 2L
|
||||
#define JS_BYTES_PER_DWORD_LOG2 3L
|
||||
#define PR_WORDS_PER_DWORD_LOG2 1L
|
||||
#endif /* _WIN32 */
|
||||
|
||||
#if defined(_WINDOWS) && !defined(_WIN32) /* WIN16 */
|
||||
#define IS_LITTLE_ENDIAN 1
|
||||
#undef IS_BIG_ENDIAN
|
||||
|
||||
#define JS_BYTES_PER_BYTE 1L
|
||||
#define JS_BYTES_PER_SHORT 2L
|
||||
#define JS_BYTES_PER_INT 2L
|
||||
#define JS_BYTES_PER_INT64 8L
|
||||
#define JS_BYTES_PER_LONG 4L
|
||||
#define JS_BYTES_PER_FLOAT 4L
|
||||
#define JS_BYTES_PER_DOUBLE 8L
|
||||
#define JS_BYTES_PER_WORD 4L
|
||||
#define JS_BYTES_PER_DWORD 8L
|
||||
|
||||
#define JS_BITS_PER_BYTE 8L
|
||||
#define JS_BITS_PER_SHORT 16L
|
||||
#define JS_BITS_PER_INT 16L
|
||||
#define JS_BITS_PER_INT64 64L
|
||||
#define JS_BITS_PER_LONG 32L
|
||||
#define JS_BITS_PER_FLOAT 32L
|
||||
#define JS_BITS_PER_DOUBLE 64L
|
||||
#define JS_BITS_PER_WORD 32L
|
||||
|
||||
#define JS_BITS_PER_BYTE_LOG2 3L
|
||||
#define JS_BITS_PER_SHORT_LOG2 4L
|
||||
#define JS_BITS_PER_INT_LOG2 4L
|
||||
#define JS_BITS_PER_INT64_LOG2 6L
|
||||
#define JS_BITS_PER_LONG_LOG2 5L
|
||||
#define JS_BITS_PER_FLOAT_LOG2 5L
|
||||
#define JS_BITS_PER_DOUBLE_LOG2 6L
|
||||
#define JS_BITS_PER_WORD_LOG2 5L
|
||||
|
||||
#define JS_ALIGN_OF_SHORT 2L
|
||||
#define JS_ALIGN_OF_INT 2L
|
||||
#define JS_ALIGN_OF_LONG 2L
|
||||
#define JS_ALIGN_OF_INT64 2L
|
||||
#define JS_ALIGN_OF_FLOAT 2L
|
||||
#define JS_ALIGN_OF_DOUBLE 2L
|
||||
#define JS_ALIGN_OF_POINTER 2L
|
||||
#define JS_ALIGN_OF_WORD 2L
|
||||
|
||||
#define JS_BYTES_PER_WORD_LOG2 2L
|
||||
#define JS_BYTES_PER_DWORD_LOG2 3L
|
||||
#define PR_WORDS_PER_DWORD_LOG2 1L
|
||||
#endif /* defined(_WINDOWS) && !defined(_WIN32) */
|
||||
|
||||
#elif defined(XP_UNIX) || defined(XP_BEOS)
|
||||
|
||||
#error "This file is supposed to be auto-generated on UNIX platforms, but the"
|
||||
#error "static version for Mac and Windows platforms is being used."
|
||||
#error "Something's probably wrong with paths/headers/dependencies/Makefiles."
|
||||
|
||||
#else
|
||||
|
||||
#error "Must define one of XP_MAC, XP_PC, or XP_UNIX"
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
||||
@@ -1,466 +0,0 @@
|
||||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
||||
*
|
||||
* The contents of this file are subject to the Netscape 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/NPL/
|
||||
*
|
||||
* Software distributed under the License is distributed on an "AS
|
||||
* IS" basis, WITHOUT WARRANTY OF ANY KIND, either express oqr
|
||||
* implied. See the License for the specific language governing
|
||||
* rights and limitations under the License.
|
||||
*
|
||||
* The Original Code is the JavaScript 2 Prototype.
|
||||
*
|
||||
* The Initial Developer of the Original Code is Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*
|
||||
* Alternatively, the contents of this file may be used under the
|
||||
* terms of the GNU Public License (the "GPL"), in which case the
|
||||
* provisions of the GPL are applicable instead of those above.
|
||||
* If you wish to allow use of your version of this file only
|
||||
* under the terms of the GPL and not to allow others to use your
|
||||
* version of this file under the NPL, indicate your decision by
|
||||
* deleting the provisions above and replace them with the notice
|
||||
* and other provisions required by the GPL. If you do not delete
|
||||
* the provisions above, a recipient may use your version of this
|
||||
* file under either the NPL or the GPL.
|
||||
*/
|
||||
|
||||
#include "world.h"
|
||||
#include "debugger.h"
|
||||
|
||||
#include <string>
|
||||
#include <ctype.h>
|
||||
#include <assert.h>
|
||||
|
||||
namespace JavaScript {
|
||||
namespace Debugger {
|
||||
|
||||
using namespace Interpreter;
|
||||
|
||||
/* keep in sync with list in debugger.h */
|
||||
static const char *shell_cmds[][3] = {
|
||||
{"assemble", "", 0},
|
||||
{"ambiguous", "", "Test command for ambiguous command detection"},
|
||||
{"ambiguous2", "", "Test command for ambiguous command detection"},
|
||||
{"continue", "", "Continue execution until complete."},
|
||||
{"dissassemble", "[start_pc] [end_pc]", "Dissassemble entire module, or subset of module."},
|
||||
{"exit", "", 0},
|
||||
{"help", "", "Display this message."},
|
||||
{"istep", "", "Execute the current opcode and stop."},
|
||||
{"let", "", "Set a debugger environment variable."},
|
||||
{"print", "", 0},
|
||||
{"register", "", "(nyi) Show the value of a single register or all registers, or set the value of a single register."},
|
||||
{"step", "", "Execute the current JS statement and stop."},
|
||||
{0, 0} /* sentry */
|
||||
};
|
||||
|
||||
enum ShellVariable {
|
||||
TRACE_SOURCE,
|
||||
TRACE_ICODE,
|
||||
VARIABLE_COUNT
|
||||
};
|
||||
|
||||
static const char *shell_vars[][3] = {
|
||||
{"tracesource", "", "(bool) Show JS source while executing."},
|
||||
{"traceicode", " ", "(bool) Show opcodes while executing."},
|
||||
{0, 0} /* sentry */
|
||||
};
|
||||
|
||||
/* return true if str2 starts with/is str1
|
||||
* XXX ignore case */
|
||||
static bool
|
||||
startsWith (const String &str1, const String &str2)
|
||||
{
|
||||
uint n;
|
||||
size_t m = str1.size();
|
||||
|
||||
if (m > str2.size())
|
||||
return false;
|
||||
|
||||
for (n = 0; n < m; ++n)
|
||||
if (str1[n] != str2[n])
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* locate the best match for |partial| in the command list |list|.
|
||||
* if no matches are found, return |length|, if multiple matches are found,
|
||||
* return |length| plus the number of ambiguous matches
|
||||
*/
|
||||
static uint32
|
||||
matchElement (const String &partial, const char *list[][3], size_t length)
|
||||
{
|
||||
uint32 ambig_matches = 0;
|
||||
uint32 match = length;
|
||||
|
||||
for (uint32 i = 0; i < length ; ++i)
|
||||
{
|
||||
String possibleMatch (widenCString(list[i][0]));
|
||||
if (startsWith(partial, possibleMatch))
|
||||
{
|
||||
if (partial.size() == possibleMatch.size())
|
||||
{
|
||||
/* exact match */
|
||||
ambig_matches = 0;
|
||||
return i;
|
||||
}
|
||||
else if (match == COMMAND_COUNT) /* no match yet */
|
||||
match = i;
|
||||
else
|
||||
++ambig_matches; /* something already matched,
|
||||
* ambiguous command */
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if (ambig_matches == 0)
|
||||
return match;
|
||||
else
|
||||
return length + ambig_matches;
|
||||
|
||||
}
|
||||
|
||||
static void
|
||||
showHelp(Formatter &out)
|
||||
{
|
||||
int i;
|
||||
|
||||
out << "JavaScript 2.0 Debugger Help...\n\n";
|
||||
|
||||
for (i = 0; shell_cmds[i][0] != 0; i++)
|
||||
{
|
||||
out << "Command : " << shell_cmds[i][0] << " " <<
|
||||
shell_cmds[i][1] << "\n";
|
||||
|
||||
if (shell_cmds[i][2])
|
||||
out << "Help : " << shell_cmds[i][2] << "\n";
|
||||
else
|
||||
out << "Help : (probably) Not Implemented.\n";
|
||||
}
|
||||
}
|
||||
|
||||
static uint32
|
||||
getClosestSourcePosForPC (Context *cx, InstructionIterator pc)
|
||||
{
|
||||
ICodeModule *iCode = cx->getICode();
|
||||
|
||||
if (iCode->mInstructionMap->begin() == iCode->mInstructionMap->end())
|
||||
return NotABanana;
|
||||
/*NOT_REACHED ("Instruction map is empty, waah.");*/
|
||||
|
||||
InstructionMap::iterator pos_iter =
|
||||
iCode->mInstructionMap->upper_bound (pc - iCode->its_iCode->begin());
|
||||
if (pos_iter != iCode->mInstructionMap->begin())
|
||||
--pos_iter;
|
||||
|
||||
return pos_iter->second;
|
||||
}
|
||||
|
||||
void
|
||||
Shell::showSourceAtPC (Context *cx, InstructionIterator pc)
|
||||
{
|
||||
if (!mResolveFileCallback)
|
||||
{
|
||||
mErr << "Source not available (Debugger was improperly initialized.)\n";
|
||||
return;
|
||||
}
|
||||
|
||||
ICodeModule *iCode = cx->getICode();
|
||||
|
||||
String fn = iCode->getFileName();
|
||||
const Reader *reader = mResolveFileCallback(fn);
|
||||
if (!reader)
|
||||
{
|
||||
mErr << "Source not available.\n";
|
||||
return;
|
||||
}
|
||||
|
||||
uint32 pos = getClosestSourcePosForPC(cx, pc);
|
||||
if (pos == NotABanana)
|
||||
{
|
||||
mErr << "Map is empty, cannot display source.\n";
|
||||
return;
|
||||
}
|
||||
|
||||
uint32 lineNum = reader->posToLineNum (pos);
|
||||
const char16 *lineBegin, *lineEnd;
|
||||
|
||||
uint32 lineStartPos = reader->getLine (lineNum, lineBegin, lineEnd);
|
||||
String sourceLine (lineBegin, lineEnd);
|
||||
|
||||
mOut << fn << ":" << lineNum << " " << sourceLine << "\n";
|
||||
|
||||
uint padding = fn.length() + (uint32)(lineNum / 10) + 3;
|
||||
uint i;
|
||||
|
||||
for (i = 0; i < padding; i++)
|
||||
mOut << " ";
|
||||
|
||||
padding = (pos - lineStartPos);
|
||||
for (i = 0; i < padding; i++)
|
||||
mOut << ".";
|
||||
|
||||
mOut << "^\n";
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
Shell::showOpAtPC(Context* cx, InstructionIterator pc)
|
||||
{
|
||||
ICodeModule *iCode = cx->getICode();
|
||||
|
||||
if ((pc < iCode->its_iCode->begin()) ||
|
||||
(pc >= iCode->its_iCode->end()))
|
||||
{
|
||||
mErr << "PC Out Of Range.";
|
||||
return;
|
||||
}
|
||||
|
||||
JSValues ®isters = cx->getRegisters();
|
||||
|
||||
printFormat(mOut, "trace [%02u:%04u]: ",
|
||||
iCode->mID, (pc - iCode->its_iCode->begin()));
|
||||
Instruction* i = *pc;
|
||||
stdOut << *i;
|
||||
if (i->op() != BRANCH && i->count() > 0) {
|
||||
mOut << " [";
|
||||
i->printOperands(stdOut, registers);
|
||||
mOut << "]\n";
|
||||
} else {
|
||||
mOut << '\n';
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
Shell::listen(Context* cx, Context::Event event)
|
||||
{
|
||||
InstructionIterator pc = cx->getPC();
|
||||
|
||||
if (mTraceSource)
|
||||
showSourceAtPC (cx, pc);
|
||||
if (mTraceICode)
|
||||
showOpAtPC (cx, pc);
|
||||
|
||||
if (!(mStopMask & event))
|
||||
return;
|
||||
|
||||
if ((mLastCommand == STEP) && (mLastICodeID == cx->getICode()->mID) &&
|
||||
(mLastSourcePos == getClosestSourcePosForPC (cx, cx->getPC())))
|
||||
/* we're in source-step mode, and the source position hasn't
|
||||
* changed yet */
|
||||
return;
|
||||
|
||||
if (!mTraceSource && !mTraceICode)
|
||||
showSourceAtPC (cx, pc);
|
||||
|
||||
static String lastLine(widenCString("help\n"));
|
||||
String line;
|
||||
LineReader reader(mIn);
|
||||
|
||||
do {
|
||||
stdOut << "jsd";
|
||||
if (mLastCommand != COMMAND_COUNT)
|
||||
stdOut << " (" << shell_cmds[mLastCommand][0] << ") ";
|
||||
stdOut << "> ";
|
||||
|
||||
reader.readLine(line);
|
||||
|
||||
if (line[0] == uni::lf)
|
||||
line = lastLine;
|
||||
else
|
||||
lastLine = line;
|
||||
|
||||
} while (doCommand(cx, line));
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* lex and execute the debugger command in |source|, return true if the
|
||||
* command does not require the script being debugged to continue (eg, ask
|
||||
* for more debugger input.)
|
||||
*/
|
||||
bool
|
||||
Shell::doCommand (Interpreter::Context *cx, const String &source)
|
||||
{
|
||||
Lexer lex (mWorld, source, widenCString("debugger console"), 0);
|
||||
const String *cmd;
|
||||
uint32 match;
|
||||
bool rv = true;
|
||||
|
||||
const Token &t = lex.get(true);
|
||||
|
||||
if (t.hasKind(Token::identifier))
|
||||
cmd = &(t.getIdentifier());
|
||||
else
|
||||
{
|
||||
mErr << "you idiot.\n";
|
||||
return true;
|
||||
}
|
||||
|
||||
match = matchElement (*cmd, shell_cmds, (size_t)COMMAND_COUNT);
|
||||
|
||||
if (match <= (uint32)COMMAND_COUNT)
|
||||
{
|
||||
switch ((ShellCommand)match)
|
||||
{
|
||||
case COMMAND_COUNT:
|
||||
mErr << "Unknown command '" << *cmd << "'.\n";
|
||||
break;
|
||||
|
||||
case AMBIGUOUS:
|
||||
case AMBIGUOUS2:
|
||||
mErr << "I pity the foogoo.\n";
|
||||
break;
|
||||
|
||||
case CONTINUE:
|
||||
mStopMask &= (Context::EV_ALL ^ Context::EV_STEP);
|
||||
rv = false;
|
||||
break;
|
||||
|
||||
case DISSASSEMBLE:
|
||||
mOut << *cx->getICode();
|
||||
break;
|
||||
|
||||
case HELP:
|
||||
showHelp (mOut);
|
||||
break;
|
||||
|
||||
case PRINT:
|
||||
doPrint (cx, lex);
|
||||
break;
|
||||
|
||||
case STEP:
|
||||
mStopMask |= Context::EV_STEP;
|
||||
rv = false;
|
||||
break;
|
||||
|
||||
case LET:
|
||||
doSetVariable (lex);
|
||||
break;
|
||||
|
||||
default:
|
||||
mErr << "Input '" << *cmd << "' matched unimplemented " <<
|
||||
"command '" << shell_cmds[match][0] << "'.\n";
|
||||
break;
|
||||
|
||||
}
|
||||
|
||||
mLastSourcePos = getClosestSourcePosForPC (cx, cx->getPC());
|
||||
mLastICodeID = cx->getICode()->mID;
|
||||
mLastCommand = (ShellCommand)match;
|
||||
|
||||
} else
|
||||
mErr << "Ambiguous command '" << *cmd << "', " <<
|
||||
(match - (uint32)COMMAND_COUNT + 1) << " similar commands.\n";
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
void
|
||||
Shell::doSetVariable (Lexer &lex)
|
||||
{
|
||||
uint32 match;
|
||||
const String *varname;
|
||||
const Token *t = &(lex.get(true));
|
||||
|
||||
if (t->hasKind(Token::identifier))
|
||||
varname = &(t->getIdentifier());
|
||||
else
|
||||
{
|
||||
mErr << "invalid variable name.\n";
|
||||
return;
|
||||
}
|
||||
|
||||
match = matchElement (*varname, shell_vars, (size_t)VARIABLE_COUNT);
|
||||
|
||||
if (match <= (uint32)VARIABLE_COUNT)
|
||||
switch ((ShellVariable)match)
|
||||
{
|
||||
case VARIABLE_COUNT:
|
||||
mErr << "Unknown variable '" << *varname << "'.\n";
|
||||
break;
|
||||
|
||||
case TRACE_SOURCE:
|
||||
t = &(lex.get(true));
|
||||
if (t->hasKind(Token::assignment))
|
||||
t = &(lex.get(true)); /* optional = */
|
||||
|
||||
if (t->hasKind(Token::True))
|
||||
mTraceSource = true;
|
||||
else if (t->hasKind(Token::False))
|
||||
mTraceSource = false;
|
||||
else
|
||||
goto badval;
|
||||
break;
|
||||
|
||||
case TRACE_ICODE:
|
||||
t = &(lex.get(true));
|
||||
if (t->hasKind(Token::assignment))
|
||||
t = &(lex.get(true)); /* optional = */
|
||||
|
||||
if (t->hasKind(Token::True))
|
||||
mTraceICode = true;
|
||||
else if (t->hasKind(Token::False))
|
||||
mTraceICode = false;
|
||||
else
|
||||
goto badval;
|
||||
break;
|
||||
|
||||
default:
|
||||
mErr << "Variable '" << *varname <<
|
||||
"' matched unimplemented variable '" <<
|
||||
shell_vars[match][0] << "'.\n";
|
||||
}
|
||||
else
|
||||
mErr << "Ambiguous variable '" << *varname << "', " <<
|
||||
(match - (uint32)COMMAND_COUNT + 1) << " similar variables.\n";
|
||||
|
||||
return;
|
||||
|
||||
badval:
|
||||
mErr << "Invalid value for variable '" <<
|
||||
shell_vars[(ShellVariable)match][0] << "'\n";
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
Shell::doPrint (Context *, Lexer &lex)
|
||||
{
|
||||
const Token *t = &(lex.get(true));
|
||||
|
||||
if (!(t->hasKind(Token::identifier)))
|
||||
{
|
||||
mErr << "Invalid register name.\n";
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
const StringAtom *name = &(t->getIdentifier());
|
||||
|
||||
VariableMap::iterator i = ((cx->getICode())->itsVariables)->find(*name);
|
||||
// if (i)
|
||||
mOut << (*i).first << " = " << (*i).second << "\n";
|
||||
// else
|
||||
// mOut << "No " << *name << " defined.\n";
|
||||
|
||||
*/
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
} /* namespace Debugger */
|
||||
} /* namespace JavaScript */
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,163 +0,0 @@
|
||||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
||||
*
|
||||
* The contents of this file are subject to the Netscape 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/NPL/
|
||||
*
|
||||
* Software distributed under the License is distributed on an "AS
|
||||
* IS" basis, WITHOUT WARRANTY OF ANY KIND, either express oqr
|
||||
* implied. See the License for the specific language governing
|
||||
* rights and limitations under the License.
|
||||
*
|
||||
* The Original Code is the JavaScript 2 Prototype.
|
||||
*
|
||||
* The Initial Developer of the Original Code is Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*
|
||||
* Alternatively, the contents of this file may be used under the
|
||||
* terms of the GNU Public License (the "GPL"), in which case the
|
||||
* provisions of the GPL are applicable instead of those above.
|
||||
* If you wish to allow use of your version of this file only
|
||||
* under the terms of the GPL and not to allow others to use your
|
||||
* version of this file under the NPL, indicate your decision by
|
||||
* deleting the provisions above and replace them with the notice
|
||||
* and other provisions required by the GPL. If you do not delete
|
||||
* the provisions above, a recipient may use your version of this
|
||||
* file under either the NPL or the GPL.
|
||||
*/
|
||||
|
||||
/* this is all vapor, don't take it to serious yet */
|
||||
|
||||
#ifndef debugger_h
|
||||
#define debugger_h
|
||||
|
||||
#include "utilities.h"
|
||||
#include "interpreter.h"
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
namespace JavaScript {
|
||||
namespace Debugger {
|
||||
|
||||
using namespace Interpreter;
|
||||
|
||||
class Shell;
|
||||
|
||||
typedef const Reader *ResolveFileCallback (const String &fileName);
|
||||
typedef bool DebuggerCommandCallback (Shell &debugger, const Lexer &lex);
|
||||
|
||||
class Breakpoint {
|
||||
public:
|
||||
/* representation of a breakpoint */
|
||||
void set();
|
||||
void clear();
|
||||
bool getState();
|
||||
InstructionIterator getPC();
|
||||
};
|
||||
|
||||
struct DebuggerCommand
|
||||
{
|
||||
DebuggerCommand(String aName, String aParamDesc, String aShortHelp,
|
||||
String aLongHelp = widenCString("No more help available."),
|
||||
DebuggerCommandCallback *aCommandFunction = 0)
|
||||
: mName(aName), mParamDesc(aParamDesc), mShortHelp(aShortHelp),
|
||||
mLongHelp(aLongHelp), mCommandFunction(aCommandFunction) {}
|
||||
|
||||
String mName;
|
||||
String mParamDesc;
|
||||
String mShortHelp;
|
||||
String mLongHelp;
|
||||
DebuggerCommandCallback *mCommandFunction;
|
||||
};
|
||||
|
||||
/* keep in sync with list in debugger.cpp */
|
||||
enum ShellCommand {
|
||||
ASSEMBLE,
|
||||
AMBIGUOUS,
|
||||
AMBIGUOUS2,
|
||||
CONTINUE,
|
||||
DISSASSEMBLE,
|
||||
EXIT,
|
||||
HELP,
|
||||
ISTEP,
|
||||
LET,
|
||||
PRINT,
|
||||
REGISTER,
|
||||
STEP,
|
||||
COMMAND_COUNT
|
||||
};
|
||||
|
||||
class Shell : public Context::Listener {
|
||||
public:
|
||||
Shell (World &aWorld, FILE *aIn, Formatter &aOut, Formatter &aErr,
|
||||
ResolveFileCallback *aCallback = 0) :
|
||||
mWorld(aWorld), mIn(aIn), mOut(aOut), mErr(aErr),
|
||||
mResolveFileCallback(aCallback), mStopMask(Context::EV_DEBUG),
|
||||
mTraceSource(false), mTraceICode(false), mLastSourcePos(0),
|
||||
mLastICodeID(NotABanana), mLastCommand(COMMAND_COUNT)
|
||||
{
|
||||
}
|
||||
|
||||
~Shell ()
|
||||
{
|
||||
}
|
||||
|
||||
ResolveFileCallback
|
||||
*setResolveFileCallback (ResolveFileCallback *aCallback)
|
||||
{
|
||||
ResolveFileCallback *rv = mResolveFileCallback;
|
||||
mResolveFileCallback = aCallback;
|
||||
return rv;
|
||||
}
|
||||
|
||||
void listen(Context *context, Context::Event event);
|
||||
|
||||
/**
|
||||
* install on a context
|
||||
*/
|
||||
bool attachToContext (Context *aContext)
|
||||
{
|
||||
aContext->addListener (this);
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* detach an icdebugger from a context
|
||||
*/
|
||||
bool detachFromContext (Context *aContext)
|
||||
{
|
||||
aContext->removeListener (this);
|
||||
return true;
|
||||
}
|
||||
|
||||
FILE *getIStream() { return mIn; }
|
||||
Formatter &getOStream() { return mOut; }
|
||||
Formatter &getEStream() { return mErr; }
|
||||
|
||||
private:
|
||||
bool doCommand (Context *cx, const String &aSource);
|
||||
void doSetVariable (Lexer &lex);
|
||||
void doPrint (Context *cx, Lexer &lex);
|
||||
|
||||
void showOpAtPC(Context* cx, InstructionIterator pc);
|
||||
void showSourceAtPC(Context* cx, InstructionIterator pc);
|
||||
|
||||
World &mWorld;
|
||||
FILE *mIn;
|
||||
Formatter &mOut, &mErr;
|
||||
ResolveFileCallback *mResolveFileCallback;
|
||||
uint32 mStopMask;
|
||||
bool mTraceSource, mTraceICode;
|
||||
uint32 mLastSourcePos, mLastICodeID;
|
||||
ShellCommand mLastCommand;
|
||||
};
|
||||
|
||||
} /* namespace Debugger */
|
||||
} /* namespace JavaScript */
|
||||
|
||||
#endif /* debugger_h */
|
||||
@@ -1,26 +0,0 @@
|
||||
debugger.o: debugger.cpp world.h utilities.h systemtypes.h hash.h \
|
||||
parser.h debugger.h interpreter.h jstypes.h gc_allocator.h vmtypes.h \
|
||||
numerics.h jsclasses.h icode.h icodegenerator.h
|
||||
gc_allocator.o: gc_allocator.cpp gc_allocator.h gc_container.h
|
||||
hash.o: hash.cpp hash.h utilities.h systemtypes.h
|
||||
icodegenerator.o: icodegenerator.cpp numerics.h utilities.h \
|
||||
systemtypes.h world.h hash.h parser.h vmtypes.h jstypes.h \
|
||||
gc_allocator.h jsclasses.h icode.h icodegenerator.h interpreter.h
|
||||
interpreter.o: interpreter.cpp interpreter.h utilities.h systemtypes.h \
|
||||
jstypes.h gc_allocator.h vmtypes.h numerics.h jsclasses.h world.h \
|
||||
hash.h parser.h icode.h icodegenerator.h jsmath.h
|
||||
js2.o: js2.cpp world.h utilities.h systemtypes.h hash.h parser.h \
|
||||
interpreter.h jstypes.h gc_allocator.h vmtypes.h numerics.h \
|
||||
jsclasses.h icode.h icodegenerator.h debugger.h
|
||||
jsmath.o: jsmath.cpp jsmath.h jstypes.h utilities.h systemtypes.h \
|
||||
gc_allocator.h
|
||||
jstypes.o: jstypes.cpp jstypes.h utilities.h systemtypes.h \
|
||||
gc_allocator.h jsclasses.h numerics.h icodegenerator.h parser.h \
|
||||
vmtypes.h world.h hash.h icode.h
|
||||
numerics.o: numerics.cpp numerics.h utilities.h systemtypes.h
|
||||
parser.o: parser.cpp numerics.h utilities.h systemtypes.h parser.h \
|
||||
world.h hash.h
|
||||
utilities.o: utilities.cpp utilities.h systemtypes.h
|
||||
vmtypes.o: vmtypes.cpp utilities.h systemtypes.h vmtypes.h numerics.h \
|
||||
jstypes.h gc_allocator.h jsclasses.h world.h hash.h parser.h icode.h
|
||||
world.o: world.cpp world.h utilities.h systemtypes.h hash.h parser.h
|
||||
@@ -1,150 +0,0 @@
|
||||
// -*- Mode: C++; tab-width: 4; indent-tabs-mode: t; c-basic-offset: 4 -*-
|
||||
//
|
||||
// The contents of this file are subject to the Netscape 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/NPL/
|
||||
//
|
||||
// Software distributed under the License is distributed on an "AS
|
||||
// IS" basis, WITHOUT WARRANTY OF ANY KIND, either express oqr
|
||||
// implied. See the License for the specific language governing
|
||||
// rights and limitations under the License.
|
||||
//
|
||||
// The Original Code is the JavaScript 2 Prototype.
|
||||
//
|
||||
// The Initial Developer of the Original Code is Netscape
|
||||
// Communications Corporation. Portions created by Netscape are
|
||||
// Copyright (C) 2000 Netscape Communications Corporation. All
|
||||
// Rights Reserved.
|
||||
|
||||
#include <iostream>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <algorithm>
|
||||
|
||||
#include "gc_allocator.h"
|
||||
#include "gc_container.h"
|
||||
|
||||
/*
|
||||
namespace JavaScript {
|
||||
|
||||
template <class T>
|
||||
typename gc_allocator<T>::pointer
|
||||
gc_allocator<T>::allocate(gc_allocator<T>::size_type n, const void*)
|
||||
{
|
||||
return static_cast<pointer>(GC_malloc(n*sizeof(T)));
|
||||
}
|
||||
|
||||
template <class T>
|
||||
void gc_allocator<T>::deallocate(gc_allocator<T>::pointer ptr, gc_allocator<T>::size_type)
|
||||
{
|
||||
// this can really be a NO-OP with the GC.
|
||||
// ::GC_free(static_cast<void*>(ptr));
|
||||
}
|
||||
|
||||
}
|
||||
*/
|
||||
|
||||
// test driver for standalone GC development.
|
||||
|
||||
namespace JS = JavaScript;
|
||||
|
||||
template <class T>
|
||||
void* operator new(std::size_t, const JS::gc_allocator<T>& alloc)
|
||||
{
|
||||
return alloc.allocate(1);
|
||||
}
|
||||
|
||||
/**
|
||||
* Define a C++ class that is garbage collectable, and wants to have its destructor
|
||||
* called when it is finalized.
|
||||
*/
|
||||
class A {
|
||||
public:
|
||||
typedef JS::gc_traits_finalizable<A> traits;
|
||||
typedef JS::gc_allocator<A, traits> allocator;
|
||||
friend struct traits;
|
||||
|
||||
static int instances;
|
||||
|
||||
void* operator new(std::size_t)
|
||||
{
|
||||
return allocator::allocate(1);
|
||||
}
|
||||
|
||||
A()
|
||||
{
|
||||
++instances;
|
||||
std::cout << "A::A() here." << std::endl;
|
||||
}
|
||||
|
||||
protected:
|
||||
~A()
|
||||
{
|
||||
--instances;
|
||||
std::cout << "A::~A() here." << std::endl;
|
||||
}
|
||||
|
||||
private:
|
||||
// void operator delete(void*) {}
|
||||
};
|
||||
|
||||
int A::instances = 0;
|
||||
|
||||
int main(int /* argc */, char* /* argv[] */)
|
||||
{
|
||||
using namespace std;
|
||||
using namespace JS;
|
||||
|
||||
cout << "testing the GC allocator." << endl;
|
||||
|
||||
#ifdef XP_MAC
|
||||
// allocate a string, using the GC, and owned by an auto_ptr, that knows how to correctly destroy the string.
|
||||
typedef gc_container<char>::string char_string;
|
||||
typedef gc_allocator<char_string> char_string_alloc;
|
||||
auto_ptr<char_string, char_string_alloc> ptr(new(char_string_alloc()) char_string("This is a garbage collectable string."));
|
||||
const char_string& str = *ptr;
|
||||
cout << str << endl;
|
||||
#endif
|
||||
|
||||
// question, how can we partially evaluate a template?
|
||||
// can we say, typedef template <class T> vector<typename T>.
|
||||
// typedef vector<int, gc_allocator<int> > int_vector;
|
||||
typedef gc_container<int>::vector int_vector;
|
||||
|
||||
// generate 1000 random values.
|
||||
int_vector values;
|
||||
for (int i = 0; i < 1000; ++i) {
|
||||
int value = rand() % 32767;
|
||||
values.push_back(value);
|
||||
// allocate a random amount of garbage.
|
||||
if (!GC_malloc(static_cast<size_t>(value)))
|
||||
cerr << "GC_malloc failed." << endl;
|
||||
// allocate an object that has a finalizer to call its destructor.
|
||||
A* a = new A();
|
||||
}
|
||||
|
||||
// run a collection.
|
||||
// gc_allocator<void>::collect();
|
||||
GC_gcollect();
|
||||
|
||||
// print out instance count.
|
||||
cout << "A::instances = " << A::instances << endl;
|
||||
|
||||
// sort the values.
|
||||
sort(values.begin(), values.end());
|
||||
|
||||
// print the values.
|
||||
int_vector::iterator iter = values.begin(), last = values.end();
|
||||
cout << *iter++;
|
||||
while (iter < last)
|
||||
cout << ' ' << *iter++;
|
||||
cout << endl;
|
||||
|
||||
#ifdef XP_MAC
|
||||
// finally, print the string again.
|
||||
cout << str << endl;
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -1,178 +0,0 @@
|
||||
// -*- Mode: C++; tab-width: 4; indent-tabs-mode: t; c-basic-offset: 4 -*-
|
||||
//
|
||||
// The contents of this file are subject to the Netscape 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/NPL/
|
||||
//
|
||||
// Software distributed under the License is distributed on an "AS
|
||||
// IS" basis, WITHOUT WARRANTY OF ANY KIND, either express oqr
|
||||
// implied. See the License for the specific language governing
|
||||
// rights and limitations under the License.
|
||||
//
|
||||
// The Original Code is the JavaScript 2 Prototype.
|
||||
//
|
||||
// The Initial Developer of the Original Code is Netscape
|
||||
// Communications Corporation. Portions created by Netscape are
|
||||
// Copyright (C) 2000 Netscape Communications Corporation. All
|
||||
// Rights Reserved.
|
||||
|
||||
#ifndef gc_allocator_h
|
||||
#define gc_allocator_h
|
||||
|
||||
#include <memory>
|
||||
|
||||
#ifndef _WIN32 // Microsoft VC6 bug: standard identifiers should be in std namespace
|
||||
using std::size_t;
|
||||
using std::ptrdiff_t;
|
||||
#endif
|
||||
|
||||
namespace JavaScript {
|
||||
extern "C" {
|
||||
void* GC_malloc(size_t bytes);
|
||||
void* GC_malloc_atomic(size_t bytes);
|
||||
void GC_free(void* ptr);
|
||||
void GC_gcollect(void);
|
||||
|
||||
typedef void (*GC_finalization_proc) (void* obj, void* client_data);
|
||||
void GC_register_finalizer(void* obj, GC_finalization_proc proc, void* client_data,
|
||||
GC_finalization_proc *old_proc, void* *old_client_data);
|
||||
}
|
||||
|
||||
#if 0 && !defined(XP_MAC)
|
||||
// for platforms where GC doesn't exist yet.
|
||||
inline void* GC_malloc(size_t bytes) { return ::operator new(bytes); }
|
||||
inline void* GC_malloc_atomic(size_t bytes) { return ::operator new(bytes); }
|
||||
inline void GC_free(void* ptr) { operator delete(ptr); }
|
||||
inline void GC_gcollect() {}
|
||||
inline void GC_register_finalizer(void* obj, GC_finalization_proc proc, void* client_data,
|
||||
GC_finalization_proc *old_proc, void* *old_client_data) {}
|
||||
#endif
|
||||
|
||||
/**
|
||||
* General case: memory for type must be allocated as a conservatively
|
||||
* scanned block of memory.
|
||||
*/
|
||||
template <class T> struct gc_traits {
|
||||
static T* allocate(size_t n) { return static_cast<T*>(GC_malloc(n * sizeof(T))); }
|
||||
};
|
||||
|
||||
/**
|
||||
* Specializations for blocks of atomic types: the macro define_atomic_type(_type)
|
||||
* specializes gc_traits<T> for types that need not be scanned by the
|
||||
* GC. Implementors are free to define other types as atomic, if they are
|
||||
* guaranteed not to contain pointers.
|
||||
*/
|
||||
#define define_atomic_type(_type) \
|
||||
template <> struct gc_traits<_type> { \
|
||||
static _type* allocate(size_t n) \
|
||||
{ \
|
||||
return static_cast<_type*>(GC_malloc_atomic(n * sizeof(_type))); \
|
||||
} \
|
||||
};
|
||||
|
||||
define_atomic_type(char)
|
||||
define_atomic_type(unsigned char)
|
||||
define_atomic_type(short)
|
||||
define_atomic_type(unsigned short)
|
||||
define_atomic_type(int)
|
||||
define_atomic_type(unsigned int)
|
||||
define_atomic_type(long)
|
||||
define_atomic_type(unsigned long)
|
||||
define_atomic_type(float)
|
||||
define_atomic_type(double)
|
||||
|
||||
#undef define_atomic_type
|
||||
|
||||
/**
|
||||
* Traits for classes that need to have their destructor called
|
||||
* when reclaimed by the garbage collector.
|
||||
*/
|
||||
template <class T> struct gc_traits_finalizable {
|
||||
static void finalizer(void* obj, void* client_data)
|
||||
{
|
||||
T* t = static_cast<T*>(obj);
|
||||
size_t n = reinterpret_cast<size_t>(client_data);
|
||||
for (size_t i = 0; i < n; ++i)
|
||||
t[i].~T();
|
||||
}
|
||||
|
||||
static T* allocate(size_t n)
|
||||
{
|
||||
T* t = gc_traits<T>::allocate(n);
|
||||
GC_finalization_proc old_proc; void* old_client_data;
|
||||
GC_register_finalizer(t, &finalizer, reinterpret_cast<void*>(n), &old_proc, &old_client_data);
|
||||
return t;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* An allocator that can be used to allocate objects in the garbage collected heap.
|
||||
*/
|
||||
template <class T, class traits = gc_traits<T> > class gc_allocator {
|
||||
public:
|
||||
typedef T value_type;
|
||||
typedef size_t size_type;
|
||||
typedef ptrdiff_t difference_type;
|
||||
typedef T *pointer;
|
||||
typedef const T *const_pointer;
|
||||
typedef T &reference;
|
||||
typedef const T &const_reference;
|
||||
|
||||
gc_allocator() {}
|
||||
template<typename U, typename UTraits> gc_allocator(const gc_allocator<U, UTraits>&) {}
|
||||
// ~gc_allocator() {}
|
||||
|
||||
static pointer address(reference r) { return &r; }
|
||||
static const_pointer address(const_reference r) { return &r; }
|
||||
|
||||
static pointer allocate(size_type n, const void* /* hint */ = 0) { return traits::allocate(n); }
|
||||
static void deallocate(pointer, size_type) {}
|
||||
|
||||
static void construct(pointer p, const T &val) { new(p) T(val);}
|
||||
static void destroy(pointer p) { p->~T(); }
|
||||
|
||||
#if defined(__GNUC__) || defined(_WIN32)
|
||||
static size_type max_size() { return size_type(-1) / sizeof(T); }
|
||||
#else
|
||||
static size_type max_size() { return std::numeric_limits<size_type>::max() / sizeof(T); }
|
||||
#endif
|
||||
|
||||
template<class U> struct rebind { typedef gc_allocator<U> other; };
|
||||
|
||||
#ifdef _WIN32
|
||||
// raw byte allocator used on some platforms (grrr).
|
||||
typedef char _Char[1];
|
||||
static char* _Charalloc(size_type n) { return (char*) rebind<_Char>::other::allocate(n); }
|
||||
|
||||
// funky operator required for calling basic_string<T> constructor (grrr).
|
||||
template<typename U, typename UTraits> int operator==(const gc_allocator<U, UTraits>&) { return 0; }
|
||||
#endif
|
||||
|
||||
// void* deallocate used on some platforms (grrr).
|
||||
static void deallocate(void*, size_type) {}
|
||||
|
||||
static void collect() { GC_gcollect(); }
|
||||
};
|
||||
|
||||
/**
|
||||
* Generic base class for objects allocated using a gc_allocator. How they are allocated
|
||||
* can be controlled by specializing gc_traits for the specific class.
|
||||
*/
|
||||
template <typename T> class gc_object {
|
||||
public:
|
||||
void* operator new(size_t) { return gc_allocator<T>::allocate(1, 0); }
|
||||
void operator delete(void* /* ptr */) {}
|
||||
};
|
||||
|
||||
/**
|
||||
* Simpler base class for classes that have no need to specialize allocation behavior.
|
||||
*/
|
||||
class gc_base {
|
||||
public:
|
||||
void* operator new(size_t n) { return GC_malloc(n); }
|
||||
void operator delete(void*) {}
|
||||
};
|
||||
}
|
||||
|
||||
#endif /* gc_allocator_h */
|
||||
@@ -1,71 +0,0 @@
|
||||
// -*- Mode: C++; tab-width: 4; indent-tabs-mode: t; c-basic-offset: 4 -*-
|
||||
//
|
||||
// The contents of this file are subject to the Netscape 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/NPL/
|
||||
//
|
||||
// Software distributed under the License is distributed on an "AS
|
||||
// IS" basis, WITHOUT WARRANTY OF ANY KIND, either express oqr
|
||||
// implied. See the License for the specific language governing
|
||||
// rights and limitations under the License.
|
||||
//
|
||||
// The Original Code is the JavaScript 2 Prototype.
|
||||
//
|
||||
// The Initial Developer of the Original Code is Netscape
|
||||
// Communications Corporation. Portions created by Netscape are
|
||||
// Copyright (C) 2000 Netscape Communications Corporation. All
|
||||
// Rights Reserved.
|
||||
|
||||
#ifndef gc_container_h
|
||||
#define gc_container_h
|
||||
|
||||
#include "gc_allocator.h"
|
||||
|
||||
#include <list>
|
||||
#include <vector>
|
||||
#include <string>
|
||||
|
||||
#define LIST std::list
|
||||
#define VECTOR std::vector
|
||||
|
||||
#if defined(__GNUC__)
|
||||
// grr, what kind of standard is this?
|
||||
#define STRING basic_string
|
||||
#define CHAR_TRAITS string_char_traits
|
||||
#else
|
||||
#define STRING std::basic_string
|
||||
#define CHAR_TRAITS std::char_traits
|
||||
#endif
|
||||
|
||||
namespace JavaScript {
|
||||
/**
|
||||
* Rebind some of the basic container types to use a GC_allocator.
|
||||
* What I really want is something more general, something like:
|
||||
* template <typename Container, typename T> class gc_rebind {
|
||||
* typedef typename Container<T, gc_allocator<T> > other;
|
||||
* };
|
||||
* But I can't figure out how to do that with C++ templates.
|
||||
*/
|
||||
template <class T> struct gc_container {
|
||||
typedef typename LIST<T, gc_allocator<T> > list;
|
||||
typedef typename VECTOR<T, gc_allocator<T> > vector;
|
||||
typedef typename STRING<T, CHAR_TRAITS<T>, gc_allocator<T> > string;
|
||||
};
|
||||
|
||||
/**
|
||||
* But, it's pretty easy to do with macros:
|
||||
*/
|
||||
#define GC_CONTAINER(container, type) container<T, gc_allocator<T> >
|
||||
|
||||
/*
|
||||
// this gives an "unimplemented C++ feature" error using CWPro5.
|
||||
// maybe someday.
|
||||
template <template<class, class> typename Container, typename T>
|
||||
struct gc_rebind {
|
||||
typedef typename Container<T, gc_allocator<T> > container;
|
||||
};
|
||||
*/
|
||||
}
|
||||
|
||||
#endif /* gc_container_h */
|
||||
@@ -1,173 +0,0 @@
|
||||
// -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
||||
//
|
||||
// The contents of this file are subject to the Netscape 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/NPL/
|
||||
//
|
||||
// Software distributed under the License is distributed on an "AS
|
||||
// IS" basis, WITHOUT WARRANTY OF ANY KIND, either express oqr
|
||||
// implied. See the License for the specific language governing
|
||||
// rights and limitations under the License.
|
||||
//
|
||||
// The Original Code is the JavaScript 2 Prototype.
|
||||
//
|
||||
// The Initial Developer of the Original Code is Netscape
|
||||
// Communications Corporation. Portions created by Netscape are
|
||||
// Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
// Rights Reserved.
|
||||
|
||||
#include "hash.h"
|
||||
#include <new>
|
||||
namespace JS = JavaScript;
|
||||
|
||||
|
||||
//
|
||||
// Hash Codes
|
||||
//
|
||||
|
||||
|
||||
// General-purpose null-terminated C string hash function
|
||||
JS::HashNumber JS::hashString(const char *s)
|
||||
{
|
||||
HashNumber h = 0;
|
||||
uchar ch;
|
||||
|
||||
while ((ch = (uchar)*s++) != 0)
|
||||
h = (h >> 28) ^ (h << 4) ^ ch;
|
||||
return h;
|
||||
}
|
||||
|
||||
|
||||
// General-purpose String hash function
|
||||
JS::HashNumber JS::hashString(const String &s)
|
||||
{
|
||||
HashNumber h = 0;
|
||||
String::const_iterator p = s.begin();
|
||||
String::size_type n = s.size();
|
||||
|
||||
if (n < 16)
|
||||
// Hash every character in a short string.
|
||||
while (n--)
|
||||
h = (h >> 28) ^ (h << 4) ^ *p++;
|
||||
else
|
||||
// Sample a la java.lang.String.hash().
|
||||
for (String::size_type m = n / 8; n >= m; p += m, n -= m)
|
||||
h = (h >> 28) ^ (h << 4) ^ *p;
|
||||
return h;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Hash Tables
|
||||
//
|
||||
|
||||
|
||||
const uint minLgNBuckets = 4;
|
||||
|
||||
|
||||
JS::GenericHashTableIterator::GenericHashTableIterator(GenericHashTable &ht):
|
||||
ht(ht), entry(0), nextBucket(ht.buckets)
|
||||
{
|
||||
DEBUG_ONLY(++ht.nReferences);
|
||||
operator++();
|
||||
}
|
||||
|
||||
|
||||
|
||||
JS::GenericHashTableIterator &
|
||||
JS::GenericHashTableIterator::operator++()
|
||||
{
|
||||
GenericHashEntry *e = entry;
|
||||
|
||||
if (e) {
|
||||
backpointer = &e->next;
|
||||
e = e->next;
|
||||
}
|
||||
if (!e) {
|
||||
GenericHashEntry **const bucketsEnd = ht.bucketsEnd;
|
||||
GenericHashEntry **bucket = nextBucket;
|
||||
|
||||
while (bucket != bucketsEnd) {
|
||||
e = *bucket++;
|
||||
if (e) {
|
||||
backpointer = bucket-1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
nextBucket = bucket;
|
||||
}
|
||||
entry = e;
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
JS::GenericHashTable::GenericHashTable(uint32 nEntriesDefault):
|
||||
nEntries(0)
|
||||
{
|
||||
DEBUG_ONLY(nReferences = 0);
|
||||
|
||||
uint lgNBuckets = ceilingLog2(nEntriesDefault);
|
||||
if (lgNBuckets < minLgNBuckets)
|
||||
lgNBuckets = minLgNBuckets;
|
||||
defaultLgNBuckets = lgNBuckets;
|
||||
|
||||
recomputeMinMaxNEntries(lgNBuckets);
|
||||
uint32 nBuckets = JS_BIT(lgNBuckets);
|
||||
buckets = new GenericHashEntry*[nBuckets];
|
||||
// No exceptions after this point unless buckets is deleted.
|
||||
|
||||
bucketsEnd = buckets + nBuckets;
|
||||
zero(buckets, bucketsEnd);
|
||||
}
|
||||
|
||||
|
||||
// Initialize shift, minNEntries, and maxNEntries based on the lg2 of the
|
||||
// number of buckets.
|
||||
void JS::GenericHashTable::recomputeMinMaxNEntries(uint lgNBuckets)
|
||||
{
|
||||
uint32 nBuckets = JS_BIT(lgNBuckets);
|
||||
shift = 32 - lgNBuckets;
|
||||
maxNEntries = nBuckets; // Maximum ratio is 100%
|
||||
minNEntries = lgNBuckets <= defaultLgNBuckets ? 0 : 3*(nBuckets>>3); // Minimum ratio is 37.5%
|
||||
}
|
||||
|
||||
|
||||
// Rehash the table. This method cannot throw out-of-memory exceptions, so it is
|
||||
// safe to call from a destructor.
|
||||
void JS::GenericHashTable::rehash()
|
||||
{
|
||||
uint32 newLgNBuckets = ceilingLog2(nEntries);
|
||||
if (newLgNBuckets < defaultLgNBuckets)
|
||||
newLgNBuckets = defaultLgNBuckets;
|
||||
uint32 newNBuckets = JS_BIT(newLgNBuckets);
|
||||
try {
|
||||
GenericHashEntry **newBuckets = new GenericHashEntry*[newNBuckets];
|
||||
// No exceptions after this point.
|
||||
|
||||
GenericHashEntry **newBucketsEnd = newBuckets + newNBuckets;
|
||||
zero(newBuckets, newBucketsEnd);
|
||||
recomputeMinMaxNEntries(newLgNBuckets);
|
||||
GenericHashEntry **be = bucketsEnd;
|
||||
for (GenericHashEntry **b = buckets; b != be; b++) {
|
||||
GenericHashEntry *e = *b;
|
||||
while (e) {
|
||||
GenericHashEntry *next = e->next;
|
||||
// Place e in the new set of buckets.
|
||||
GenericHashEntry **nb = newBuckets + (e->keyHash*goldenRatio >> shift);
|
||||
e->next = *nb;
|
||||
*nb = e;
|
||||
e = next;
|
||||
}
|
||||
}
|
||||
delete[] buckets;
|
||||
buckets = newBuckets;
|
||||
bucketsEnd = newBucketsEnd;
|
||||
} catch (std::bad_alloc) {
|
||||
// Out of memory. Ignore the error and just relax the resizing boundaries.
|
||||
if (buckets + JS_BIT(newLgNBuckets) > bucketsEnd)
|
||||
maxNEntries >>= 1;
|
||||
else
|
||||
minNEntries <<= 1;
|
||||
}
|
||||
}
|
||||
@@ -1,373 +0,0 @@
|
||||
// -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
||||
//
|
||||
// The contents of this file are subject to the Netscape 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/NPL/
|
||||
//
|
||||
// Software distributed under the License is distributed on an "AS
|
||||
// IS" basis, WITHOUT WARRANTY OF ANY KIND, either express oqr
|
||||
// implied. See the License for the specific language governing
|
||||
// rights and limitations under the License.
|
||||
//
|
||||
// The Original Code is the JavaScript 2 Prototype.
|
||||
//
|
||||
// The Initial Developer of the Original Code is Netscape
|
||||
// Communications Corporation. Portions created by Netscape are
|
||||
// Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
// Rights Reserved.
|
||||
|
||||
#ifndef hash_h
|
||||
#define hash_h
|
||||
|
||||
#include "utilities.h"
|
||||
|
||||
namespace JavaScript {
|
||||
|
||||
|
||||
//
|
||||
// Hash Codes
|
||||
//
|
||||
|
||||
typedef uint32 HashNumber;
|
||||
|
||||
HashNumber hashString(const char *s);
|
||||
HashNumber hashString(const String &s);
|
||||
|
||||
|
||||
template<class Key>
|
||||
struct Hash {
|
||||
HashNumber operator()(Key key) const;
|
||||
};
|
||||
|
||||
template<class Key>
|
||||
inline HashNumber Hash<Key>::operator()(Key key) const
|
||||
{
|
||||
return hashString(key);
|
||||
}
|
||||
|
||||
|
||||
const HashNumber goldenRatio = 0x9E3779B9U;
|
||||
|
||||
|
||||
//
|
||||
// Private
|
||||
//
|
||||
|
||||
// Base class for user-defined hash entries.
|
||||
// private
|
||||
class GenericHashEntry {
|
||||
public:
|
||||
GenericHashEntry *next; // Link to next entry in the same bucket
|
||||
const HashNumber keyHash; // This entry's hash value
|
||||
|
||||
protected:
|
||||
explicit GenericHashEntry(HashNumber keyHash): next(0), keyHash(keyHash) {}
|
||||
|
||||
friend class GenericHashTable;
|
||||
};
|
||||
|
||||
|
||||
// private
|
||||
class GenericHashTableIterator;
|
||||
class GenericHashTable {
|
||||
protected:
|
||||
GenericHashEntry **buckets; // Vector of hash buckets
|
||||
GenericHashEntry **bucketsEnd; // Pointer past end of vector of hash buckets
|
||||
uint defaultLgNBuckets; // lg2 of minimum number of buckets for which to size the table
|
||||
uint32 nEntries; // Number of entries in table
|
||||
uint32 minNEntries; // Minimum number of entries without rehashing
|
||||
uint32 maxNEntries; // Maximum number of entries without rehashing
|
||||
uint32 shift; // 32 - lg2(number of buckets)
|
||||
#ifdef DEBUG
|
||||
public:
|
||||
uint32 nReferences; // Number of iterators and references currently pointing to this hash table
|
||||
#endif
|
||||
|
||||
public:
|
||||
explicit GenericHashTable(uint32 nEntriesDefault);
|
||||
~GenericHashTable() {
|
||||
#ifndef _WIN32
|
||||
ASSERT(nReferences == 0);
|
||||
#endif
|
||||
delete[] buckets;
|
||||
}
|
||||
|
||||
void recomputeMinMaxNEntries(uint lgNBuckets);
|
||||
void rehash();
|
||||
void maybeGrow() {if (nEntries > maxNEntries) rehash();}
|
||||
void maybeShrink() {if (nEntries < minNEntries) rehash();}
|
||||
|
||||
friend class GenericHashTableIterator;
|
||||
|
||||
typedef GenericHashTableIterator Iterator;
|
||||
};
|
||||
|
||||
// This ought to be GenericHashTable::Iterator, but this doesn't work due to a
|
||||
// Microsoft VC6 bug.
|
||||
class GenericHashTableIterator {
|
||||
protected:
|
||||
GenericHashTable &ht; // Hash table being iterated
|
||||
GenericHashEntry *entry; // Current entry; nil if done
|
||||
GenericHashEntry **backpointer; // Pointer to pointer to current entry
|
||||
GenericHashEntry **nextBucket; // Next bucket; pointer past end of vector of hash buckets if done
|
||||
public:
|
||||
explicit GenericHashTableIterator(GenericHashTable &ht);
|
||||
~GenericHashTableIterator() {ht.maybeShrink(); DEBUG_ONLY(--ht.nReferences);}
|
||||
|
||||
operator bool() const {return entry != 0;} // Return true if there are entries left.
|
||||
GenericHashTableIterator &operator++();
|
||||
};
|
||||
|
||||
|
||||
//
|
||||
// Hash Tables
|
||||
//
|
||||
|
||||
template<class Data, class Key, class H = Hash<Key> >
|
||||
class HashTable: private GenericHashTable {
|
||||
H hasher; // Hash function
|
||||
|
||||
struct Entry: public GenericHashEntry {
|
||||
Data data;
|
||||
|
||||
Entry(HashNumber keyHash, Key key): GenericHashEntry(keyHash), data(key) {}
|
||||
template<class Value>
|
||||
Entry(HashNumber keyHash, Key key, Value value): GenericHashEntry(keyHash), data(key, value) {}
|
||||
};
|
||||
|
||||
public:
|
||||
class Reference {
|
||||
#ifdef _WIN32 // Microsoft VC6 bug: friend declarations to inner classes don't work
|
||||
public:
|
||||
#endif
|
||||
Entry *entry; // Current entry; nil if done
|
||||
GenericHashEntry **backpointer; // Pointer to pointer to current entry
|
||||
const HashNumber keyHash; // This entry's key's hash value
|
||||
#ifdef DEBUG
|
||||
GenericHashTable *ht; // Hash table to which this Reference points
|
||||
#endif
|
||||
|
||||
public:
|
||||
#ifndef _WIN32
|
||||
Reference(HashTable &ht, Key key); // Search for an entry with the given key.
|
||||
#else // Microsoft VC6 bug: VC6 doesn't allow this to be defined outside the class
|
||||
Reference(HashTable &ht, Key key): keyHash(ht.hasher(key)) {
|
||||
#ifdef DEBUG
|
||||
Reference::ht = &ht;
|
||||
++ht.nReferences;
|
||||
#endif
|
||||
HashNumber kh = keyHash;
|
||||
HashNumber h = kh*goldenRatio >> ht.shift;
|
||||
GenericHashEntry **bp = ht.buckets + h;
|
||||
Entry *e;
|
||||
|
||||
while ((e = static_cast<Entry *>(*bp)) != 0 && !(e->keyHash == kh && e->data == key))
|
||||
bp = &e->next;
|
||||
entry = e;
|
||||
backpointer = bp;
|
||||
}
|
||||
#endif
|
||||
private:
|
||||
Reference(const Reference&); // No copy constructor
|
||||
void operator=(const Reference&); // No assignment operator
|
||||
public:
|
||||
#if defined(DEBUG) && !defined(_WIN32)
|
||||
~Reference() {if (ht) --ht->nReferences;}
|
||||
#endif
|
||||
|
||||
operator bool() const {return entry != 0;} // Return true if an entry was found.
|
||||
Data &operator*() const {ASSERT(entry); return entry->data;} // Return the data of the entry that was found.
|
||||
|
||||
friend class HashTable;
|
||||
};
|
||||
|
||||
class Iterator: public GenericHashTableIterator {
|
||||
public:
|
||||
explicit Iterator(HashTable &ht): GenericHashTableIterator(ht) {}
|
||||
private:
|
||||
Iterator(const Iterator&); // No copy constructor
|
||||
void operator=(const Iterator&); // No assignment operator
|
||||
public:
|
||||
|
||||
// Go to next entry.
|
||||
Iterator &operator++() {return *static_cast<Iterator*>(&GenericHashTableIterator::operator++());}
|
||||
Data &operator*() const {ASSERT(entry); return static_cast<Entry *>(entry)->data;} // Return current entry's data.
|
||||
void erase();
|
||||
};
|
||||
|
||||
HashTable(uint32 nEntriesDefault = 0, const H &hasher = H()): GenericHashTable(nEntriesDefault), hasher(hasher) {}
|
||||
~HashTable();
|
||||
|
||||
template<class Value> Data &insert(Reference &r, Key key, Value value);
|
||||
Data &insert(Reference &r, Key key);
|
||||
Data &insert(Key key);
|
||||
void erase(Reference &r);
|
||||
void erase(Key key);
|
||||
Data *operator[](Key key);
|
||||
|
||||
friend class Reference;
|
||||
friend class Iterator;
|
||||
|
||||
#ifndef _WIN32
|
||||
template<class Value> Data &insert(Key key, Value value);
|
||||
#else // Microsoft VC6 bug: VC6 doesn't allow this to be defined outside the class
|
||||
template<class Value> Data &insert(Key key, Value value) {
|
||||
Reference r(*this, key);
|
||||
if (r)
|
||||
return *r = value;
|
||||
else
|
||||
return insert(r, key, value);
|
||||
}
|
||||
#endif
|
||||
};
|
||||
|
||||
|
||||
//
|
||||
// Implementation
|
||||
//
|
||||
|
||||
template<class Data, class Key, class H>
|
||||
HashTable<Data, Key, H>::~HashTable()
|
||||
{
|
||||
GenericHashEntry **be = bucketsEnd;
|
||||
for (GenericHashEntry **b = buckets; b != be; b++) {
|
||||
Entry *e = static_cast<Entry *>(*b);
|
||||
while (e) {
|
||||
Entry *next = static_cast<Entry *>(e->next);
|
||||
delete e;
|
||||
e = next;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#ifndef _WIN32
|
||||
template<class Data, class Key, class H>
|
||||
HashTable<Data, Key, H>::Reference::Reference(HashTable &ht, Key key):
|
||||
keyHash(ht.hasher(key))
|
||||
{
|
||||
#ifdef DEBUG
|
||||
Reference::ht = &ht;
|
||||
++ht.nReferences;
|
||||
#endif
|
||||
HashNumber kh = keyHash;
|
||||
HashNumber h = kh*goldenRatio >> ht.shift;
|
||||
GenericHashEntry **bp = ht.buckets + h;
|
||||
Entry *e;
|
||||
|
||||
while ((e = static_cast<Entry *>(*bp)) != 0 && !(e->keyHash == kh && e->data == key))
|
||||
bp = &e->next;
|
||||
entry = e;
|
||||
backpointer = bp;
|
||||
}
|
||||
|
||||
|
||||
// Insert the given key/value pair into the hash table. Reference must
|
||||
// be the result of an unsuccessful search for that key in the table.
|
||||
// The reference is not valid after this method is called.
|
||||
// Return a reference to the new entry's value.
|
||||
template<class Data, class Key, class H> template<class Value>
|
||||
inline Data &HashTable<Data, Key, H>::insert(Reference &r, Key key, Value value)
|
||||
{
|
||||
ASSERT(r.ht == this && !r.entry);
|
||||
Entry *e = new Entry(r.keyHash, key, value);
|
||||
*r.backpointer = e;
|
||||
++nEntries;
|
||||
maybeGrow();
|
||||
#ifdef DEBUG
|
||||
--r.ht->nReferences;
|
||||
r.ht = 0;
|
||||
#endif
|
||||
return e->data;
|
||||
}
|
||||
#endif
|
||||
|
||||
// Same as above but without a Value argument.
|
||||
template<class Data, class Key, class H>
|
||||
inline Data &HashTable<Data, Key, H>::insert(Reference &r, Key key)
|
||||
{
|
||||
ASSERT(r.ht == this && !r.entry);
|
||||
Entry *e = new Entry(r.keyHash, key);
|
||||
*r.backpointer = e;
|
||||
++nEntries;
|
||||
maybeGrow();
|
||||
#ifdef DEBUG
|
||||
--r.ht->nReferences;
|
||||
r.ht = 0;
|
||||
#endif
|
||||
return e->data;
|
||||
}
|
||||
|
||||
|
||||
|
||||
// Insert the given key/value pair into the hash table. If an entry with a
|
||||
// matching key already exists, replace that entry's value.
|
||||
// Return a reference to the new entry's value.
|
||||
#ifndef _WIN32 // Microsoft VC6 bug: VC6 doesn't allow this to be defined outside the class
|
||||
template<class Data, class Key, class H> template<class Value>
|
||||
Data &HashTable<Data, Key, H>::insert(Key key, Value value)
|
||||
{
|
||||
Reference r(*this, key);
|
||||
if (r)
|
||||
return *r = value;
|
||||
else
|
||||
return insert(r, key, value);
|
||||
}
|
||||
#endif
|
||||
|
||||
// Same as above but without a Value argument.
|
||||
template<class Data, class Key, class H>
|
||||
Data &HashTable<Data, Key, H>::insert(Key key)
|
||||
{
|
||||
Reference r(*this, key);
|
||||
if (r)
|
||||
return *r;
|
||||
else
|
||||
return insert(r, key);
|
||||
}
|
||||
|
||||
|
||||
// Reference r must point to an existing entry. Delete that entry.
|
||||
// The reference is not valid after this method is called.
|
||||
template<class Data, class Key, class H>
|
||||
inline void HashTable<Data, Key, H>::erase(Reference &r)
|
||||
{
|
||||
Entry *e = r.entry;
|
||||
ASSERT(r.ht == this && e);
|
||||
*r.backpointer = e->next;
|
||||
--nEntries;
|
||||
delete e;
|
||||
#ifdef DEBUG
|
||||
--r.ht->nReferences;
|
||||
r.ht = 0;
|
||||
#endif
|
||||
maybeShrink();
|
||||
}
|
||||
|
||||
|
||||
// Remove the hash table entry, if any, matching the given key.
|
||||
template<class Data, class Key, class H>
|
||||
void HashTable<Data, Key, H>::erase(Key key)
|
||||
{
|
||||
Reference r(*this, key);
|
||||
if (r)
|
||||
erase(r);
|
||||
}
|
||||
|
||||
|
||||
// Return a pointer to the value of the hash table entry matching the given key.
|
||||
// Return nil if no entry matches.
|
||||
template<class Data, class Key, class H>
|
||||
Data *HashTable<Data, Key, H>::operator[](Key key)
|
||||
{
|
||||
Reference r(*this, key);
|
||||
if (r)
|
||||
return &*r;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,306 +0,0 @@
|
||||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
||||
*
|
||||
* The contents of this file are subject to the Netscape 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/NPL/
|
||||
*
|
||||
* Software distributed under the License is distributed on an "AS
|
||||
* IS" basis, WITHOUT WARRANTY OF ANY KIND, either express oqr
|
||||
* implied. See the License for the specific language governing
|
||||
* rights and limitations under the License.
|
||||
*
|
||||
* The Original Code is the JavaScript 2 Prototype.
|
||||
*
|
||||
* The Initial Developer of the Original Code is Netscape
|
||||
* Communications Corporation. Portions created by Netscape are
|
||||
* Copyright (C) 1998 Netscape Communications Corporation. All
|
||||
* Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*
|
||||
* Alternatively, the contents of this file may be used under the
|
||||
* terms of the GNU Public License (the "GPL"), in which case the
|
||||
* provisions of the GPL are applicable instead of those above.
|
||||
* If you wish to allow use of your version of this file only
|
||||
* under the terms of the GPL and not to allow others to use your
|
||||
* version of this file under the NPL, indicate your decision by
|
||||
* deleting the provisions above and replace them with the notice
|
||||
* and other provisions required by the GPL. If you do not delete
|
||||
* the provisions above, a recipient may use your version of this
|
||||
* file under either the NPL or the GPL.
|
||||
*/
|
||||
|
||||
#ifndef icodegenerator_h
|
||||
#define icodegenerator_h
|
||||
|
||||
#include <vector>
|
||||
#include <stack>
|
||||
|
||||
#include "utilities.h"
|
||||
#include "parser.h"
|
||||
#include "vmtypes.h"
|
||||
#include "jsclasses.h"
|
||||
|
||||
|
||||
namespace JavaScript {
|
||||
namespace ICG {
|
||||
|
||||
using namespace VM;
|
||||
using namespace JSTypes;
|
||||
using namespace JSClasses;
|
||||
|
||||
typedef std::map<String, TypedRegister, std::less<String> > VariableList;
|
||||
typedef std::map<uint32, uint32, std::less<uint32> > InstructionMap;
|
||||
|
||||
|
||||
class ICodeModule {
|
||||
public:
|
||||
ICodeModule(InstructionStream *iCode, VariableList *variables,
|
||||
uint32 maxRegister, uint32 maxParameter,
|
||||
InstructionMap *instructionMap) :
|
||||
its_iCode(iCode), itsVariables(variables),
|
||||
itsParameterCount(maxParameter), itsMaxRegister(maxRegister),
|
||||
mID(++sMaxID), mInstructionMap(instructionMap) { }
|
||||
~ICodeModule()
|
||||
{
|
||||
delete its_iCode;
|
||||
delete itsVariables;
|
||||
delete mInstructionMap;
|
||||
}
|
||||
|
||||
Formatter& print(Formatter& f);
|
||||
void setFileName (String aFileName) { mFileName = aFileName; }
|
||||
String getFileName () { return mFileName; }
|
||||
|
||||
InstructionStream *its_iCode;
|
||||
VariableList *itsVariables;
|
||||
uint32 itsParameterCount;
|
||||
uint32 itsMaxRegister;
|
||||
uint32 mID;
|
||||
InstructionMap *mInstructionMap;
|
||||
String mFileName;
|
||||
|
||||
static uint32 sMaxID;
|
||||
|
||||
};
|
||||
|
||||
typedef std::vector<const StringAtom *> LabelSet;
|
||||
class LabelEntry {
|
||||
public:
|
||||
LabelEntry(LabelSet *labelSet, Label *breakLabel)
|
||||
: labelSet(labelSet), breakLabel(breakLabel), continueLabel(NULL) { }
|
||||
LabelEntry(LabelSet *labelSet, Label *breakLabel, Label *continueLabel)
|
||||
: labelSet(labelSet), breakLabel(breakLabel), continueLabel(continueLabel) { }
|
||||
|
||||
bool containsLabel(const StringAtom *label);
|
||||
|
||||
LabelSet *labelSet;
|
||||
Label *breakLabel;
|
||||
Label *continueLabel;
|
||||
};
|
||||
typedef std::vector<LabelEntry *> LabelStack;
|
||||
|
||||
Formatter& operator<<(Formatter &f, ICodeModule &i);
|
||||
|
||||
/****************************************************************/
|
||||
|
||||
// An ICodeGenerator provides the interface between the parser and the
|
||||
// interpreter. The parser constructs one of these for each
|
||||
// function/script, adds statements and expressions to it and then
|
||||
// converts it into an ICodeModule, ready for execution.
|
||||
|
||||
class ICodeGenerator {
|
||||
public:
|
||||
typedef enum { kNoFlags = 0, kIsTopLevel = 0x01, kIsStaticMethod = 0x02, kIsWithinWith = 0x04 } ICodeGeneratorFlags;
|
||||
private:
|
||||
InstructionStream *iCode;
|
||||
bool iCodeOwner;
|
||||
LabelList labels;
|
||||
|
||||
Register mTopRegister; // highest (currently) alloacated register
|
||||
uint32 mParameterCount; // number of parameters declared for the function
|
||||
// these must come before any variables declared.
|
||||
TypedRegister mExceptionRegister; // reserved to carry the exception object.
|
||||
VariableList *variableList; // name|register pair for each variable
|
||||
|
||||
World *mWorld; // used to register strings
|
||||
JSScope *mGlobal; // the scope for compiling within
|
||||
LabelStack mLabelStack; // stack of LabelEntry objects, one per nested looping construct
|
||||
// maps source position to instruction index
|
||||
InstructionMap *mInstructionMap;
|
||||
|
||||
JSClass *mClass; // enclosing class when generating code for methods
|
||||
ICodeGeneratorFlags mFlags; // assorted flags
|
||||
|
||||
std::vector<bool> mPermanentRegister;
|
||||
|
||||
Register getTempRegister()
|
||||
{
|
||||
while (mTopRegister < mPermanentRegister.size())
|
||||
if (!mPermanentRegister[mTopRegister])
|
||||
return mTopRegister++;
|
||||
else
|
||||
++mTopRegister;
|
||||
mPermanentRegister.resize(mTopRegister + 1);
|
||||
mPermanentRegister[mTopRegister] = false;
|
||||
return mTopRegister++;
|
||||
}
|
||||
|
||||
void resetTopRegister() { mTopRegister = mParameterCount; }
|
||||
void resetStatement() { resetTopRegister(); }
|
||||
|
||||
TypedRegister allocateRegister(const StringAtom& name, JSType *type);
|
||||
|
||||
void setRegisterForVariable(const StringAtom& name, TypedRegister r) { (*variableList)[name] = r; }
|
||||
|
||||
JSType *findType(const StringAtom& typeName);
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
void setLabel(Label *label);
|
||||
|
||||
void jsr(Label *label) { iCode->push_back(new Jsr(label)); }
|
||||
void rts() { iCode->push_back(new Rts()); }
|
||||
void branch(Label *label);
|
||||
GenericBranch *branchTrue(Label *label, TypedRegister condition);
|
||||
GenericBranch *branchFalse(Label *label, TypedRegister condition);
|
||||
|
||||
void beginTry(Label *catchLabel, Label *finallyLabel)
|
||||
{ iCode->push_back(new Tryin(catchLabel, finallyLabel)); }
|
||||
void endTry() { iCode->push_back(new Tryout()); }
|
||||
|
||||
void beginWith(TypedRegister obj) { iCode->push_back(new Within(obj)); }
|
||||
void endWith() { iCode->push_back(new Without()); }
|
||||
|
||||
|
||||
|
||||
void startStatement(uint32 pos) { (*mInstructionMap)[iCode->size()] = pos; }
|
||||
|
||||
ICodeOp mapExprNodeToICodeOp(ExprNode::Kind kind);
|
||||
|
||||
|
||||
bool isTopLevel() { return (mFlags & kIsTopLevel) != 0; }
|
||||
bool isWithinWith() { return (mFlags & kIsWithinWith) != 0; }
|
||||
bool isStaticMethod() { return (mFlags & kIsStaticMethod) != 0; }
|
||||
|
||||
void setFlag(uint32 flag, bool v) { mFlags = (ICodeGeneratorFlags)((v) ? mFlags | flag : mFlags & ~flag); }
|
||||
|
||||
|
||||
typedef enum {Var, Property, Slot, Static, Constructor, Name, Method} LValueKind;
|
||||
|
||||
LValueKind resolveIdentifier(const StringAtom &name, TypedRegister &v, uint32 &slotIndex);
|
||||
TypedRegister handleIdentifier(IdentifierExprNode *p, ExprNode::Kind use, ICodeOp xcrementOp, TypedRegister ret, RegisterList *args);
|
||||
TypedRegister handleDot(BinaryExprNode *b, ExprNode::Kind use, ICodeOp xcrementOp, TypedRegister ret, RegisterList *args);
|
||||
ICodeModule *genFunction(FunctionStmtNode *f, bool isConstructor, JSClass *superClass);
|
||||
|
||||
public:
|
||||
|
||||
ICodeGenerator(World *world, JSScope *global, JSClass *aClass = NULL, ICodeGeneratorFlags flags = kIsTopLevel);
|
||||
|
||||
~ICodeGenerator()
|
||||
{
|
||||
if (iCodeOwner) {
|
||||
delete iCode;
|
||||
delete mInstructionMap;
|
||||
}
|
||||
}
|
||||
|
||||
ICodeModule *complete();
|
||||
|
||||
TypedRegister genExpr(ExprNode *p,
|
||||
bool needBoolValueInBranch = false,
|
||||
Label *trueBranch = NULL,
|
||||
Label *falseBranch = NULL);
|
||||
TypedRegister genStmt(StmtNode *p, LabelSet *currentLabelSet = NULL);
|
||||
|
||||
void returnStmt(TypedRegister r);
|
||||
void returnStmt();
|
||||
void throwStmt(TypedRegister r) { iCode->push_back(new Throw(r)); }
|
||||
void debuggerStmt() { iCode->push_back(new Debugger()); }
|
||||
|
||||
TypedRegister allocateVariable(const StringAtom& name);
|
||||
TypedRegister allocateVariable(const StringAtom& name, const StringAtom& typeName);
|
||||
|
||||
TypedRegister findVariable(const StringAtom& name)
|
||||
{
|
||||
VariableList::iterator i = variableList->find(name);
|
||||
return (i == variableList->end()) ? TypedRegister(NotARegister, &None_Type) : (*i).second;
|
||||
}
|
||||
|
||||
TypedRegister allocateParameter(const StringAtom& name) { mParameterCount++; return allocateRegister(name, &Any_Type); }
|
||||
TypedRegister allocateParameter(const StringAtom& name, const StringAtom& typeName)
|
||||
{ mParameterCount++; return allocateRegister(name, findType(typeName)); }
|
||||
TypedRegister allocateParameter(const StringAtom& name, JSType *type)
|
||||
{ mParameterCount++; return allocateRegister(name, type); }
|
||||
|
||||
Formatter& print(Formatter& f);
|
||||
|
||||
TypedRegister op(ICodeOp op, TypedRegister source);
|
||||
TypedRegister op(ICodeOp op, TypedRegister source1, TypedRegister source2);
|
||||
TypedRegister binaryOp(ICodeOp op, TypedRegister source1, TypedRegister source2);
|
||||
TypedRegister call(TypedRegister base, TypedRegister target, RegisterList *args);
|
||||
TypedRegister getMethod(TypedRegister thisArg, uint32 slotIndex);
|
||||
|
||||
void move(TypedRegister destination, TypedRegister source);
|
||||
TypedRegister logicalNot(TypedRegister source);
|
||||
TypedRegister test(TypedRegister source);
|
||||
|
||||
TypedRegister loadBoolean(bool value);
|
||||
TypedRegister loadImmediate(double value);
|
||||
TypedRegister loadString(const String &value);
|
||||
TypedRegister loadString(const StringAtom &name);
|
||||
|
||||
TypedRegister newObject(TypedRegister constructor);
|
||||
TypedRegister newArray();
|
||||
TypedRegister newFunction(ICodeModule *icm);
|
||||
TypedRegister newClass(JSClass *clazz);
|
||||
|
||||
TypedRegister cast(TypedRegister arg, JSType *toType);
|
||||
|
||||
TypedRegister super();
|
||||
TypedRegister loadName(const StringAtom &name, JSType *t = &Any_Type);
|
||||
void saveName(const StringAtom &name, TypedRegister value);
|
||||
TypedRegister nameXcr(const StringAtom &name, ICodeOp op);
|
||||
|
||||
TypedRegister deleteProperty(TypedRegister base, const StringAtom &name);
|
||||
TypedRegister getProperty(TypedRegister base, const StringAtom &name);
|
||||
void setProperty(TypedRegister base, const StringAtom &name, TypedRegister value);
|
||||
TypedRegister propertyXcr(TypedRegister base, const StringAtom &name, ICodeOp op);
|
||||
|
||||
TypedRegister getStatic(JSClass *base, const String &name);
|
||||
void setStatic(JSClass *base, const StringAtom &name, TypedRegister value);
|
||||
TypedRegister staticXcr(JSClass *base, const StringAtom &name, ICodeOp op);
|
||||
|
||||
TypedRegister getElement(TypedRegister base, TypedRegister index);
|
||||
void setElement(TypedRegister base, TypedRegister index, TypedRegister value);
|
||||
TypedRegister elementXcr(TypedRegister base, TypedRegister index, ICodeOp op);
|
||||
|
||||
TypedRegister getSlot(TypedRegister base, uint32 slot);
|
||||
void setSlot(TypedRegister base, uint32 slot, TypedRegister value);
|
||||
TypedRegister slotXcr(TypedRegister base, uint32 slot, ICodeOp op);
|
||||
|
||||
TypedRegister varXcr(TypedRegister var, ICodeOp op);
|
||||
|
||||
InstructionStream *getICode() { return iCode; }
|
||||
|
||||
Label *getLabel();
|
||||
|
||||
};
|
||||
|
||||
Formatter& operator<<(Formatter &f, ICodeGenerator &i);
|
||||
Formatter& operator<<(Formatter &f, ICodeModule &i);
|
||||
/*
|
||||
std::ostream &operator<<(std::ostream &s, ICodeGenerator &i);
|
||||
std::ostream &operator<<(std::ostream &s, StringAtom &str);
|
||||
*/
|
||||
|
||||
|
||||
|
||||
} /* namespace IGC */
|
||||
} /* namespace JavaScript */
|
||||
|
||||
#endif /* icodegenerator_h */
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,113 +0,0 @@
|
||||
// -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
||||
//
|
||||
// The contents of this file are subject to the Netscape 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/NPL/
|
||||
//
|
||||
// Software distributed under the License is distributed on an "AS
|
||||
// IS" basis, WITHOUT WARRANTY OF ANY KIND, either express oqr
|
||||
// implied. See the License for the specific language governing
|
||||
// rights and limitations under the License.
|
||||
//
|
||||
// The Original Code is the JavaScript 2 Prototype.
|
||||
//
|
||||
// The Initial Developer of the Original Code is Netscape
|
||||
// Communications Corporation. Portions created by Netscape are
|
||||
// Copyright (C) 2000 Netscape Communications Corporation. All
|
||||
// Rights Reserved.
|
||||
|
||||
#ifndef interpreter_h
|
||||
#define interpreter_h
|
||||
|
||||
#include "utilities.h"
|
||||
#include "jstypes.h"
|
||||
#include "vmtypes.h"
|
||||
#include "icodegenerator.h"
|
||||
#include "gc_allocator.h"
|
||||
|
||||
namespace JavaScript {
|
||||
namespace Interpreter {
|
||||
|
||||
using namespace ICG;
|
||||
using namespace JSTypes;
|
||||
|
||||
struct Activation;
|
||||
|
||||
struct Linkage;
|
||||
|
||||
class Context : public gc_base {
|
||||
void initContext();
|
||||
public:
|
||||
explicit Context(World& world, JSScope* aGlobal)
|
||||
: mWorld(world), mGlobal(aGlobal), mLinkage(0), mActivation(0), mHasOperatorsPackageLoaded(false) { initContext(); }
|
||||
|
||||
World& getWorld() { return mWorld; }
|
||||
JSScope* getGlobalObject() { return mGlobal; }
|
||||
InstructionIterator getPC() { return mPC; }
|
||||
|
||||
JSValues& getRegisters();
|
||||
ICodeModule* getICode();
|
||||
|
||||
enum Event {
|
||||
EV_NONE = 0x0000,
|
||||
EV_STEP = 0x0001,
|
||||
EV_THROW = 0x0002,
|
||||
EV_DEBUG = 0x0004,
|
||||
EV_ALL = 0xffff
|
||||
};
|
||||
|
||||
class Listener {
|
||||
public:
|
||||
virtual void listen(Context *context, Event event) = 0;
|
||||
};
|
||||
|
||||
void addListener(Listener* listener);
|
||||
void removeListener(Listener* listener);
|
||||
|
||||
class Frame {
|
||||
public:
|
||||
virtual Frame* getNext() = 0;
|
||||
virtual void getState(InstructionIterator& pc, JSValues*& registers,
|
||||
ICodeModule*& iCode) = 0;
|
||||
};
|
||||
|
||||
Frame* getFrames();
|
||||
|
||||
JSValue interpret(ICodeModule* iCode, const JSValues& args);
|
||||
void doCall(JSFunction *target, Instruction *pc);
|
||||
|
||||
ICodeModule* compile(const String &source);
|
||||
ICodeModule* genCode(StmtNode *p, const String &fileName);
|
||||
JSValue readEvalFile(FILE* in, const String& fileName);
|
||||
|
||||
void addBinaryOperator(BinaryOperator::BinaryOp op, BinaryOperator *fn) { mBinaryOperators[op].push_back(fn); }
|
||||
const JSValue findBinaryOverride(JSValue &operand1, JSValue &operand2, BinaryOperator::BinaryOp op);
|
||||
|
||||
|
||||
bool hasOperatorsPackageLoaded() { return mHasOperatorsPackageLoaded; }
|
||||
|
||||
private:
|
||||
void broadcast(Event event);
|
||||
void initOperatorsPackage();
|
||||
|
||||
private:
|
||||
World& mWorld;
|
||||
JSScope* mGlobal;
|
||||
Linkage* mLinkage;
|
||||
typedef std::vector<Listener*, gc_allocator<Listener*> > ListenerList;
|
||||
typedef ListenerList::iterator ListenerIterator;
|
||||
ListenerList mListeners;
|
||||
Activation* mActivation;
|
||||
bool mHasOperatorsPackageLoaded;
|
||||
|
||||
InstructionIterator mPC;
|
||||
|
||||
BinaryOperatorList mBinaryOperators[BinaryOperator::BinaryOperatorCount];
|
||||
|
||||
}; /* class Context */
|
||||
|
||||
} /* namespace Interpreter */
|
||||
} /* namespace JavaScript */
|
||||
|
||||
#endif /* interpreter_h */
|
||||
@@ -1,33 +0,0 @@
|
||||
class ArithmeticNode extends BinaryNode {
|
||||
|
||||
ArithmeticNode(String aOp, ExpressionNode aLeft, ExpressionNode aRight)
|
||||
{
|
||||
super(aOp, aLeft, aRight);
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
JSValue lV = left.eval(theEnv);
|
||||
JSValue rV = right.eval(theEnv);
|
||||
|
||||
if (op == "+")
|
||||
return lV.add(theEnv, rV);
|
||||
else
|
||||
if (op == "-")
|
||||
return lV.subtract(theEnv, rV);
|
||||
else
|
||||
if (op == "*")
|
||||
return lV.multiply(theEnv, rV);
|
||||
else
|
||||
if (op == "/")
|
||||
return lV.divide(theEnv, rV);
|
||||
else
|
||||
if (op == "%")
|
||||
return lV.remainder(theEnv, rV);
|
||||
else {
|
||||
System.out.println("missing arithmetic op " + op);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,16 +0,0 @@
|
||||
class AssignmentNode extends BinaryNode {
|
||||
|
||||
AssignmentNode(String aOp, ExpressionNode aLeft, ExpressionNode aRight)
|
||||
{
|
||||
super(aOp, aLeft, aRight);
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
JSReference lV = left.evalLHS(theEnv);
|
||||
JSValue rV = right.eval(theEnv);
|
||||
|
||||
return lV.base.putProp(theEnv, lV.id, rV);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,72 +0,0 @@
|
||||
class BinaryNode extends ExpressionNode {
|
||||
|
||||
BinaryNode(String aOp, ExpressionNode aLeft, ExpressionNode aRight)
|
||||
{
|
||||
left = aLeft;
|
||||
right = aRight;
|
||||
op = aOp;
|
||||
}
|
||||
|
||||
JSReference evalLHS(Environment theEnv)
|
||||
{
|
||||
if (op == ".") {
|
||||
JSValue lV = left.eval(theEnv);
|
||||
JSString id;
|
||||
if (right instanceof JSIdentifier)
|
||||
id = (JSString)right;
|
||||
else
|
||||
id = right.eval(theEnv).toJSString(theEnv);
|
||||
return new JSReference(lV, id);
|
||||
}
|
||||
else
|
||||
throw new RuntimeException("bad lValue operator " + op);
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
JSValue lV = left.eval(theEnv);
|
||||
JSValue rV = right.eval(theEnv);
|
||||
|
||||
if (op == ".")
|
||||
return lV.getProp(theEnv, rV.toJSString(theEnv));
|
||||
else
|
||||
if (op == "()")
|
||||
return lV.call(theEnv, rV);
|
||||
else
|
||||
if (op == ",")
|
||||
return JSValueList.buildList(lV, rV);
|
||||
else {
|
||||
System.out.println("missing binary op " + op);
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
String print(String indent)
|
||||
{
|
||||
StringBuffer result = new StringBuffer(indent);
|
||||
result.append(getClass().toString());
|
||||
result.append(" ");
|
||||
result.append(op);
|
||||
result.append("\n");
|
||||
indent += " ";
|
||||
if (left == null) {
|
||||
result.append(indent);
|
||||
result.append("null\n");
|
||||
}
|
||||
else
|
||||
result.append(left.print(indent));
|
||||
if (right == null) {
|
||||
result.append(indent);
|
||||
result.append("null\n");
|
||||
}
|
||||
else
|
||||
result.append(right.print(indent));
|
||||
return result.toString();
|
||||
}
|
||||
|
||||
protected ExpressionNode left;
|
||||
protected ExpressionNode right;
|
||||
protected String op;
|
||||
|
||||
}
|
||||
@@ -1,36 +0,0 @@
|
||||
class BitwiseNode extends BinaryNode {
|
||||
|
||||
BitwiseNode(String aOp, ExpressionNode aLeft, ExpressionNode aRight)
|
||||
{
|
||||
super(aOp, aLeft, aRight);
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
JSInteger lV = left.eval(theEnv).toJSInteger(theEnv);
|
||||
JSValue rV = right.eval(theEnv);
|
||||
|
||||
if (op == "&")
|
||||
return lV.and(theEnv, rV);
|
||||
else
|
||||
if (op == "|")
|
||||
return lV.or(theEnv, rV);
|
||||
else
|
||||
if (op == "^")
|
||||
return lV.xor(theEnv, rV);
|
||||
else
|
||||
if (op == "<<")
|
||||
return lV.shr(theEnv, rV);
|
||||
else
|
||||
if (op == ">>")
|
||||
return lV.shl(theEnv, rV);
|
||||
else
|
||||
if (op == ">>>")
|
||||
return lV.ushl(theEnv, rV);
|
||||
else {
|
||||
System.out.println("missing bitwise op " + op);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,24 +0,0 @@
|
||||
import java.io.*;
|
||||
|
||||
class Brenda {
|
||||
|
||||
public static void main(String[] args) {
|
||||
try {
|
||||
JSLexer lexer = new JSLexer((args != null) ? new DataInputStream(new FileInputStream(args[0])) : new DataInputStream(System.in));
|
||||
JSParser parser = new JSParser(lexer);
|
||||
ControlNodeGroup tree = new ControlNodeGroup();
|
||||
parser.statements(0, tree);
|
||||
System.out.println(ControlNode.printAll());
|
||||
|
||||
Environment theEnv = new Environment();
|
||||
ControlNode c = tree.getHead();
|
||||
while (c != null) c = c.eval(theEnv);
|
||||
|
||||
System.out.println("After eval :\n" + theEnv.print());
|
||||
|
||||
} catch(Exception e) {
|
||||
System.err.println("exception: "+e);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,59 +0,0 @@
|
||||
class ConditionalNode extends ControlNode {
|
||||
|
||||
ConditionalNode(ExpressionNode aCondition)
|
||||
{
|
||||
super(aCondition);
|
||||
}
|
||||
|
||||
ConditionalNode(ExpressionNode aCondition, ControlNode aTrueCode)
|
||||
{
|
||||
super(aCondition);
|
||||
trueCode = aTrueCode;
|
||||
}
|
||||
|
||||
ConditionalNode(ExpressionNode aCondition, ControlNode aTrueCode, ControlNode aFalseCode)
|
||||
{
|
||||
super(aCondition);
|
||||
trueCode = aTrueCode;
|
||||
setNext(aFalseCode);
|
||||
}
|
||||
|
||||
void moveNextToTrue()
|
||||
{
|
||||
trueCode = next;
|
||||
setNext(null);
|
||||
}
|
||||
|
||||
ControlNode eval(Environment theEnv)
|
||||
{
|
||||
JSBoolean b = expr.eval(theEnv).toJSBoolean(theEnv);
|
||||
if (b.isTrue())
|
||||
return trueCode;
|
||||
else
|
||||
return next;
|
||||
}
|
||||
|
||||
String print()
|
||||
{
|
||||
StringBuffer result = new StringBuffer("ConditionalNode ");
|
||||
result.append(index);
|
||||
result.append("\nexpr:\n");
|
||||
if (expr == null)
|
||||
result.append("expr = null\n");
|
||||
else
|
||||
result.append(expr.print(""));
|
||||
result.append("true branch:\n");
|
||||
if (trueCode == null)
|
||||
result.append("true branch = null\n");
|
||||
else
|
||||
result.append("true branch->" + trueCode.index + "\n");
|
||||
result.append("false branch:\n");
|
||||
if (next == null)
|
||||
result.append("false branch = null\n");
|
||||
else
|
||||
result.append("false branch->" + next.index + "\n");
|
||||
return result.toString();
|
||||
}
|
||||
|
||||
protected ControlNode trueCode;
|
||||
}
|
||||
@@ -1,67 +0,0 @@
|
||||
|
||||
import java.util.Vector;
|
||||
|
||||
class ControlNode {
|
||||
|
||||
private static Vector gList = new Vector();
|
||||
|
||||
static String printAll()
|
||||
{
|
||||
StringBuffer result = new StringBuffer();
|
||||
for (int i = 0; i < gList.size(); i++) {
|
||||
result.append(((ControlNode)(gList.elementAt(i))).print());
|
||||
}
|
||||
return result.toString();
|
||||
}
|
||||
|
||||
ControlNode(ExpressionNode anExpr)
|
||||
{
|
||||
expr = anExpr;
|
||||
index = gList.size();
|
||||
gList.addElement(this);
|
||||
}
|
||||
|
||||
ExpressionNode getExpression()
|
||||
{
|
||||
return expr;
|
||||
}
|
||||
|
||||
void setNext(ControlNode aNext)
|
||||
{
|
||||
next = aNext;
|
||||
}
|
||||
|
||||
ControlNode eval(Environment theEnv)
|
||||
{
|
||||
if (expr != null) theEnv.resultValue = expr.eval(theEnv);
|
||||
return next;
|
||||
}
|
||||
|
||||
String print()
|
||||
{
|
||||
StringBuffer result = new StringBuffer(getClass().toString().substring(6));
|
||||
result.append(" #");
|
||||
result.append(index);
|
||||
result.append("\nexpr: \n");
|
||||
if (expr == null)
|
||||
result.append("expr = null\n");
|
||||
else
|
||||
result.append(expr.print(""));
|
||||
result.append("next: ");
|
||||
if (next == null)
|
||||
result.append("next = null\n");
|
||||
else
|
||||
result.append("next->" + next.index + "\n");
|
||||
return result.toString();
|
||||
}
|
||||
|
||||
protected ExpressionNode expr;
|
||||
protected ControlNode next;
|
||||
protected int index;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,153 +0,0 @@
|
||||
|
||||
import java.util.Vector;
|
||||
|
||||
class ControlNodeGroup {
|
||||
|
||||
ControlNodeGroup()
|
||||
{
|
||||
}
|
||||
|
||||
ControlNodeGroup(ControlNode aHead)
|
||||
{
|
||||
head = aHead;
|
||||
}
|
||||
|
||||
void add(ControlNodeGroup aGroup)
|
||||
{
|
||||
if (head == null) {
|
||||
head = aGroup.head;
|
||||
}
|
||||
else {
|
||||
fixTails(aGroup.getHead());
|
||||
}
|
||||
addTails(aGroup);
|
||||
}
|
||||
|
||||
void add(ControlNode aNode)
|
||||
{
|
||||
fixTails(aNode);
|
||||
addTail(aNode);
|
||||
if (head == null) head = aNode;
|
||||
}
|
||||
|
||||
void addBreak(ControlNode aNode)
|
||||
{
|
||||
fixTails(aNode);
|
||||
addBreakTail(aNode);
|
||||
if (head == null) head = aNode;
|
||||
}
|
||||
|
||||
void addContinue(ControlNode aNode)
|
||||
{
|
||||
fixTails(aNode);
|
||||
addContinueTail(aNode);
|
||||
if (head == null) head = aNode;
|
||||
}
|
||||
|
||||
void fixTails(ControlNode butt)
|
||||
{
|
||||
int count = tails.size();
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
ControlNode aNode = (ControlNode)(tails.elementAt(i));
|
||||
aNode.setNext(butt);
|
||||
}
|
||||
tails.removeAllElements();
|
||||
}
|
||||
|
||||
void fixContinues(ControlNode butt, String label)
|
||||
{
|
||||
int count = continueTails.size();
|
||||
int i = 0;
|
||||
while (i < count) {
|
||||
ControlNode c = (ControlNode)(continueTails.elementAt(i));
|
||||
ExpressionNode e = c.getExpression();
|
||||
String tgt = (e == null) ? null : ((JSIdentifier)e).s;
|
||||
if ((tgt == null) || tgt.equals(label)) {
|
||||
c.setNext(butt);
|
||||
continueTails.removeElementAt(i);
|
||||
count--;
|
||||
}
|
||||
else
|
||||
i++;
|
||||
}
|
||||
}
|
||||
|
||||
void setHead(ControlNode aHead)
|
||||
{
|
||||
head = aHead;
|
||||
}
|
||||
|
||||
ControlNode getHead()
|
||||
{
|
||||
return head;
|
||||
}
|
||||
|
||||
void addTail(ControlNode aTail)
|
||||
{
|
||||
tails.addElement(aTail);
|
||||
}
|
||||
|
||||
void addBreakTail(ControlNode aTail)
|
||||
{
|
||||
breakTails.addElement(aTail);
|
||||
}
|
||||
|
||||
void addContinueTail(ControlNode aTail)
|
||||
{
|
||||
continueTails.addElement(aTail);
|
||||
}
|
||||
|
||||
void removeTail(ControlNode aTail)
|
||||
{
|
||||
tails.removeElement(aTail);
|
||||
}
|
||||
|
||||
void addTails(ControlNodeGroup aGroup)
|
||||
{
|
||||
int count = aGroup.tails.size();
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
tails.addElement(aGroup.tails.elementAt(i));
|
||||
}
|
||||
aGroup.tails.removeAllElements();
|
||||
|
||||
count = aGroup.breakTails.size();
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
breakTails.addElement(aGroup.breakTails.elementAt(i));
|
||||
}
|
||||
aGroup.breakTails.removeAllElements();
|
||||
|
||||
count = aGroup.continueTails.size();
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
continueTails.addElement(aGroup.continueTails.elementAt(i));
|
||||
}
|
||||
aGroup.continueTails.removeAllElements();
|
||||
}
|
||||
|
||||
void shiftBreakTails(String label)
|
||||
{
|
||||
int count = breakTails.size();
|
||||
int i = 0;
|
||||
while (i < count) {
|
||||
ControlNode c = (ControlNode)(breakTails.elementAt(i));
|
||||
ExpressionNode e = c.getExpression();
|
||||
String tgt = (e == null) ? null : ((JSIdentifier)e).s;
|
||||
if ((tgt == null) || tgt.equals(label)) {
|
||||
tails.addElement(c);
|
||||
breakTails.removeElementAt(i);
|
||||
count--;
|
||||
}
|
||||
else
|
||||
i++;
|
||||
}
|
||||
}
|
||||
|
||||
ControlNode head;
|
||||
Vector tails = new Vector();
|
||||
Vector breakTails = new Vector();
|
||||
Vector continueTails = new Vector();
|
||||
|
||||
}
|
||||
@@ -1,30 +0,0 @@
|
||||
|
||||
import java.util.Hashtable;
|
||||
|
||||
class Environment {
|
||||
|
||||
JSScope scope = new JSScope("globals");
|
||||
JSScope globalScope = scope;
|
||||
|
||||
|
||||
void enterNewScope(JSScope newScope)
|
||||
{
|
||||
newScope.parent = scope;
|
||||
scope = newScope;
|
||||
}
|
||||
|
||||
void leaveScope()
|
||||
{
|
||||
scope = scope.parent;
|
||||
}
|
||||
|
||||
String print()
|
||||
{
|
||||
StringBuffer result = new StringBuffer("Globals contents :\n");
|
||||
result.append(scope.toString());
|
||||
return result.toString();
|
||||
}
|
||||
|
||||
JSValue resultValue;
|
||||
|
||||
}
|
||||
@@ -1,24 +0,0 @@
|
||||
class ExpressionNode {
|
||||
|
||||
ExpressionNode()
|
||||
{
|
||||
}
|
||||
|
||||
String print(String indent)
|
||||
{
|
||||
return indent + "ExpressionNode(" + getClass().toString() + ")\n";
|
||||
}
|
||||
|
||||
JSReference evalLHS(Environment theEnv)
|
||||
{
|
||||
System.out.println("Unimplemented evalLHS for " + print(""));
|
||||
return null;
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
System.out.println("Unimplemented eval for " + print(""));
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,36 +0,0 @@
|
||||
class FunctionNode extends ExpressionNode {
|
||||
|
||||
FunctionNode(JSIdentifier aName, ControlNodeGroup aBody, ExpressionNode parameterList)
|
||||
{
|
||||
fn = new NativeFunction(aBody.getHead());
|
||||
name = aName;
|
||||
if (parameterList != null) {
|
||||
if (parameterList instanceof BinaryNode)
|
||||
buildParameterVector((BinaryNode)parameterList);
|
||||
else
|
||||
fn.parameters.addElement(parameterList);
|
||||
}
|
||||
}
|
||||
|
||||
void buildParameterVector(BinaryNode x)
|
||||
{
|
||||
if (x.left instanceof BinaryNode) {
|
||||
buildParameterVector((BinaryNode)(x.left));
|
||||
fn.parameters.addElement(x.right);
|
||||
}
|
||||
else {
|
||||
fn.parameters.addElement(x.left);
|
||||
fn.parameters.addElement(x.right);
|
||||
}
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
theEnv.scope.putProp(theEnv, name, fn);
|
||||
return fn;
|
||||
}
|
||||
|
||||
JSString name;
|
||||
NativeFunction fn;
|
||||
|
||||
}
|
||||
@@ -1,52 +0,0 @@
|
||||
class JSBoolean extends JSValue {
|
||||
|
||||
static JSBoolean JSTrue = new JSBoolean(true);
|
||||
static JSBoolean JSFalse = new JSBoolean(false);
|
||||
|
||||
private JSBoolean(boolean p)
|
||||
{
|
||||
b = p;
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
return this;
|
||||
}
|
||||
|
||||
boolean isTrue()
|
||||
{
|
||||
return b;
|
||||
}
|
||||
|
||||
boolean isFalse()
|
||||
{
|
||||
return !b;
|
||||
}
|
||||
|
||||
JSValue bang(Environment theEnv) {
|
||||
return (b) ? JSFalse : JSTrue;
|
||||
}
|
||||
|
||||
JSValue typeof(Environment theEnv) {
|
||||
return new JSString("boolean");
|
||||
}
|
||||
|
||||
JSBoolean toJSBoolean(Environment theEnv) {
|
||||
return this;
|
||||
}
|
||||
|
||||
JSValue toPrimitive(Environment theEnv, String hint) {
|
||||
return this;
|
||||
}
|
||||
|
||||
JSString toJSString(Environment theEnv) {
|
||||
return (b) ? new JSString("true") : new JSString("false");
|
||||
}
|
||||
|
||||
JSDouble toJSDouble(Environment theEnv) {
|
||||
return (b) ? new JSDouble(1) : new JSDouble(0);
|
||||
}
|
||||
|
||||
boolean b;
|
||||
|
||||
}
|
||||
@@ -1,111 +0,0 @@
|
||||
class JSDouble extends JSNumber {
|
||||
|
||||
JSDouble(double p)
|
||||
{
|
||||
d = p;
|
||||
}
|
||||
|
||||
JSDouble(String s)
|
||||
{
|
||||
d = new Double(s).doubleValue();
|
||||
}
|
||||
|
||||
String print(String indent)
|
||||
{
|
||||
return indent + "JSDouble " + d + "\n";
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return Double.toString(d);
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
return this;
|
||||
}
|
||||
|
||||
JSValue plus(Environment theEnv) {
|
||||
return this;
|
||||
}
|
||||
|
||||
JSValue minus(Environment theEnv) {
|
||||
return new JSDouble(-d);
|
||||
}
|
||||
|
||||
JSValue add(Environment theEnv, JSValue rV) {
|
||||
if (rV instanceof JSString)
|
||||
return toJSString(theEnv).add(theEnv, rV);
|
||||
else
|
||||
return new JSDouble(d + rV.toJSDouble(theEnv).d);
|
||||
}
|
||||
|
||||
JSValue subtract(Environment theEnv, JSValue rV) {
|
||||
return new JSDouble(d - rV.toJSDouble(theEnv).d);
|
||||
}
|
||||
|
||||
JSValue multiply(Environment theEnv, JSValue rV) {
|
||||
return new JSDouble(d * rV.toJSDouble(theEnv).d);
|
||||
}
|
||||
|
||||
JSValue divide(Environment theEnv, JSValue rV) {
|
||||
return new JSDouble(d / rV.toJSDouble(theEnv).d);
|
||||
}
|
||||
|
||||
JSValue remainder(Environment theEnv, JSValue rV) {
|
||||
return new JSDouble(d % rV.toJSDouble(theEnv).d);
|
||||
}
|
||||
|
||||
JSValue gt(Environment theEnv, JSValue rV) {
|
||||
return (d > rV.toJSDouble(theEnv).d) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
}
|
||||
|
||||
JSValue ge(Environment theEnv, JSValue rV) {
|
||||
return (d >= rV.toJSDouble(theEnv).d) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
}
|
||||
|
||||
JSValue lt(Environment theEnv, JSValue rV) {
|
||||
return (d < rV.toJSDouble(theEnv).d) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
}
|
||||
|
||||
JSValue le(Environment theEnv, JSValue rV) {
|
||||
return (d <= rV.toJSDouble(theEnv).d) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
}
|
||||
|
||||
JSValue eq(Environment theEnv, JSValue rV) {
|
||||
return (d == rV.toJSDouble(theEnv).d) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
}
|
||||
|
||||
JSValue ne(Environment theEnv, JSValue rV) {
|
||||
return (d != rV.toJSDouble(theEnv).d) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
}
|
||||
|
||||
JSDouble toJSDouble(Environment theEnv) {
|
||||
return this;
|
||||
}
|
||||
|
||||
JSValue toPrimitive(Environment theEnv, String hint) {
|
||||
return this;
|
||||
}
|
||||
|
||||
JSInteger toJSInteger(Environment theEnv) {
|
||||
return new JSInteger((int)d);
|
||||
}
|
||||
|
||||
JSBoolean toJSBoolean(Environment theEnv) {
|
||||
return ((d == d) && (d != 0.0)) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
}
|
||||
|
||||
JSString toJSString(Environment theEnv) {
|
||||
return new JSString(Double.toString(d));
|
||||
}
|
||||
|
||||
JSObject toJSObject(Environment theEnv) {
|
||||
return new NativeNumber(d);
|
||||
}
|
||||
|
||||
|
||||
|
||||
double d;
|
||||
|
||||
}
|
||||
@@ -1,22 +0,0 @@
|
||||
|
||||
|
||||
class JSException extends RuntimeException {
|
||||
|
||||
JSException(JSValue x)
|
||||
{
|
||||
value = x;
|
||||
}
|
||||
|
||||
JSValue getValue()
|
||||
{
|
||||
return value;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return value.toJSString(null).s;
|
||||
}
|
||||
|
||||
JSValue value;
|
||||
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,23 +0,0 @@
|
||||
class JSIdentifier extends JSString {
|
||||
|
||||
JSIdentifier(String s)
|
||||
{
|
||||
super(s);
|
||||
}
|
||||
|
||||
String print(String indent)
|
||||
{
|
||||
return indent + "JSIdentifier : " + s + "\n";
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
return theEnv.scope.getProp(theEnv, this);
|
||||
}
|
||||
|
||||
JSReference evalLHS(Environment theEnv)
|
||||
{
|
||||
return new JSReference(theEnv.scope, this);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,68 +0,0 @@
|
||||
class JSInteger extends JSNumber {
|
||||
|
||||
JSInteger(String s)
|
||||
{
|
||||
i = new Integer(s).intValue();
|
||||
}
|
||||
|
||||
JSInteger(int p)
|
||||
{
|
||||
i = p;
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
return this;
|
||||
}
|
||||
|
||||
JSBoolean toJSBoolean(Environment theEnv) {
|
||||
return (i != 0) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
}
|
||||
|
||||
JSDouble toJSDouble(Environment theEnv) {
|
||||
return new JSDouble(i);
|
||||
}
|
||||
|
||||
JSInteger toJSInteger(Environment theEnv) {
|
||||
return this;
|
||||
}
|
||||
|
||||
JSValue toPrimitive(Environment theEnv, String hint) {
|
||||
return this;
|
||||
}
|
||||
|
||||
JSString toJSString(Environment theEnv) {
|
||||
return new JSString(Integer.toString(i));
|
||||
}
|
||||
|
||||
JSValue twiddle(Environment theEnv) {
|
||||
return new JSInteger(~i);
|
||||
}
|
||||
|
||||
JSValue and(Environment theEnv, JSValue rV) {
|
||||
return new JSInteger(i & rV.toJSInteger(theEnv).i);
|
||||
}
|
||||
|
||||
JSValue or(Environment theEnv, JSValue rV) {
|
||||
return new JSInteger(i | rV.toJSInteger(theEnv).i);
|
||||
}
|
||||
|
||||
JSValue xor(Environment theEnv, JSValue rV) {
|
||||
return new JSInteger(i ^ rV.toJSInteger(theEnv).i);
|
||||
}
|
||||
|
||||
JSValue shl(Environment theEnv, JSValue rV) {
|
||||
return new JSInteger(i >> rV.toJSInteger(theEnv).i);
|
||||
}
|
||||
|
||||
JSValue shr(Environment theEnv, JSValue rV) {
|
||||
return new JSInteger(i << rV.toJSInteger(theEnv).i);
|
||||
}
|
||||
|
||||
JSValue ushl(Environment theEnv, JSValue rV) {
|
||||
return new JSInteger(i >>> rV.toJSInteger(theEnv).i);
|
||||
}
|
||||
|
||||
int i;
|
||||
|
||||
}
|
||||
@@ -1,41 +0,0 @@
|
||||
class JSName extends ExpressionNode {
|
||||
|
||||
JSName(JSIdentifier anID, int aScope)
|
||||
{
|
||||
id = anID;
|
||||
scope = aScope; // this is the scope that the name was used in
|
||||
}
|
||||
|
||||
String print(String indent)
|
||||
{
|
||||
return indent + "JSName : " + id.s + ", scope : " + scope + "\n";
|
||||
}
|
||||
|
||||
JSReference evalLHS(Environment theEnv)
|
||||
{
|
||||
JSScope scope = theEnv.scope;
|
||||
while (scope != null) {
|
||||
if (scope.hasProp(theEnv, id))
|
||||
return new JSReference(scope, id);
|
||||
else
|
||||
scope = scope.parent;
|
||||
}
|
||||
return new JSReference(theEnv.globalScope, id);
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
JSScope scope = theEnv.scope;
|
||||
while (scope != null) {
|
||||
if (scope.hasProp(theEnv, id))
|
||||
return scope.getProp(theEnv, id);
|
||||
else
|
||||
scope = scope.parent;
|
||||
}
|
||||
throw new JSException(new JSString(id.s + " undefined"));
|
||||
}
|
||||
|
||||
JSIdentifier id;
|
||||
int scope;
|
||||
|
||||
}
|
||||
@@ -1,8 +0,0 @@
|
||||
abstract class JSNumber extends JSValue {
|
||||
|
||||
JSValue typeof(Environment theEnv) {
|
||||
return new JSString("number");
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -1,84 +0,0 @@
|
||||
|
||||
import java.util.Hashtable;
|
||||
|
||||
class JSObject extends JSValue {
|
||||
|
||||
static JSObject objectPrototype = new JSObject("Object");
|
||||
static JSObject JSUndefined = new JSObject("undefined");
|
||||
|
||||
JSObject(String aClass)
|
||||
{
|
||||
oClass = aClass;
|
||||
prototype = objectPrototype;
|
||||
}
|
||||
|
||||
void setPrototype(JSObject aPrototype)
|
||||
{
|
||||
prototype = aPrototype;
|
||||
}
|
||||
|
||||
String print(String indent)
|
||||
{
|
||||
return indent + "JSObject : " + oClass + "\n";
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return oClass + contents.toString();
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
return this;
|
||||
}
|
||||
|
||||
JSValue typeof(Environment theEnv) {
|
||||
if (this == JSUndefined)
|
||||
return new JSString("undefined");
|
||||
else
|
||||
return new JSString("object");
|
||||
}
|
||||
|
||||
JSBoolean toJSBoolean(Environment theEnv) {
|
||||
return JSBoolean.JSTrue;
|
||||
}
|
||||
|
||||
JSDouble toJSDouble(Environment theEnv) {
|
||||
return toPrimitive(theEnv, "Number").toJSDouble(theEnv);
|
||||
}
|
||||
|
||||
JSValue getProp(Environment theEnv, JSString id)
|
||||
{
|
||||
Object v = contents.get(id.s);
|
||||
if (v == null)
|
||||
if (prototype == null)
|
||||
return JSUndefined;
|
||||
else
|
||||
return prototype.getProp(theEnv, id);
|
||||
else
|
||||
return (JSValue)v;
|
||||
}
|
||||
|
||||
boolean hasProp(Environment theEnv, JSString id)
|
||||
{
|
||||
Object v = contents.get(id.s);
|
||||
if (v == null)
|
||||
if (prototype == null)
|
||||
return false;
|
||||
else
|
||||
return prototype.hasProp(theEnv, id);
|
||||
else
|
||||
return true;
|
||||
}
|
||||
|
||||
JSValue putProp(Environment theEnv, JSString id, JSValue rV) {
|
||||
contents.put(id.s, rV);
|
||||
return rV;
|
||||
}
|
||||
|
||||
|
||||
Hashtable contents = new Hashtable();
|
||||
|
||||
String oClass;
|
||||
|
||||
JSObject prototype;
|
||||
}
|
||||
@@ -1,12 +0,0 @@
|
||||
class JSReference {
|
||||
|
||||
JSReference(JSValue aBase, JSString aID)
|
||||
{
|
||||
base = aBase;
|
||||
id = aID;
|
||||
}
|
||||
|
||||
JSValue base;
|
||||
JSString id;
|
||||
|
||||
}
|
||||
@@ -1,10 +0,0 @@
|
||||
class JSScope extends JSObject {
|
||||
|
||||
JSScope(String s)
|
||||
{
|
||||
super(s);
|
||||
}
|
||||
|
||||
JSScope parent;
|
||||
|
||||
}
|
||||
@@ -1,83 +0,0 @@
|
||||
class JSString extends JSValue {
|
||||
|
||||
JSString(String p)
|
||||
{
|
||||
s = p;
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
return this;
|
||||
}
|
||||
|
||||
JSValue typeof(Environment theEnv) {
|
||||
return new JSString("string");
|
||||
}
|
||||
|
||||
JSValue add(Environment theEnv, JSValue rV)
|
||||
{
|
||||
return new JSString(s + rV.toJSString(theEnv).s);
|
||||
}
|
||||
|
||||
JSValue gt(Environment theEnv, JSValue rV) {
|
||||
if (rV instanceof JSString)
|
||||
return (s.compareTo(rV.toJSString(theEnv).s) == 1) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
else
|
||||
return toJSDouble(theEnv).gt(theEnv, rV);
|
||||
}
|
||||
|
||||
JSValue ge(Environment theEnv, JSValue rV) {
|
||||
if (rV instanceof JSString)
|
||||
return (s.compareTo(rV.toJSString(theEnv).s) != -1) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
else
|
||||
return toJSDouble(theEnv).ge(theEnv, rV);
|
||||
}
|
||||
|
||||
JSValue lt(Environment theEnv, JSValue rV) {
|
||||
if (rV instanceof JSString)
|
||||
return (s.compareTo(rV.toJSString(theEnv).s) == -1) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
else
|
||||
return toJSDouble(theEnv).lt(theEnv, rV);
|
||||
}
|
||||
|
||||
JSValue le(Environment theEnv, JSValue rV) {
|
||||
if (rV instanceof JSString)
|
||||
return (s.compareTo(rV.toJSString(theEnv).s) != 1) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
else
|
||||
return toJSDouble(theEnv).le(theEnv, rV);
|
||||
}
|
||||
|
||||
JSValue eq(Environment theEnv, JSValue rV) {
|
||||
if (rV instanceof JSString)
|
||||
return (s.compareTo(rV.toJSString(theEnv).s) == 0) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
else
|
||||
return toJSDouble(theEnv).eq(theEnv, rV);
|
||||
}
|
||||
|
||||
JSValue ne(Environment theEnv, JSValue rV) {
|
||||
if (rV instanceof JSString)
|
||||
return (s.compareTo(rV.toJSString(theEnv).s) != 0) ? JSBoolean.JSTrue : JSBoolean.JSFalse;
|
||||
else
|
||||
return toJSDouble(theEnv).ne(theEnv, rV);
|
||||
}
|
||||
|
||||
JSDouble toJSDouble(Environment theEnv) {
|
||||
return new JSDouble(s); // XXX Way More To Do, see Rhino ScriptRuntime.java
|
||||
}
|
||||
|
||||
JSString toJSString(Environment theEnv) {
|
||||
return this;
|
||||
}
|
||||
|
||||
JSValue toPrimitive(Environment theEnv, String hint) {
|
||||
return this;
|
||||
}
|
||||
|
||||
String print(String indent)
|
||||
{
|
||||
return indent + "JSString : " + s + "\n";
|
||||
}
|
||||
|
||||
protected String s;
|
||||
|
||||
}
|
||||
@@ -1,222 +0,0 @@
|
||||
class JSValue extends ExpressionNode {
|
||||
|
||||
String print(String indent)
|
||||
{
|
||||
return indent + "JSValue\n";
|
||||
}
|
||||
|
||||
JSReference evalLHS(Environment theEnv)
|
||||
{
|
||||
throw new RuntimeException("EvalLHS on non-lvalue");
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
throw new RuntimeException("Eval on JSValue");
|
||||
}
|
||||
|
||||
JSValue unimplemented(String op)
|
||||
{
|
||||
throw new RuntimeException("unimplemented " + op + " called");
|
||||
}
|
||||
|
||||
JSValue gt(Environment theEnv, JSValue rV) {
|
||||
JSValue lV = toPrimitive(theEnv, "Number");
|
||||
rV = rV.toPrimitive(theEnv, "Number");
|
||||
if ((lV instanceof JSString) && (rV instanceof JSString))
|
||||
return lV.gt(theEnv, rV);
|
||||
else
|
||||
return lV.toJSDouble(theEnv).gt(theEnv, rV.toJSDouble(theEnv));
|
||||
}
|
||||
|
||||
JSValue ge(Environment theEnv, JSValue rV) {
|
||||
JSValue lV = toPrimitive(theEnv, "Number");
|
||||
rV = rV.toPrimitive(theEnv, "Number");
|
||||
if ((lV instanceof JSString) && (rV instanceof JSString))
|
||||
return lV.ge(theEnv, rV);
|
||||
else
|
||||
return lV.toJSDouble(theEnv).ge(theEnv, rV.toJSDouble(theEnv));
|
||||
}
|
||||
|
||||
JSValue lt(Environment theEnv, JSValue rV) {
|
||||
JSValue lV = toPrimitive(theEnv, "Number");
|
||||
rV = rV.toPrimitive(theEnv, "Number");
|
||||
if ((lV instanceof JSString) && (rV instanceof JSString))
|
||||
return lV.lt(theEnv, rV);
|
||||
else
|
||||
return lV.toJSDouble(theEnv).lt(theEnv, rV.toJSDouble(theEnv));
|
||||
}
|
||||
|
||||
JSValue le(Environment theEnv, JSValue rV) {
|
||||
JSValue lV = toPrimitive(theEnv, "Number");
|
||||
rV = rV.toPrimitive(theEnv, "Number");
|
||||
if ((lV instanceof JSString) && (rV instanceof JSString))
|
||||
return lV.le(theEnv, rV);
|
||||
else
|
||||
return lV.toJSDouble(theEnv).le(theEnv, rV.toJSDouble(theEnv));
|
||||
}
|
||||
|
||||
JSValue eq(Environment theEnv, JSValue rV) {
|
||||
JSValue lV = toPrimitive(theEnv, "Number");
|
||||
rV = rV.toPrimitive(theEnv, "Number");
|
||||
if ((lV instanceof JSString) && (rV instanceof JSString))
|
||||
return lV.eq(theEnv, rV);
|
||||
else
|
||||
return lV.toJSDouble(theEnv).eq(theEnv, rV.toJSDouble(theEnv));
|
||||
}
|
||||
|
||||
JSValue ne(Environment theEnv, JSValue rV) {
|
||||
JSValue lV = toPrimitive(theEnv, "Number");
|
||||
rV = rV.toPrimitive(theEnv, "Number");
|
||||
if ((lV instanceof JSString) && (rV instanceof JSString))
|
||||
return lV.ne(theEnv, rV);
|
||||
else
|
||||
return lV.toJSDouble(theEnv).ne(theEnv, rV.toJSDouble(theEnv));
|
||||
}
|
||||
|
||||
JSValue plus(Environment theEnv) {
|
||||
return toJSDouble(theEnv).plus(theEnv);
|
||||
}
|
||||
|
||||
JSValue minus(Environment theEnv) {
|
||||
return toJSDouble(theEnv).minus(theEnv);
|
||||
}
|
||||
|
||||
JSValue twiddle(Environment theEnv) {
|
||||
return toJSInteger(theEnv).twiddle(theEnv);
|
||||
}
|
||||
|
||||
JSValue bang(Environment theEnv) {
|
||||
return toJSBoolean(theEnv).bang(theEnv);
|
||||
}
|
||||
|
||||
JSValue typeof(Environment theEnv) {
|
||||
return unimplemented("typeof");
|
||||
}
|
||||
|
||||
JSValue add(Environment theEnv, JSValue rV) {
|
||||
JSValue lV = toPrimitive(theEnv, "");
|
||||
rV = rV.toPrimitive(theEnv, "");
|
||||
if ((lV instanceof JSString) || (rV instanceof JSString))
|
||||
return lV.add(theEnv, rV);
|
||||
else
|
||||
return lV.toJSDouble(theEnv).add(theEnv, rV);
|
||||
}
|
||||
|
||||
JSValue subtract(Environment theEnv, JSValue rV) {
|
||||
return toJSDouble(theEnv).subtract(theEnv, rV.toJSDouble(theEnv));
|
||||
}
|
||||
|
||||
JSValue multiply(Environment theEnv, JSValue rV) {
|
||||
return toJSDouble(theEnv).multiply(theEnv, rV.toJSDouble(theEnv));
|
||||
}
|
||||
|
||||
JSValue divide(Environment theEnv, JSValue rV) {
|
||||
return toJSDouble(theEnv).divide(theEnv, rV.toJSDouble(theEnv));
|
||||
}
|
||||
|
||||
JSValue remainder(Environment theEnv, JSValue rV) {
|
||||
return toJSDouble(theEnv).remainder(theEnv, rV.toJSDouble(theEnv));
|
||||
}
|
||||
|
||||
JSValue and(Environment theEnv, JSValue rV) {
|
||||
return toJSInteger(theEnv).and(theEnv, rV.toJSInteger(theEnv));
|
||||
}
|
||||
|
||||
JSValue or(Environment theEnv, JSValue rV) {
|
||||
return toJSInteger(theEnv).or(theEnv, rV.toJSInteger(theEnv));
|
||||
}
|
||||
|
||||
JSValue xor(Environment theEnv, JSValue rV) {
|
||||
return toJSInteger(theEnv).xor(theEnv, rV.toJSInteger(theEnv));
|
||||
}
|
||||
|
||||
JSValue shl(Environment theEnv, JSValue rV) {
|
||||
return toJSInteger(theEnv).shl(theEnv, rV.toJSInteger(theEnv));
|
||||
}
|
||||
|
||||
JSValue shr(Environment theEnv, JSValue rV) {
|
||||
return toJSInteger(theEnv).shr(theEnv, rV.toJSInteger(theEnv));
|
||||
}
|
||||
|
||||
JSValue ushl(Environment theEnv, JSValue rV) {
|
||||
return toJSInteger(theEnv).ushl(theEnv, rV.toJSInteger(theEnv));
|
||||
}
|
||||
|
||||
JSValue getProp(Environment theEnv, JSString id) {
|
||||
return toJSObject(theEnv).getProp(theEnv, id);
|
||||
}
|
||||
|
||||
boolean hasProp(Environment theEnv, JSString id) {
|
||||
return toJSObject(theEnv).hasProp(theEnv, id);
|
||||
}
|
||||
|
||||
JSValue putProp(Environment theEnv, JSString id, JSValue rV) {
|
||||
return toJSObject(theEnv).putProp(theEnv, id, rV);
|
||||
}
|
||||
|
||||
JSValue call(Environment theEnv, JSValue rV) {
|
||||
throw new JSException(new JSString("[[call]] not implemented"));
|
||||
}
|
||||
|
||||
JSValue defaultValue(Environment theEnv, String hint) {
|
||||
/*
|
||||
When the [[DefaultValue]] method of O is called with hint String, the following steps are taken:
|
||||
1. Call the [[Get]] method of object O with argument "toString".
|
||||
2. If Result(1) is not an object, go to step 5.
|
||||
3. Call the [[Call]] method of Result(1), with O as the this value and an empty argument list.
|
||||
4. If Result(3) is a primitive value, return Result(3).
|
||||
5. Call the [[Get]] method of object O with argument "valueOf".
|
||||
6. If Result(5) is not an object, go to step 9.
|
||||
7. Call the [[Call]] method of Result(5), with O as the this value and an empty argument list.
|
||||
8. If Result(7) is a primitive value, return Result(7).
|
||||
9. Generate a runtime error.
|
||||
*/
|
||||
JSValue v = null;
|
||||
if (hint.equals("String")) {
|
||||
v = getProp(theEnv, new JSString("toString"));
|
||||
if (v instanceof JSObject) {
|
||||
// invoke 'v.Call' with 'this' as the JS this
|
||||
}
|
||||
else {
|
||||
v = getProp(theEnv, new JSString("valueOf"));
|
||||
if (v instanceof JSObject) {
|
||||
}
|
||||
else
|
||||
throw new JSException(new JSString("No default value"));
|
||||
}
|
||||
}
|
||||
else { // hint.equals("Number")
|
||||
/*
|
||||
When the [[DefaultValue]] method of O is called with hint Number, the following steps are taken:
|
||||
1. Call the [[Get]] method of object O with argument "valueOf".
|
||||
2. If Result(1) is not an object, go to step 5.
|
||||
3. Call the [[Call]] method of Result(1), with O as the this value and an empty argument list.
|
||||
4. If Result(3) is a primitive value, return Result(3).
|
||||
5. Call the [[Get]] method of object O with argument "toString".
|
||||
6. If Result(5) is not an object, go to step 9.
|
||||
7. Call the [[Call]] method of Result(5), with O as the this value and an empty argument list.
|
||||
8. If Result(7) is a primitive value, return Result(7).
|
||||
9. Generate a runtime error.
|
||||
*/
|
||||
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
JSValue toPrimitive(Environment theEnv, String hint) {
|
||||
JSValue result = defaultValue(theEnv, hint);
|
||||
if (result instanceof JSObject)
|
||||
throw new JSException(new JSString("default value returned object"));
|
||||
else
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
JSObject toJSObject(Environment theEnv) { unimplemented("toJSObjet"); return null; }
|
||||
JSDouble toJSDouble(Environment theEnv) { unimplemented("toJSDouble"); return null; }
|
||||
JSInteger toJSInteger(Environment theEnv) { unimplemented("toJSInteger"); return null; }
|
||||
JSString toJSString(Environment theEnv) { unimplemented("toJSString"); return null; }
|
||||
JSBoolean toJSBoolean(Environment theEnv) { unimplemented("toJSBoolean"); return null; }
|
||||
|
||||
}
|
||||
@@ -1,40 +0,0 @@
|
||||
|
||||
import java.util.Vector;
|
||||
|
||||
class JSValueList extends JSValue {
|
||||
|
||||
static JSValueList buildList(JSValue left, JSValue right)
|
||||
{
|
||||
JSValueList theList;
|
||||
if (left instanceof JSValueList) {
|
||||
theList = (JSValueList)left;
|
||||
theList.add(right);
|
||||
}
|
||||
else
|
||||
if (right instanceof JSValueList) {
|
||||
theList = (JSValueList)right;
|
||||
theList.add(left);
|
||||
}
|
||||
else {
|
||||
theList = new JSValueList();
|
||||
theList.add(left);
|
||||
theList.add(right);
|
||||
}
|
||||
|
||||
return theList;
|
||||
}
|
||||
|
||||
void add(JSValue v)
|
||||
{
|
||||
if (v instanceof JSValueList) {
|
||||
JSValueList vl = (JSValueList)v;
|
||||
for (int i = 0; i < vl.contents.size(); i++)
|
||||
contents.addElement((JSValue)(vl.contents.elementAt(i)));
|
||||
}
|
||||
else
|
||||
contents.addElement(v);
|
||||
}
|
||||
|
||||
Vector contents = new Vector();
|
||||
|
||||
}
|
||||
@@ -1,39 +0,0 @@
|
||||
class LogicalNode extends BinaryNode {
|
||||
|
||||
LogicalNode(String aOp, ExpressionNode aLeft, ExpressionNode aRight)
|
||||
{
|
||||
super(aOp, aLeft, aRight);
|
||||
}
|
||||
|
||||
JSValue eval(Environment theEnv)
|
||||
{
|
||||
JSBoolean b = left.eval(theEnv).toJSBoolean(theEnv);
|
||||
if (op == "&&") {
|
||||
if (b.isFalse())
|
||||
return b;
|
||||
else {
|
||||
b = right.eval(theEnv).toJSBoolean(theEnv);
|
||||
if (b.isFalse())
|
||||
return b;
|
||||
else
|
||||
return JSBoolean.JSTrue;
|
||||
}
|
||||
}
|
||||
if (op == "||") {
|
||||
if (b.isTrue())
|
||||
return b;
|
||||
else {
|
||||
b = right.eval(theEnv).toJSBoolean(theEnv);
|
||||
if (b.isTrue())
|
||||
return b;
|
||||
else
|
||||
return JSBoolean.JSFalse;
|
||||
}
|
||||
}
|
||||
else {
|
||||
System.out.println("missing logical op " + op);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user