United StatesChange Country, Oracle Worldwide Web Sites Communities I am a... I want to...
JDK-4674826 : REGRESSION: java.net.Socket constructor throws security exception

Details
Type:
Bug
Submit Date:
2002-04-25
Status:
Resolved
Updated Date:
2005-05-11
Project Name:
JDK
Resolved Date:
2002-09-24
Component:
core-libs
OS:
windows_2000
Sub-Component:
java.net
CPU:
x86
Priority:
P3
Resolution:
Fixed
Affected Versions:
1.4.0,1.4.1_01
Fixed Versions:
1.4.1_03 (03)

Related Reports
Backport:
Relates:

Sub Tasks

Description
Name: gm110360			Date: 04/25/2002

FULL PRODUCT VERSION :
java version "1.4.0"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.0-b92)
Java HotSpot(TM) Client VM (build 1.4.0-b92, mixed mode)

FULL OPERATING SYSTEM VERSION :
Microsoft Windows 2000 [Version 5.00.2195]

A DESCRIPTION OF THE PROBLEM :
When creating a subclass of java.net.Socket and passing a
custom java.net.SocketImpl to the super constructor, this
constructor tries to find out if it gets an old or a new
java.net.SocketImpl by calling java.net.Socket#checkOldImpl.
This method in turn calls getDeclaredMethod, which fires the
SecurityException.

The reason for the check is because java.net.SocketImpl
changed in 1.4. But since the check itself fires the
exception, it doesn't matter if an old or new version is
provided.

This makes it impossible to create and use SocketImpl
subclasses.

REGRESSION.  Last worked in version 1.3

STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
1. Create a subclass of java.net.SocketImpl
2. Create a subclass of java.net.Socket, passing the
subclass from step one to the super constructor.
3. In an applet, try to create an instance of the subclass
from step two.

EXPECTED VERSUS ACTUAL BEHAVIOR :
A java.security.AccessControlException is thrown.

ERROR MESSAGES/STACK TRACES THAT OCCUR :
java.security.AccessControlException: access denied (java.lang.RuntimePermission
accessDeclaredMembers)
 at
java.security.AccessControlContext.checkPermission(AccessControlContext.java:270)
 at java.security.AccessController.checkPermission(AccessController.java:401)
 at java.lang.SecurityManager.checkPermission(SecurityManager.java:542)
 at java.lang.SecurityManager.checkMemberAccess(SecurityManager.java:1662)
 at java.lang.Class.checkMemberAccess(Class.java:1401)
 at java.lang.Class.getDeclaredMethod(Class.java:1218)
 at java.net.Socket.checkOldImpl(Socket.java:323)
 at java.net.Socket.<init>(Socket.java:83)
 at SocketApplet$FunkySocket.<init>(SocketApplet.java:50)
 at SocketApplet.init(SocketApplet.java:57)
 at sun.applet.AppletPanel.run(AppletPanel.java:341)
 at java.lang.Thread.run(Thread.java:536)


This bug can be reproduced always.

---------- BEGIN SOURCE ----------
import java.applet.Applet;
import java.io.*;
import java.net.*;

/**
 * Simple Applet for exposing the Socket constructor
 * bug.
 */
public class SocketApplet extends Applet {

    /**
     * A no-op SocketImpl descendant.
     */
    class FunkySocketImpl extends SocketImpl {
	protected void accept(SocketImpl impl) throws IOException {
	}

	protected int available(){
	    return 0;
	}

	protected void bind(InetAddress host, int port){
	}

	protected void close(){
	}

	protected void connect(InetAddress address, int port){
	}

	protected void connect(String host, int port){
	}

	/**
	 * This version of connect is only compilable on
	 * 1.4, since it has SocketAddress in the parameter
	 * list.
	protected void connect(SocketAddress a,int b){
	}
	*/

	protected void create(boolean stream){
	}

	protected InputStream getInputStream(){
	    return null;
	}

	protected OutputStream getOutputStream(){
	    return null;
	}

	protected void listen(int backlog){
	}

	public Object getOption(int optID){
	    return null;
	}

	public void setOption(int optID, Object value){
	}

	protected void sendUrgentData(int i){
	}
    }

    /**
     * A no-op Socket descendant.
     */
    class FunkySocket extends Socket {
	public FunkySocket(SocketImpl impl) throws IOException {
	    super(impl);
	}
    }

    /**
     * Our test case entrypoint. Generates
     * a SecurityException.
     */
    public void init(){
	FunkySocketImpl socketImpl = new FunkySocketImpl();
	try{
	    FunkySocket socko = new FunkySocket(socketImpl);
	}catch(IOException ioex){
	    System.err.println(ioex);
	}
    }
}

---------- END SOURCE ----------

Release Regression From : 1.3.1_02
The above release value was the last known release where this 
bug was known to work. Since then there has been a regression.

(Review ID: 145584) 
======================================================================


###@###.### 2003-02-21

We have some code that creates special 
kinds of outbound socket using our own impl. Unfortunately the JDK's 
(1.4.1_01) version of Socket does this:

     private void checkOldImpl() {
	if (impl == null)
	    return;
	Class[] cl = new Class[2];
	cl[0] = SocketAddress.class;
	cl[1] = Integer.TYPE;
	try {
	    impl.getClass().getDeclaredMethod("connect", cl);
	} catch (NoSuchMethodException e) {
	    oldImpl = true;
	}
     }

and getDeclaredMethod is not allowed in an applet. This seems like a clear 
bug to me since this code is only for backwards compatibility anyway.
###@###.### 2005-05-11 03:58:08 GMT
###@###.### 2005-05-11 03:58:14 GMT

                                    

Comments
CONVERTED DATA

BugTraq+ Release Management Values

COMMIT TO FIX:
1.4.1_03
mantis

FIXED IN:
1.4.1_03
mantis

INTEGRATED IN:
1.4.1_03
mantis

VERIFIED IN:
mantis-beta


                                     
2004-06-14
EVALUATION

This is a classes_net bug.

###@###.### 2002-04-26

As this is a regression for custom impls it should be examined for
hopper-beta.
###@###.### 2002-04-29

There is a doPrivileged clause missing in the code. This is rather simple to fix. Will fix for hopper-betta.

###@###.### 2002-04-29
                                     
2002-04-29



Hardware and Software, Engineered to Work Together