Socket concurrency
Howdy all!
Is it possible for two threads to be using the same socket at the same time - where one is just writing to the socket's OutputStream and the other is just reading from the socket's InputStream - and for the same to be happenning on the other end (so both client and server have reader and writer threads attached to the socket)?
Thanks!
Rob
:)
Yes it is possible. You start one thread to do listening/reading on the socket and another thread to write to the socket's stream. It can be done the same way by both server and client programs.
Cheers!
Similar Messages
-
Non-blocking socket concurrent limitation?
I have 2 socket program,one is server side used nio package with JDK1.4.1,the other is client used traditional socket,the client will initialize about 50
threads trying to connect with server when starting,but only about 15
can be accepted,these 2 program are runnning in the same computer which
OS is win2000 professional PC.
the followd is these code:
please make a probe with them ,and tell me what's going on?
server:
package nio_select_demo;
import java.io.*;
import java.net.*;
import java.nio.*;
import java.nio.channels.*;
import java.util.*;
import java.nio.charset.Charset;
import java.nio.charset.CharsetDecoder;
public class Server implements Runnable
// The port we will listen on
private int port;
// A pre-allocated buffer for processing data
private final ByteBuffer buffer = ByteBuffer.allocate( 16384 );
private ByteBuffer resBuf = ByteBuffer.allocate( 128 );
Selector selector;
AddInfo test ;
public Server( int port ) {
this.port = port;
// for (int i=0; i<threadnum; ++i) {
new Thread( this ).start();
test = new AddInfo();
test.start();
public void run() {
try {
// create a ServerSocketChannel
ServerSocketChannel ssc1 = ServerSocketChannel.open();
// ServerSocketChannel ssc2 = ServerSocketChannel.open();
// Set it to non-blocking
ssc1.configureBlocking( false );
// Get the Socket connected to this channel, and bind it
// to the listening port
ServerSocket ss = ssc1.socket();
InetSocketAddress isa = new InetSocketAddress( port );
ss.bind( isa , 60 );
// Create a new Selector for selecting
selector = Selector.open();
// Register the ServerSocketChannel, so we can
// listen for incoming connections
ssc1.register( selector, SelectionKey.OP_ACCEPT );
System.out.println( "Listening on port "+port );
int n = 0;
while (true) {
// See if we've had any activity -- either
// an incoming connection, or incoming data on an
// existing connection
int num = selector.select();
// If we don't have any activity, loop around and wait
// again
if (num == 0) {
continue;
// Get the keys corresponding to the activity
// that has been detected, and process them
// one by one
Set keys = selector.selectedKeys();
Iterator it = keys.iterator();
while (it.hasNext()) {
// Get a key representing one of bits of I/O
// activity
SelectionKey key = (SelectionKey)it.next();
// What kind of activity is it?
if ((key.readyOps() & SelectionKey.OP_ACCEPT) ==
SelectionKey.OP_ACCEPT) {
System.out.println( "accept request" );
// It's an incoming connection.
// Register this socket with the Selector
// so we can listen for input on it
SocketChannel sc = ((ServerSocketChannel)key.channel()).accept();
System.out.println( "Got connection from "+sc.socket());
// Make sure to make it non-blocking, so we can
// use a selector on it.
//SocketChannel sc = s.getChannel();
sc.configureBlocking( false );
// Register it with the selector, for reading
sc.register( selector, SelectionKey.OP_READ| SelectionKey.OP_WRITE);
} else if ((key.readyOps() & SelectionKey.OP_READ) ==
SelectionKey.OP_READ) {
//ssc.register(selector , SelectionKey.OP_READ);
SocketChannel sc = null;
try {
// It's incoming data on a connection, so
// process it
sc = (SocketChannel)key.channel();
Socket s1 = sc.socket();
s1.setTcpNoDelay(true);
System.out.println( "enter processing data" );
boolean ok = processInput( key );
synchronized (selector) {
key.interestOps(key.interestOps() & ~SelectionKey.OP_READ);
// If the connection is dead, then remove it
// from the selector and close it
if (!ok) {
key.cancel();
System.out.println("dead");
Socket s = null;
try {
s = sc.socket();
s.close();
} catch( IOException ie ) {
System.err.println( "Error closing socket "+s+": "+ie );
} catch( IOException ie ) {
ie.printStackTrace();
// On exception, remove this channel from the selector
key.cancel();
System.err.println( "Error raised in this socket");
try {
sc.close();
} catch( IOException ie2 ) { System.out.println( ie2 ); }
System.out.println( "Closed "+sc );
else if ((key.readyOps() & SelectionKey.OP_WRITE) ==
SelectionKey.OP_WRITE) {
System.out.println("Enter Writing");
String response = new String();
if((response=this.test.getInfo())!=null){
resBuf.clear();
SocketChannel sc = (SocketChannel)key.channel();
resBuf = ByteBuffer.wrap( response.getBytes("ISO-8859-1" ) );
sc.write( resBuf );
synchronized (selector) {
key.interestOps(key.interestOps() & ~SelectionKey.OP_WRITE);
// We remove the selected keys, because we've dealt
// with them.
keys.clear();
} catch( IOException ie ) {
System.err.println( ie );
private boolean processInput( SelectionKey key ) throws IOException {
buffer.clear();
SocketChannel sc = (SocketChannel)key.channel();
sc.read( buffer );
buffer.flip();
String response = new String("response ok");
// If no data, close the connection
if (buffer.limit()==0) {
return false;
Charset charset=Charset.forName("ISO-8859-1");
CharsetDecoder decoder = charset.newDecoder();
CharBuffer charBuffer = decoder.decode(buffer);
System.out.println(charBuffer.toString());
System.out.println( "Processed "+buffer.limit()+" from "+sc );
return true;
static public void main( String args[] ) throws Exception {
int port = Integer.parseInt( args[0] );
System.out.println(port);
new Server( port );
cilent:
import java.io.*;
import java.net.*;
import java.util.*;
public class Client implements Runnable
private String host;
private int port;
private int acport;
//the size of buffer on how much we write and read per cycle
private static final int maxWriteSize = 128;
public Client( String host, int port, int numThreads ) {
this.host = host;
this.port = port;
for(int i =0;i<50;i++){//initialize 50 client threads
new Thread(this).start();
public void run() {
byte buffer[] = new byte[maxWriteSize];
byte buffer2[] = new byte[maxWriteSize];
try {
Socket s = new Socket( );
InetSocketAddress sa = new InetSocketAddress(host,this.port);
s.connect(sa);
System.out.println(s);
s.setTcpNoDelay(true);
InputStream in = s.getInputStream();
OutputStream out = s.getOutputStream();
for (int i=0; i<maxWriteSize; ++i) {
buffer[i] = (byte)'a';
out.write( buffer, 0, maxWriteSize );
int pause = 500;
in.read( buffer , 0 , maxWriteSize );
System.out.println( Thread.currentThread()+" wrote "+maxWriteSize);
String res = new String ( buffer );
String res2 = new String ( buffer2 );
System.out.println( res );
try { Thread.sleep( pause ); } catch( InterruptedException ie ) {}
} catch( Exception ie ) {
ie.printStackTrace();
System.err.println(ie.getMessage());
static public void main( String args[] ) throws Exception {
String host = "127.0.0.1";
int port = Integer.parseInt( args[0] );
int numThreads = Integer.parseInt( args[1] );
new Client( host, port, numThreads );I have found the reason!!!
because of system resource limitation,windows can't afford to maintain
so many concurrent stream-IO,so some socket will be closed.
I modified the client side code,adding thes segments to client instantialize
such as :
public Client( String host, int port, int numThreads ) {
for(int i =0;i<1000;i++){
new Thread(this).start();
try {
Thread.currentThread().sleep(100);//give system some idle
} catch (InterruptedException e) {
/* ignore */
then the server can accept more than 1000 client request concurrently. -
We sometimes see this failure intermitently when using the FlexUnit Ant task to run tests in a CI environment. The Ant task throws this exception:
java.util.concurrent.ExecutionException: could not close client/server socket
I have seen this for a while now, and still see it with the latest 4.1 RC versions.
Here is the console output seen along with the above exception:
FlexUnit player target: flash
Validating task attributes ...
Generating default values ...
Using default working dir [C:\DJTE\commons.formatter_swc\d3flxcmn32\extracted\Source\Flex]
Using the following settings for the test run:
FLEX_HOME: [C:\dev\vert-d3flxcmn32\302100.41.0.20110323122739_d3flxcmn32]
haltonfailure: [false]
headless: [false]
display: [99]
localTrusted: [true]
player: [flash]
port: [1024]
swf: [C:\DJTE\commons.formatter_swc\d3flxcmn32\extracted\build\commons.formatter.tests.unit.sw f]
timeout: [1800000ms]
toDir: [C:\DJTE\commons.formatter_swc\d3flxcmn32\reports\xml]
Setting up server process ...
Entry [C:\DJTE\commons.formatter_swc\d3flxcmn32\extracted\build] already available in local trust file at [C:\Users\user\AppData\Roaming\Macromedia\Flash Player\#Security\FlashPlayerTrust\flexUnit.cfg].
Executing 'rundll32' with arguments:
'url.dll,FileProtocolHandler'
'C:\DJTE\commons.formatter_swc\d3flxcmn32\extracted\build\commons.formatter.tests.unit.swf '
The ' characters around the executable and arguments are
not part of the command.
Starting server ...
Opening server socket on port [1024].
Waiting for client connection ...
Client connected.
Setting inbound buffer size to [262144] bytes.
Receiving data ...
Sending acknowledgement to player to start sending test data ...
Stopping server ...
End of test data reached, sending acknowledgement to player ...
When the problem occurs, it is not always during the running of any particular test (that I am aware of). Recent runs where this failure was seen had the following number of tests executed (note: the total number that should be run is 45677): 18021, 18, 229.
Here is a "good" run when the problem does not occur:
Setting inbound buffer size to [262144] bytes.
Receiving data ...
Sending acknowledgement to player to start sending test data ...
Stopping server ...
End of test data reached, sending acknowledgement to player ...
Closing client connection ...
Closing server on port [1024] ...
Analyzing reports ...
Suite: com.formatters.help.TestGeographicSiteUrls
Tests run: 5, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.008 sec
Suite: com.formatters.functionalUnitTest.testCases.TestNumericUDF
Tests run: 13, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.071 sec
Results :
Tests run: 45,677, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 201.186 sec
Has anyone else ran across this problem?
Thanks,
TrevorI am not sure if this information will help everyone, but here goes...
For us, these problems with FlexUnit tests crashing the Flash Player appear to be related to couple of factors. Recently, we moved up from Flex 3.2 to Flex 4.1 as our development baseline. Many people complained that their development environment (Flash Builder, etc.) was much more unstable. Apparently, 4.1 produces SWFs that require more memory to run than 3.2 does? Anyway, we still had Flash Player 10.1 as our runtime baseline. Apparently, that version of the player was not as capable of running larger FlexUnit test SWFs, and would crash (as I posted months earlier). I upgraded to the latest 10.3 standalone player versions, and the crashes have now ceased. It would be nice to know exactly what was causing the crashes, but memory management (or lack of) is my best guess.
So, if you are seeing these issues, try upgrading to the latest Flash Player version.
Regards,
Trevor -
Maximum number of concurrent connections using java sockets
How can we find out the maximum number of concurrent connections that can be handled by a pooled connection server?
I have a pooled server which creates a predefined number of handlers. Upon receiving a new request it accepts the connection and sends it to one of the handler.
The solution works well for low number of concurrent connections - < 50 or 100
But as the number increases there seems to be an issue
1. Ignoring request even if i increase the handlers
2. Increase in delay. [I feel that the listening thread is not getting the time slice to go read the socket for new requests]
Any idea as to how i can solve this?
Would an NIO socket help [am using the conventional java.io Serversocket, because my clients may not be non-blocking]??
Any help would be appreciated.
AnpThere is no set maximum, but it is in the thousands on most platforms. I have a production server that handles tens of thousands of connections simultaneously. Most likely you have a bug in your code.
-
I am creating a server using the 1.4x jre and NIO everytime I run the server process I max out at 64 concurrent connections. Spawning a new thread does not seem to work. I know other people have conquered this hurdle and I would appreciate any guidance I could get. Thanks in advance.
I have my environment set up so I can compile and run test programs (when I want ) using beta 1.4.02. This does not seem to solve the problem. The error is caused when after 64 connections have been accepted and you loop back to selector.select().
The error message is slightly different depending on which tester I am running but it boils down to
java.io.IOException: The parameter is incorrect
at sun.nio.ch.PollArrayWrapper.poll0(Native Method)
at sun.nio.ch.PollArrayWrapper.poll(PollArrayWrapper.java:146)
at sun.nio.ch.PollSelectorImpl.doSelect(PollSelectorImpl.java:46)
at sun.nio.ch.SelectorImpl.select(SelectorImpl.java:62)
at sun.nio.ch.SelectorImpl.select(SelectorImpl.java:67)
at mindbridge.test.Server4.run(Server4.java:79)
at java.lang.Thread.run(Thread.java:536) -
I have an application connected to an IPCBUS over which it
receives events at unpredictable intervals. My app also has various
GUI elements allowing the user to interact with a backend RPC
server. Every now-and-then I find the response to an RPC messed up
and from tracing it would seem to coincide with incoming traffic
from the bus. The two pieces of data is non-related and carried
over different socket connections. My question is whether flex is
supposed to handle this gracefully or is it documented somewhere
that you are allowed to have traffic on a single socket at any one
time. Of course the two aspects uses different callback functions
to handle their data and everything is heavily based on extending
the EventDispatcher class.I haven't yet tried doing network programming in Flash, but
as a longtime Winsock/sockets programmer, this smells to me like a
bug in your code. It's common for new network programmers to
misunderstand how TCP/IP works, thus causing problems when they try
to use it.
The most important thing to understand is that TCP is a
stream protocol. There are no packets in TCP, at the
application level. If the remote host makes three "send" calls, one
with 50 bytes, the next with 100, and the next with 150, your
program can receive all 300 bytes in a single receive call, or one
byte at a time in 300 separate receives, or anything in between.
How those bytes are packetized over the wire is, effectively,
totally outside your application's control, due to optimizations in
TCP like the Nagle and delayed-ACK algorithms. If there is anything
smarter than a switch between the two hosts, things can get even
crazier.
So, if you're expecting a "packet" from the server, you need
to somehow be able to know when you've received the whole thing.
The two common ways of doing that are length-prefixing and
delimiting.
An example of length-prefixing is to always send 2 bytes at
the start of every packet with the length of that packet, as a
binary number. Beware when doing this that different machine types
have different byte orders for integers at the binary level. You
need to agree on a standard. Or, you can limit yourself to 256-byte
packets by sending just a single byte length prefix, and avoid the
mess.
An example of delimiting is to put some special byte or group
of bytes between packets that never occurs in regular data. A lot
of the Internet protocols do this, with linefeed characters.
And then there are the protocols like HTTP that do both: the
header lines are delimited with linefeeds, and then you have an
optional block of content following the headers, whose size is
declared in the Content-Length header in a form of length
prefixing.
If you know all this, and you're sure you've done it right,
post some code so we can offer more than general advice, as I've
done. -
Last year I posted 4 programs that provided a simple client server using both stream sockets and NIO. I decided as an exercise in using Java 5 to port that code and try to use as many of the new features as possible. The following code is very long and does what all the previous example programs did. In replies do not repost the whole of this message.
It provides a simple chat like client and server. The user can request either a stream connection or a NIO connection or provide one of their own.
//========================== MsgSwitch.java ===========================//
package pkwnet.msgswitch;
import java.util.logging.Logger;
import java.util.logging.Level;
import java.util.logging.Handler;
* main class for message switch
* command line arguments are
* -p port number for server
* -s run server
* -a server ip address including port for client
* -i idle timer in seconds
* -n use NIO
* -c specify connection class
public class MsgSwitch {
static private int errors = 0;
static private String address = "127.0.0.1:6060";
static private String connectionClass = "pkwnet.msgswitch.StreamConnection";
static public void main(String [] args) {
int port = 6060;
int idleTime = 600;
boolean server = false;
boolean nio = false;
Logger logger = Logger.getLogger("msgswitch");
for(String arg : args) {
if(arg.startsWith("-a")) {
address = arg.substring(2);
} else if(arg.startsWith("-p")) {
port = argToInt(arg);
server = true;
} else if(arg.startsWith("-i")) {
idleTime = argToInt(arg);
} else if (arg.startsWith("-s")) {
server = true;
} else if (arg.startsWith("-c")) {
connectionClass = arg.substring(2);
} else if (arg.startsWith("-n")) {
connectionClass = "pkwnet.msgswitch.NIOConnection";
} else {
String err = "unknown argument=" + arg;
logger.severe(err);
System.err.println(err);
errors++;
if (errors == 0) {
if (server) {
new Server().listen(port,idleTime, nio);
} else {
new Client().start(address, nio);
} else {
fail(errors + " errors encountered", null);
static private int argToInt(String arg) {
int val = 0;
try {
val = Integer.parseInt(arg.substring(2));
} catch (NumberFormatException e) {
String err = "invalid argument format: " + arg;
Logger.getLogger("msgswitch").severe(err);
System.err.println(err);
errors++;
return val;
static public void fail(String err, Throwable e) {
String msg = "Operation terminated: " + err;
Logger.getLogger("msgswitch").log(Level.SEVERE, msg, e);
System.err.println(msg);
System.exit(12);
static public Connection getConnection() {
Connection conn = null;
try {
conn = (Connection) Class.forName(connectionClass).newInstance();
} catch (Exception e) {
fail ("connection class error", e);
return conn;
static public void logCaller(Logger logger, Level level) {
String text = "CALLED";
if (logger.isLoggable(level)) {
try {
throw new Exception("logging stack");
} catch (Exception e) {
StackTraceElement [] st = e.getStackTrace();
if (st.length > 1) {
text += formatElement(st[1]);
if (st.length >2) {
text += formatElement(st[2]);
logger.log(level, text);
static private String formatElement(StackTraceElement ste) {
return "\n " + ste.getClassName() + "." + ste.getMethodName()
+ "(" + ste.getFileName() + ":" + ste.getLineNumber() + ")";
//================= Client.java =============================================//
package pkwnet.msgswitch;
* a simple Swing chat GUI using Java 5 and sockets.
* @author PKWooster
* @version 1.0 August 31,2005
import javax.swing.JFrame;
import javax.swing.JTextField;
import javax.swing.JTextArea;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JMenu;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JDialog;
import javax.swing.SwingUtilities;
import java.awt.Container;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.awt.BorderLayout;
import static java.awt.BorderLayout.*;
client GUI class
public class Client extends JFrame implements ConnectionListener {
// swing GUI components
private JTextField userText = new JTextField(40);
private JTextArea sessionLog = new JTextArea(24,40);
private JTextField statusText = new JTextField(40);
private JPanel outPanel = new JPanel();
private JScrollPane sessionLogScroll = new JScrollPane(sessionLog);
private JMenuBar menuBar = new JMenuBar();
private JMenuItem startItem = new JMenuItem("Start");
private JMenuItem hostItem = new JMenuItem("Host");
private JMenuItem aboutItem = new JMenuItem("About");
private JMenuItem abortItem = new JMenuItem("Abort");
private JMenuItem exitItem = new JMenuItem("Exit");
private JMenu fileMenu = new JMenu("File");
private JMenu helpMenu = new JMenu("Help");
private Container cp;
private String address;
private Connection connection;
private boolean sendReady = false;
private boolean nio = false;
Client() {
public void start(String address, boolean nio) {
this.address = address;
this.nio = nio;
SwingUtilities.invokeLater(new Runnable() {
public void run() {
runClient();
private void runClient() {
connection = MsgSwitch.getConnection();
connection.addConnectionListener(this);
buildMenu();
cp = getContentPane();
sessionLog.setEditable(false);
outPanel.add(new JLabel("Send: "));
outPanel.add(userText);
// enter on userText causes transmit
userText.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent evt){userTyped(evt);}
cp.setLayout(new BorderLayout());
cp.add(outPanel,NORTH);
cp.add(sessionLogScroll,CENTER);
cp.add(statusText,SOUTH);
setStatus("Closed");
addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent evt) {
mnuExit();
pack();
setVisible(true);
* attempt to send the contents of the user text field
private void userTyped(ActionEvent evt) {
if (sendReady) {
String txt = evt.getActionCommand()+"\n";
userText.setText("");
toSessionLog("> ", txt);
sendReady = false;
connection.send(txt);
* append text to the session log
private void toSessionLog(String prefix, String txt) {
sessionLog.append(prefix + txt);
sessionLog.setCaretPosition(sessionLog.getDocument().getLength() ); // force last line visible
* build the standard menu bar
private void buildMenu()
JMenuItem item;
// file menu
startItem.addActionListener(new ActionListener()
{public void actionPerformed(ActionEvent e){mnuStart();}});
fileMenu.add(startItem);
hostItem.addActionListener(new ActionListener()
{public void actionPerformed(ActionEvent e){mnuHost();}});
fileMenu.add(hostItem);
exitItem.addActionListener(new ActionListener()
{public void actionPerformed(ActionEvent e){mnuExit();}});
fileMenu.add(exitItem);
menuBar.add(fileMenu);
helpMenu.add(aboutItem);
aboutItem.addActionListener(new ActionListener()
{public void actionPerformed(ActionEvent e){mnuAbout();}});
menuBar.add(helpMenu);
setJMenuBar(menuBar);
* start and stop communications from start menu
private void mnuStart() {
if(connection.getState() == Connection.State.CLOSED) {
connection.connect(address);
} else {
connection.disconnect();
* prompt user for host in form address:port
private void mnuHost() {
String txt = JOptionPane.showInputDialog("Enter host address:port", connection.getAddress());
if (txt == null)return;
address = txt;
private void mnuAbout() {
JDialog dialog = new JDialog(this, "About Client");
JTextField text = new JTextField("Simple character client");
dialog.getContentPane().add(text);
dialog.pack();
dialog.setVisible(true);
// exit menu
private void mnuExit() {
exit();
private void exit() {
connection.disconnect();
System.exit(0);
private void setStatus(String st) {
statusText.setText(st);
private void setStatus(Connection.State state) {
switch(state) {
case OPENED:
startItem.setText("Stop");
setStatus("Connected to "+address);
break;
case CLOSED:
startItem.setText("Start");
setStatus("Disconnected");
break;
case OPENING:
setStatus("Connecting to "+address);
startItem.setText("Abort");
break;
case CLOSING:
setStatus("Disconnecting from "+address);
startItem.setText("Abort");
break;
public void stateChanged(final ConnectionEvent event) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
setStatus(event.getState());
public void dataAvailable(final ConnectionEvent event) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
setStatus(event.getState());
String txt = event.getData();
if (txt == null) {
txt = "$null$";
toSessionLog("< ", txt + "\n");
public void sendAllowed(final ConnectionEvent event) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
setStatus(event.getState());
sendReady = true;
public void accept(ConnectionEvent event) {
//========================== Server.java ===============================//
package pkwnet.msgswitch;
import java.io.*;
import java.net.*;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
* a simple message switch using stream based socket i/o
* a very simple text message switching program
* user commands start with $ and consist of blank seperated arguments
* other lines sent by the user are forwarded
* $on nickname targets
* sign on as nickname, sending to targets
* $to targets
* change target list, reports current value
* $list nicknames
* list status of specified nicknames
* $list
* list all connected users
* $off
* sign off
* @author PKWooster
* @version 1.0 September 1, 2005
public class Server {
private ConcurrentHashMap<String, User> perUser = new ConcurrentHashMap<String,User>();
private Timer idleTimer;
private Connection conn;
public void listen(int port, final int idleTime, boolean nio) {
idleTimer = new Timer();
idleTimer.scheduleAtFixedRate(new TimerTask(){public void run(){oneSec();}},0,1000);
conn = MsgSwitch.getConnection();
conn.addConnectionListener(new ConnectionListener() {
public void stateChanged(ConnectionEvent event) {
public void dataAvailable(ConnectionEvent event) {
public void sendAllowed(ConnectionEvent event) {
public void accept(ConnectionEvent event) {
Connection uconn = event.getConnection();
new User(uconn, perUser, idleTime);
conn.listen(port);
idleTimer.cancel();
private void oneSec() {
Collection<User> uc = perUser.values();
for(User u : uc) {
u.oneSec();
//================= User.java ==============================================//
package pkwnet.msgswitch;
import java.io.*;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.logging.Logger;
import java.util.logging.Level;
* defines the processing for a message switch user
* @author PKWooster
* @version 1.0 June 15,2004
public class User implements ConnectionListener {
private ConcurrentHashMap<String, User> perUser;
private String name;
private String address;
private boolean signedOn = false;
private String[] targets;
private AtomicInteger remainingTime;
private int idleTime;
Connection conn;
Logger logger;
* construct a user, link it to its connection and put it in the perUser table
User(Connection conn, ConcurrentHashMap<String,User>p, int idle) {
this.conn = conn;
logger = Logger.getLogger("msgswitch.user");
conn.addConnectionListener(this);
address = conn.getAddress();
logger.info("creating user " + address);
perUser = p;
idleTime = idle;
remainingTime = new AtomicInteger(idleTime);
rename(address);
targets = new String[0];
* process state changes
public void stateChanged(ConnectionEvent event) {
if(event.getState() == Connection.State.CLOSED) {
close(false);
* data is available, process commands and forward other data.
public void dataAvailable(ConnectionEvent event) {
String msg = event.getData();
if (msg.startsWith("$")) {
doCommand(msg);
} else {
forward(msg);
remainingTime.set(idleTime);
* do nothing for sendAllowed events
public void sendAllowed(ConnectionEvent event) {
* do nothing for accept events
public void accept(ConnectionEvent event) {
* called once per second by the server main thread.
public void oneSec() {
if(idleTime != 0 && 1 > remainingTime.decrementAndGet()) {
close(true);
* send a message
private void send(String msg) {
conn.send(msg);
remainingTime.set(idleTime);
* forward data messages to other users
* @param txt the message to send
private void forward(String txt) {
txt = name+": "+txt + "\n";
if(0 < targets.length) {
for(String target :targets) {
User user = perUser.get(target);
if(user != null) {
user.send(txt);
} else {
for (User user : perUser.values()) {
if (user != this) {
user.send(txt);
* execute command messages, commands start with a $
* and contain arguments delimited by white space.
* @param command the command string
private void doCommand(String command) {
boolean good = false;
command = command.substring(1).trim();
if(command.length() > 0) {
String [] args = command.split("\\s+");
if(args[0].equals("on")) {
good = signOn(args);
} else if(args[0].equals("off")) {
good = signOff(args);
} else if(args[0].equals("list")) {
good = listUsers(args);
} else if(args[0].equals("to")) {
good = setTargets(args,1);
} else if(args[0].equals("idle")) {
good = setIdle(args);
if(!good) {
send("invalid command=" + command + "\n");
* sign on command
private boolean signOn(String [] args) {
boolean good = false;
if(args.length >1) {
String nm = args[1];
logger.info("signing on as: " + nm);
if(rename(nm)) {
conn.setName(name);
send("Signed on as " + name + "\n");
signedOn = true;
good = true;
setTargets(args,2);
} else {
send("name="+nm+" already signed on\n");
return good;
* set forwarding targets
private boolean setTargets(String [] args, int start) {
if(start < args.length) {
targets = new String[args.length-start];
System.arraycopy(args, start, targets, 0, targets.length);
String str = "to=";
for(String target : targets) {
str += (target + " ");
send(str+"\n");
return true;
* set idle timeout
private boolean setIdle(String[] args) {
try {
idleTime = new Integer(args[1]).intValue();
remainingTime.set(idleTime);
send("idle time set to "+idleTime+"\r\n");
return true;
} catch(NumberFormatException exc) {
return false;
* sign off
private boolean signOff(String [] args) {
close(true);
return true;
* list connected users
private boolean listUsers(String [] args) {
TreeSet<String> allUsers = new TreeSet<String>(perUser.keySet());
HashSet<String> t = new HashSet<String>(Arrays.asList(targets));
LinkedList<String> users;
String response = "On,Target,Nickname\n";
if(args.length < 2) {
users = new LinkedList<String>(allUsers);
} else {
users = new LinkedList<String>();
for (int i = 1; i < args.length; i++) {
users.add(args);
for(String username : users) {
if(username.equals(name)) {
response += "*,";
} else {
response += (allUsers.contains(username) ? "y," : "n,");
response += (t.contains(username) ? "y," : "n,");
response += (username + "\n");
send(response);
return true;
* rename this user, first we attempt to add the new name then we remove
* the old one. Both names will be registered for a short while.
* @param newname the new name for this user
* @return true if the rename was successful
private boolean rename(String newname) {
boolean b = false;
logger.info("rename name="+name+" newname="+newname);
if (name != null && name.equals(newname)) {
b = true;
} else if (null == perUser.putIfAbsent(newname, this)) {
if (name != null) {
perUser.remove(name);
name = newname;
b = true;
return b;
* delete from perUser and close our connection
private void close(boolean disconnect) {
logger.info("closing user "+name);
perUser.remove(name);
if (disconnect) {
conn.disconnect();
//====================== Connection.java ===============================//
package pkwnet.msgswitch;
import java.util.HashSet;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.logging.Logger;
import java.util.logging.Level;
public abstract class Connection {
public enum State {CLOSED, OPENING, OPENED, CLOSING}
private HashSet<ConnectionListener> listeners = new HashSet<ConnectionListener>();
private State state = State.CLOSED;
private String host = "127.0.0.1";
private int port = 6060;
private String name = "unconnected";
public Connection() {
public abstract void listen(int port);
public abstract void connect(String address);
public abstract void disconnect();
public abstract void send(String message);
public void addConnectionListener(ConnectionListener listener) {
listeners.add(listener);
public void removeConnectionListener(ConnectionListener listener) {
listeners.remove(listener);
protected void fireDataAvailable(String data) {
for (ConnectionListener listener : listeners) {
listener.dataAvailable(new ConnectionEvent(this, state, data));
private void fireStateChanged() {
for (ConnectionListener listener : listeners) {
listener.stateChanged(new ConnectionEvent(this, state));
protected void fireSendAllowed() {
for (ConnectionListener listener : listeners) {
listener.sendAllowed(new ConnectionEvent(this, state));
protected void fireAccept(Connection conn) {
for (ConnectionListener listener : listeners) {
listener.accept(new ConnectionEvent(this, conn));
protected void setState(State state) {
if (this.state != state) {
this.state = state;
fireStateChanged();
public State getState() {
return state;
protected void setAddress(String address) {
int n = address.indexOf(':');
String pt = null;
setName(address);
if(n == 0) {
host = "127.0.0.1";
pt = address.substring(1);
else if(n < 0) {
host = address;
port = 5050;
} else {
host = address.substring(0,n);
pt = address.substring(n+1);
if (pt != null) {
try {
port = Integer.parseInt(pt);
} catch (NumberFormatException e) {
port = -1;
public String getName() {
return name;
public void setName(String value) {
name = value;
public String getAddress() {
return host + ":" + port;
public String getHost() {
return host;
public void setPort(int value) {
port = value;
public int getPort() {
return port;
//=================== ConnectionEvent.java ================================//
package pkwnet.msgswitch;
public class ConnectionEvent extends java.util.EventObject {
private final String data;
private final Connection.State state;
private final Connection conn;
public ConnectionEvent(Object source, Connection.State state, String data, Connection conn) {
super(source);
this.state = state;
this.data = data;
this.conn = conn;
public ConnectionEvent(Object source, Connection.State state, String data) {
this(source, state, data, null);
public ConnectionEvent(Object source, Connection.State state) {
this(source, state, null, null);
public ConnectionEvent(Object source, Connection conn) {
this(source, conn.getState(), null, conn);
public Connection.State getState() {
return state;
public String getData() {
return data;
public Connection getConnection() {
return conn;
//============================ ConnectionListener.java ===================//
package pkwnet.msgswitch;
public interface ConnectionListener extends java.util.EventListener {
public void stateChanged(ConnectionEvent event);
public void dataAvailable(ConnectionEvent event);
public void sendAllowed(ConnectionEvent event);
public void accept(ConnectionEvent event);
//============================ StreamConnection.java ===================//
package pkwnet.msgswitch;
import java.net.Socket;
import java.net.ServerSocket;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.IOException;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.logging.Logger;
import java.util.logging.Level;
* provides stream socket i/o of character strings
* @author PKWooster
* @version 1.0 September 1, 2005
public class StreamConnection extends Connection {
private Socket sock;
private BufferedReader in;
private BufferedWriter out;
private Thread recvThread = null;
private Thread sendThread = null;
protected LinkedBlockingQueue<String> sendQ;
Logger logger;
public StreamConnection() {
super();
logger = Logger.getLogger("msgswitch.stream");
sendQ = new LinkedBlockingQueue<String>();
* open a socket and start i/o threads
public void connect(String ipAddress) {
setAddress(ipAddress);
try {
sock = new Socket(getHost(), getPort());
connect(sock);
} catch (IOException e) {
logger.log(Level.SEVERE, "Connection failed to=" + ipAddress, e);
private void connect(Socket sock) {
this.sock = sock;
String ipAddress = getAddress();
try {
in = new BufferedReader(new InputStreamReader(sock.getInputStream()));
out = new BufferedWriter(new OutputStreamWriter(sock.getOutputStream()));
recvThread = new Thread(new Runnable() {
public void run() {
doRecv();
},"Recv." + getName());
sendThread = new Thread(new Runnable() {
public void run() {
doSend();
},"Send."+getName());
sendThread.start();
recvThread.start();
setState(State.OPENED);
} catch(IOException e) {
logger.log(Level.SEVERE, "Connection failed to="+ipAddress, e);
public void listen(int port) {
StreamConnection sconn;
setPort(port);
try {
ServerSocket ss = new ServerSocket(port);
while(true) {
Socket us = ss.accept();
sconn = new StreamConnection();
String ipAddress = us.getInetAddress() + ":" + us.getPort();
sconn.setAddress(ipAddress);
sconn.connect(us);
fireAccept(sconn);
} catch(Exception e) {
logger.log(Level.SEVERE, "listen failed", e);
* close the socket connection
public void disconnect() {
logger.fine("disconnect sock=" + sock + " state="+ getState());
if(getState() == State.OPENED) {
setState(State.CLOSING);
try {
sock.shutdownOutput();
} catch(IOException ie) {
logger.log(Level.SEVERE, "showdown failed", ie);
} else if(getState() != State.CLOSED) {
try {
sock.close();
} catch(Exception e) {
logger.log(Level.SEVERE, "close failed", e);
if (sendThread.isAlive()) {
sendThread.interrupt();
sendQ.clear();
setState(State.CLOSED);
public void send(String message) {
if (getState() == State.OPENED) {
try {
sendQ.put(message);
} catch(InterruptedException e) {
logger.log(Level.SEVERE, "sendQ put interrupted", e);
setState(State.CLOSING);
disconnect();
* sets the public name of this connection
public void setName(String name) {
super.setName(name);
if (sendThread != null) {
try {
recvThread.setName("recv." + name);
sendThread.setName("send." + name);
} catch(Exception e) {
logger.log(Level.SEVERE, "nameing threads failed", e);
* the main loop for the send thread
private void doSend() {
String msg;
boolean running = true;
while (running) {
if (sendQ.size() == 0) {
fireSendAllowed();
try {
msg = sendQ.take();
out.write(msg);
out.flush();
} catch(Exception e) {
if (getState() == State.OPENED) {
logger.log(Level.SEVERE, "write failed", e);
setState(State.CLOSING);
disconnect();
running = false;
* the main loop for the receive thread
private void doRecv() {
String inbuf;
while (getState() == State.OPENED) {
try {
inbuf = in.readLine();
} catch(Exception e) {
if (getState() == State.OPENED) {
logger.log(Level.SEVERE, "readline failed", e);
inbuf = null;
if(inbuf == null) {
logger.fine("null received on: " + getAddHere are three of them:
NIO server
NIO client
Multithreaded server
The stream based client example seems to have been deleted, probably lost in the troll wars. I also posted a new Simple multithreaded server that uses the same protocol. As the client is missing, I'll repost it. -
Small input program (html) using sockets.
I'm having problems with the following whenever a cd is inputted via cdinput.html it runs cdprocess.jsp to create an XML document with DOM in memory this is sent to the server and is later printed out to the users screen. The server must be started in order for it to work. For some reason it doesn't seem to be working? In cd process i'm suppose to modify a few things they've been numbered i've complete all of them so far but i'm not sure if #4 is correct. I've been stuck on it for a while now, any help would be appreciated.
cdinput.html
<html>
<head><title></title></head>
<body>
<br /><center>
<table width="500" border="0"
cellpadding="4" cellspacing="0">
<tr>
<td bgcolor="lightblue">
<font color="white" face="Arial"><b>CD Input</b>
</font></td>
</tr>
<tr>
<td>
<form method="post" action="cdprocess.jsp">
<table>
<tr>
<td><b>CD Title:</b></td>
<td><input type="text" name="cdtitle" size="20"></td>
</tr>
<tr>
<td><b>CD Artist:</b></td>
<td><input type="text" name="cdartist" size="20"></td>
</tr>
<tr>
<td><b>Track 1 title:</b></td>
<td><input type="text" name="track1title" size="20"></td>
</tr>
<tr>
<td><b>Track 1 time:</b></td>
<td><input type="text" name="track1time" size="20"></td>
</tr>
<tr>
<td><b>Track 1 rating:</b></td>
<td><select name="track1rating">
<option value="1"> 1 </option>
<option value="2"> 2 </option>
<option value="3"> 3 </option>
<option value="4"> 4 </option>
<option value="5"> 5 </option>
</select></td>
</tr>
</table><br />
<input type="submit" value="Enter CD">
</form>
</td>
</tr>
</table>
</center>
</body>
</html>
SimpleServer2.java
import java.net.*;
import java.io.*;
The server half of a simple client/server application.
The server that reads lines of text from a socket and sends
back a copy of the same text to the client.
The main difference between this example and SimpleServer is that
this one allows multiple sequential (not concurrent) connections
from clients.
public class SimpleServer2 {
public static final int serverListenPort = 10151;
The main method is the entry point for the application.
Because this is a simple application for testing, everything
is done inside the main method.
@param args Arguments entered on the command-line.
public static void main(String[] args) throws IOException {
ServerSocket myServerSocket = null;
// Try to open a server socket listening on specified listen port
try {
myServerSocket = new ServerSocket(serverListenPort);
catch (IOException e) {
System.err.println("Could not listen on port" + serverListenPort);
System.err.println("Perhaps somebody else is using that port number??");
System.exit(1);
* This is where the difference begins.
* Note the while(true) loop, which means that we will
* accept an infinite number of connections from clients,
* one at a time. The server will never exit by itself,
* you will have to kill it manually by typing Ctrl-C
* at the command line where it is running.
while(true) {
// Create a variable to hold the socket that we get when a
// new client connects
Socket myClientSocket = null;
// Accept a new connection from a client
// This method call will block until a client does connect
try {
myClientSocket = myServerSocket.accept();
catch (IOException e) {
System.err.println("Accept failed.");
System.exit(1);
// Now that we have a socket, the reading and writing code
// is basically the same as in the client application.
// We start by getting hold of the output stream to write data
// to the socket, and the input stream to read data from the socket.
PrintWriter out = new PrintWriter(myClientSocket.getOutputStream(), true);
BufferedReader in = new BufferedReader(
new InputStreamReader(myClientSocket.getInputStream()));
String inputLine, outputLine;
// Now use a loop to read in lines of text from the client, and
// echo them back to the client
// Note that this time we do NOT break out of the loop.
// We will just wait for the client to close the connection,
// and when it does, our inputLine will be null and then we
// will break out of the loop.
while ((inputLine = in.readLine()) != null) {
outputLine = inputLine;
out.println(outputLine);
// If we have broken out of the loop, we can assume that
// the input is closed. The output probably is too, but
// just in case, we'll close it anyway.
out.close();
cdprocess.jsp
<%@page import="java.io.*"%>
<%@page import="java.net.*"%>
<%@page import="javax.xml.parsers.*"%>
<%@page import="org.w3c.dom.*"%>
<%@page import="org.apache.xml.serialize.*"%>
<%!
public static final String serverHost = "cdserver";
public static final int serverPort = 10151;
%>
<hr />
<pre>
<%
Socket mySocket = null; // socket object
PrintWriter sockOut = null; // to send data to the socket
BufferedReader sockIn = null; // to receive data from the socket
try {
// #1 add line that creates a client socket
mySocket = new Socket(serverHost, serverPort);
// #2 add lines that create input and output streams
// attached to the socket you just created
sockOut = new PrintWriter(mySocket.getOutputStream(), true);
sockIn = new BufferedReader(new InputStreamReader(mySocket.getInputStream()));
} catch (UnknownHostException e) {
throw e; // This time the JSP can handle the exception, not us
} catch (IOException e) {
throw e; // This time the JSP can handle the exception, not us
String cdTitle, cdArtist, track1Title, track1Time, track1Rating;
// Retrieve the HTML form field values
cdTitle = request.getParameter("cdtitle");
cdArtist = request.getParameter("cdartist");
track1Title = request.getParameter("track1title");
track1Time = request.getParameter("track1time");
track1Rating = request.getParameter("track1rating");
* Our goal is to build an XML document in memory using DOM.
* We will build it up one tree-node at a time, and when it is
* finished, we will write the whole lot out to a file on disk.
/* Start of the DOM code */
// Create a new DOM factory, and from that a new DOM builder object
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = factory.newDocumentBuilder();
// Note that we are creating a new (empty) document
Document document = builder.newDocument();
// The root element of our document wil be <cd>
// It gets stored as the child node of the whole document (it is the root)
Element rootElement = document.createElement("cd");
document.appendChild(rootElement);
// Create an element for the CD title called <title>
Element cdTitleElement = document.createElement("title");
// Add a text code under the <title> element with the value that
// the user entered into the title field of the web form (cdTitle)
cdTitleElement.appendChild(document.createTextNode(cdTitle));
// Place the <title> element underneath the <cd> element in the tree
rootElement.appendChild(cdTitleElement);
// Create an <artist> element with the form data, place underneath <cd>
Element cdArtistElement = document.createElement("artist");
cdArtistElement.appendChild(document.createTextNode(cdArtist));
rootElement.appendChild(cdArtistElement);
// Create a <tracklist> element and place it underneath <cd> in the tree
// Note that it has no text node associated with it (it not a leaf node)
Element trackListElement = document.createElement("tracklist");
rootElement.appendChild(trackListElement);
// In this example we only have one track, so it is not necessary to
// use a loop (in fact it is quite silly)
// But the code below is included to demonstrate how you could loop
// through and add a set of different tracks one by one if you
// needed to (although you would need to have the track data already
// stored in an array or a java.util.Vector or similar
int numTracks = 1;
for (int i=0; i<numTracks; i++) {
String trackNum = Integer.toString(i+1);
// Note that this element has an attribute associated with it that
// is the track number. It will look like: <track id="1">
// The <track> element is placed underneath <tracklist> in the tree
Element trackElement = document.createElement("track");
trackElement.setAttribute("id", trackNum);
trackListElement.appendChild(trackElement);
// Track title element called <title>, placed underneath <track>
Element trackTitleElement = document.createElement("title");
trackTitleElement.appendChild(document.createTextNode(track1Title));
trackElement.appendChild(trackTitleElement);
// Track time element called <time>, placed underneath <track>
Element trackTimeElement = document.createElement("time");
trackTimeElement.appendChild(document.createTextNode(track1Time));
trackElement.appendChild(trackTimeElement);
// Track rating element called <rating>, placed underneath <track>
Element trackRatingElement = document.createElement("rating");
trackRatingElement.appendChild(document.createTextNode(track1Rating));
trackElement.appendChild(trackRatingElement);
/* End of DOM code */
/* Start of serialization code */
// Create a new OutputFormat - this is something specific needed by the
// XMLSerializer class shown below. We will specify that we want the
// generated XML to be formatted with indenting so it is easy to read.
OutputFormat format = new OutputFormat();
format.setIndenting(true);
* Note: the next line of code is the one change to serialization
// Create a new XMLSerializer that will be used to write out the XML
// This time we will serialize it to the socket
// #3 change this line so that it serializes to the socket,
// not to the "out" object
XMLSerializer serializer = new XMLSerializer(writer, format);
// Call the serialize() method, and pass to it out XML document
// stored in memory in a DOM tree
serializer.serialize(document);
/* End of serialization code */
// Print out a message to indicate the end of the data, and
// flush the stream so all the data gets sent now
sockOut.println("<!--QUIT-->");
sockOut.flush();
BufferedReader stdIn = new BufferedReader(new InputStreamReader(System.in));
String fromServer;
String fromUser;
#4 add a while loop that reads text from the
server socket input stream, line by line, and prints
it out to the web page, using out.println(...);
Note that because the reply from the server will contain
XML, you will need to call upon the toHTMLString() method
defined below to escape the < and > symbols so that they
will display correctly in the web browser.
Also note that as you receive the reply back from the
server, you should look out for the special <!--QUIT-->
string that will indicate when there is no more data
to receive.
while ((fromServer = sockIn.readLine()) != null) {
out.println(sockIn.readLine());
// If the reply from the server said "QUIT", exit from the
// while loop by using a break statement.
if (fromServer.equals("QUIT")) {
out.println("Connection closed - good bye ...");
// Print the text from the server out to the user's screen
out.println("Reply from Server: " + fromServer);
// Now read a line of text from the keyboard (typed by user)
fromUser = stdIn.readLine();
// If it wasn't null, print it out to the screen, and also
// print a copy of it out to the socket
if (fromUser != null) {
out.println("Client: " + fromUser);
sockOut.println(fromUser);
// Close all the streams we have open, and then close the socket
sockOut.close();
sockIn.close();
mySocket.close();
%>
<%!
This method will escape any special HTML characters in a string
of text. For example, if you are trying to print out an XML
document using a JSP, you need to escape all the '<' and '>' tags
so that the web browser will not try and treat them as HTML.
Note that generic utility code like this would usually be put into
a JavaBean, but is put in the JSP here for simplicity.
This code taken from H. Bergsten, JavaServer Pages, O'Reilly, 2001.
private static String toHTMLString(String in) {
StringBuffer out = new StringBuffer();
for (int i = 0; in != null && i < in.length(); i++) {
char c = in.charAt(i);
if (c == '\'') {
out.append("'");
else if (c == '\"') {
out.append(""");
else if (c == '<') {
out.append("<");
else if (c == '>') {
out.append(">");
else if (c == '&') {
out.append("&");
else {
out.append(c);
return out.toString();
%>
</pre>
<hr />the following also has me stumped:
// #3 change this line so that it serializes to the socket,
// not to the "out" object
i tried changing the first parameter to the socket "mySocket" but it just gives me a compilation error. -
Concurrent transactions problem- Can anybody help?- very urgent
I have tested our application for multiple transactions i.e. concurrent transactions between two servers with IIS and Tomcat environment. We found some unexpected result and which is irrespective of the data (size ranging from 10 bytes to 10 kb, 50kb 70kb etc) sending across the servers on
I was testing with 5 transactions (with data size of 13 bytes) from one machine (server1) i.e 5 windows of internet explorer. When I clicked on all the five, one after another quickly, I found that 4 transactions got success and one browser went to hang mode.
Second time when I clicked on it, I found that 3 transactions got success, 1 in hang mode and 1 failed.
We traced the exception at the point where it fails. Everytime it fails while reading the response back from the other end through InputStreamBuffer. The block in which it fails is
Please follow the piece of code which i have written
//reading response from the destination decrypt url,
//which is also encrypted and signed
//sending the same to caller of encrypt
String data="";
int end=0;
char c[]=new char[4*1024];
BufferedReader buf=null;
//reading data in a chunks of data
try
inr=new InputStreamReader(connection.getInputStream());
buf=new BufferedReader(inr,12*1024);
while ((end=buf.read(c))!=-1)
data=new StringBuffer(data).append(c,0,end).toString();
catch(OutOfMemoryError e)
System.out.println("Out of memory errror"+e.getMessage());
try
response.sendError(HttpServletResponse.SC_NOT_FOUND);
return;
catch(Exception e1)
return;
catch(Exception e1)
System.out.println("Failure in reading response"+e1.getMessage());
try
response.sendError(HttpServletResponse.SC_NOT_FOUND);
return;
catch(Exception e2)
return;
finally
try
if(inr!=null)
inr.close();
if(buf!=null)
buf.close();
if (connection != null)
connection.disconnect();
catch(Exception e)
System.out.println("Error in closing connection"+e.getMessage());
Here the connection get disconnected and throws the following exceptions at difterent time of testing in failure case.
1. Failure in reading response JVM_recv in socket input stream read (code=10004)
Error in closing connection Socket closed
2. Null pointer exception.
Could you please tell us what would be the reasons for the above exceptions or failure and how to rectify or handle it.
Thanks & Regards
Gabriel- First, do not use BufferedReader.
Use InputStream.read(byte[]) and make them to an String.
If does not help use another stable version of TOMCAT
on the same way.
Also it is better to read the data over the Servlet API
methods not over the IO streams.
e.g. request.getParameter("XXX")
- Do not close the socket connection in TOMCAT.
TOMCAT themselves close the connection for you.
Use the flush() method for getting the data faster. -
[SOLVED]GPG no longer supports --no-use-standard-socket?
I've used an SD card for where I store my gnupghome for a long time. I have delegated subkeys and all the configuration for them there. It's mounted to /mnt/keys on vfat. These cards use a FAT file system as I use these keys on multiple operating systems.
GPG with release 2.1 has removed the 'standard socket' options, which means now if your gnupg home is on any file system that can't create socket files (see: FAT), gpg-agent can no longer run. Ironically, this is also the release that *removes* all support for running gpg without an agent!
I'm disappointed this was not considered news for arch, I even wrote a small silly wrapper just for forcing me to read front page stories! (http://github.com/codemac/yosumiru)
The GPG news page had the following:
With GnuPG 2.1 the need of GPG_AGENT_INFO has been completely removed and the variable is ignored. Instead a fixed Unix domain socket named S.gpg-agent in the GnuPG home directory (by default ~/.gnupg) is used. The agent is also started on demand by all tools requiring services from the agent.
Any thoughts on how I can keep my gnupg on a FAT filesystem and still run the agent? I'm feeling pretty hosed right now, and am pretty confused why this feature was removed from gpg agent, as this would be as simple as keeping the old functionality, but maybe forcing the --no-use-standard-socket option to be in gpg.conf
Last edited by codemac (2014-12-02 18:43:06)codemac wrote:I've used an SD card for where I store my gnupghome for a long time. I have delegated subkeys and all the configuration for them there. It's mounted to /mnt/keys on vfat. These cards use a FAT file system as I use these keys on multiple operating systems.
That's exactly what I used to do as well: mount a USB key read-only and run gpg --homedir /path/to/usb.
codemac wrote:
GPG with release 2.1 has removed the 'standard socket' options, which means now if your gnupg home is on any file system that can't create socket files (see: FAT), gpg-agent can no longer run. Ironically, this is also the release that *removes* all support for running gpg without an agent!
I'm disappointed this was not considered news for arch, I even wrote a small silly wrapper just for forcing me to read front page stories! (http://github.com/codemac/yosumiru)
The GPG news page had the following:
With GnuPG 2.1 the need of GPG_AGENT_INFO has been completely removed and the variable is ignored. Instead a fixed Unix domain socket named S.gpg-agent in the GnuPG home directory (by default ~/.gnupg) is used. The agent is also started on demand by all tools requiring services from the agent.
Any thoughts on how I can keep my gnupg on a FAT filesystem and still run the agent? I'm feeling pretty hosed right now, and am pretty confused why this feature was removed from gpg agent, as this would be as simple as keeping the old functionality, but maybe forcing the --no-use-standard-socket option to be in gpg.conf
I don't understand why you insist on using --no-use-standard-socket...
Some background: traditionally gpg-agent is started by a DE (e.g. xfce4-session starts it). This is useful because gpg-agent also manages ssh keys. However, this is not required anymore because agents are started on-demand and multiple agents can run concurrently.
Now, if you didn't have a vFAT FS, all is good as you call gpg --homedir because it will invoke gpg-agent with the correct --homedir flag.
So, all you need to do now is to rsync your gnupg dir on the SD card to some temp dir, e.g. /dev/shm/gnupg and use this dir as an argument to --homedir, and don't care about the agent at all. -
How to integrate a class with template.java - Java Concurrent Program. 11i
Hello, I have a java class I got from a vendor. This java class needs to run through as concurrent program. As per metalink note *How To Create a Java Concurrent Program? [ID 827563.1]* it says that, we must require template.java to wrap around the custom class. I have done that in the following java code. However, being a new java guy, I really dont know how to connect these two classes and constructor.
Any suggestions about how do I make these classes work in order to run from a concurrent program?
package oracle.apps.fnd.cp.request;
import oracle.apps.fnd.util.*;
import oracle.apps.fnd.cp.request.*;
import java.io.BufferedReader;
import java.io.IOException;
import javax.net.ssl.SSLSocketFactory;
public class cyberBatch implements JavaConcurrentProgram {
// Optionally provide class constructor without any arguments.
// If you provide any arguments to the class constructor then while running the program will fail.
public void runProgram(CpContext pCpContext) {
ReqCompletion lRC = pCpContext.getReqCompletion();
String CompletionText = "";
// This class is to upload files but can be expanded to download files also.
public class SSLFileTransfer {
Properties props =
new Properties(); // stores properties from property file
* SSLFileTransfer(): constructor
public SSLFileTransfer() {
* init(): initialization (load property file)
* @param propsFile properties needed for file transfer
public void init(String propsFile) {
try {
props.load(new BufferedInputStream(new FileInputStream(new File(propsFile))));
} catch (Exception e) {
e.printStackTrace();
System.exit(-1);
* usage()
public static void usage() {
System.out.println("USAGE: java SSLFileTransfer <full path property file name>");
System.exit(-1);
* getFactory(): get factory for authentication
* @throws IOException if exception occurs
private SSLSocketFactory getFactory() throws IOException {
try {
SSLContext ctx;
KeyManagerFactory kmf;
KeyStore ks, ks1;
char[] passphrase =
props.getProperty("passPhrase").toCharArray();
ctx = SSLContext.getInstance("TLS");
kmf = KeyManagerFactory.getInstance("SunX509");
ks = KeyStore.getInstance("PKCS12", "BC");
ks1 = KeyStore.getInstance("JKS");
ks.load(new FileInputStream(props.getProperty("key")),
passphrase);
ks1.load(new FileInputStream(props.getProperty("keyStore")),
passphrase);
kmf.init(ks, passphrase);
TrustManagerFactory tmf =
TrustManagerFactory.getInstance("SunX509");
tmf.init(ks1);
ctx.init(kmf.getKeyManagers(), tmf.getTrustManagers(), null);
return ctx.getSocketFactory();
} catch (Exception e) {
e.printStackTrace();
throw new IOException(e.getMessage());
* getHost(): Get host from property file
private String getHost() {
return props.getProperty("host", "localhost");
* getPort(): Get port from property file
private int getPort() {
return Integer.parseInt(props.getProperty("port"));
* sendRequest(): Send request (file) to the server
* @param out stream to send the data to the server
* @throws Exception if an error occurs.
private void sendRequest(PrintWriter out) throws Exception {
String path = props.getProperty("path");
out.println("POST " + path + " HTTP/1.0");
final String BOUNDARY = "7d03135102b8";
out.println("Content-Type: multipart/form-data; boundary=" +
BOUNDARY);
String uploadFile = props.getProperty("uploadFile");
String authString =
props.getProperty("bcUserName") + ":" + props.getProperty("bcPassword");
String encodedAuthString =
"Basic " + new sun.misc.BASE64Encoder().encode(authString.getBytes());
out.println("Authorization: " + encodedAuthString);
final String CRLF = "\r\n";
StringBuffer sbuf = new StringBuffer();
sbuf.append("--" + BOUNDARY + CRLF);
sbuf.append("Content-Disposition: form-data; name=\"upfile\"; filename=\"" +
uploadFile + "\"" + CRLF);
sbuf.append("Content-Type: text/plain" + CRLF + CRLF);
FileReader fi = new FileReader(uploadFile);
char[] buf = new char[1024000];
int cnt = fi.read(buf);
sbuf.append(buf, 0, cnt);
sbuf.append(CRLF);
sbuf.append("--" + BOUNDARY + "--" + CRLF);
int sz = sbuf.length();
out.println("Content-Length: " + sz);
out.println();
out.println(sbuf);
out.flush();
// Make sure there were no surprises
if (out.checkError())
System.out.println("SSLFileTransfer: java.io.PrintWriter error");
* readResponse(): reads response from the server
* @param in stream to get the data from the server
* @throws Exception if an error occurs.
private void readResponse(BufferedReader in) throws Exception {
boolean successful = false;
String inputLine;
while ((inputLine = in.readLine()) != null) {
if (inputLine.startsWith("HTTP") &&
inputLine.indexOf("200") >= 0)
successful = true;
System.out.println(inputLine);
System.out.println("UPLOAD FILE " +
(successful ? "SUCCESSFUL" : "FAILED") +
"!!!\n");
* upload(): upload file to server
* @throws Exception if an error occurs.
public void upload() throws Exception {
try {
SSLSocketFactory factory = getFactory();
SSLSocket socket =
(SSLSocket)factory.createSocket(getHost(), getPort());
PrintWriter out =
new PrintWriter(new BufferedWriter(new OutputStreamWriter(socket.getOutputStream())));
BufferedReader in =
new BufferedReader(new InputStreamReader(socket.getInputStream()));
socket.startHandshake();
sendRequest(out);
readResponse(in);
out.close();
in.close();
socket.close();
} catch (Exception e) {
e.printStackTrace();
throw e;
* main(): main method to start file transfer
* @param args command line arguments (property file, see usage())
* @throws Exception if an error occurs.
public static void main(String[] args) throws Exception {
if (args == null || args.length != 1)
usage();
SSLFileTransfer fileXfer = new SSLFileTransfer();
fileXfer.init(args[0]);
fileXfer.upload();
lRC.setCompletion(ReqCompletion.NORMAL,CompletionText) ;
}Thanks,
RI believe the OP is aware of this :) -- Re: Oracle 11i - 11.5.10.2 - and Java
Thanks,
Hussein -
Need some design idea for a multi- thread concurrent system
I am totally new to this area. Hope ppl can give me some suggestion for the following project.
The project is using socket to deal with huge concurrent data. Server will send me more than 50K (maybe more) XML strings in a short time.
I need parse strings and save them in the data structure.
What I have done is using ExecutorService to deal with this problem. Unfortunately, it's already too slow even I don't save data into data structure.(data structure will cause synchronization problem, and make system even worse).
I was required to develop this software in a single machine and windows based OS.
Should I only use single thread to do this project? or some other strategy?
Can anybody give me some suggestion.
Thanks so much.Peter. Thanks again.
Could you help me to take a look at this code. Appreciate that.
ThreadPool class:
protected ExecutorService threadPool = Executors.newFixedThreadPool(5);
incoming = new Socket("127.0.0.1", port1);
outcoming = new Socket("127.0.0.1", port2);
out = new PrintWriter(outcoming.getOutputStream(), true);
isr = new InputStreamReader(incoming.getInputStream());
is = new BufferedReader(isr);
while (true) {
String str;
str = is.readLine();
if (str == null) {
cleanup();
closeSocket();
printout();
} else {
this.threadPool.submit(new WorkerRunnable(str,
"Thread Pooled Server"));
}WorkerRunnable class:
public void run() {
try {
SAXBuilder builder = new SAXBuilder();
InputSource is = new InputSource( );
is.setCharacterStream(new StringReader(xmlString));
org.jdom.Document doc = builder.build(is);
org.jdom.Element root = doc.getRootElement();
org.jdom.Element order = root.getChild("Changes");
List orderList = order.getChildren("OrderChange");
if (orderList.size() != 0) {
org.jdom.Element orderchange = (org.jdom.Element) orderList.get(0);
String price = orderchange.getAttribute("orderPrice").getValue();
String quantity = bookchange.getAttribute("orderQuantity").getValue();
String symbol = bookchange.getAttribute("orderName").getValue();
} catch(Exception e)
{} -
Help with flex4unit ant build.xml: Socket timeout waiting for flexunit report
I'm having trouble setting up ant to build and test my project locally and I'm not sure what the next step is.
Info:
Running on XP/Cygwin.
All of the files that FlexUnit4 references when used in Flash Builder are in my '${basename}/libs' folder (eg FlexUnit4_1.0.swc).
I've placed the flexunit4 task in my ant/libs folder.
I'm getting two errors...
I don't think I've set up the 'socket' stuff right for the tests. It just sits and waits then dies...
[flexunit] Waiting for client connection ...
(about a minute later)
[flexunit] Stopping server ...
[flexunit] End of test data reached, sending acknowledgement to player ...
[flexunit] Closing client connection ...
[flexunit] Closing server on port [1024] ...
BUILD FAILED
java.util.concurrent.ExecutionException: Socket timeout waiting for flexunit report
Plus this is the error I get from the flash player:
ReferenceError: Error #1065: Variable mx.skins.spark::BorderSkin is not defined.
I don't know why it's complaining about Borderskin as I think I have included all the flex4 libs I could find. I suspect this second error is causing the first error?
Any help appreciated. I think I'm just setting it up all wrong.
Screencap of errors:
http://twitpic.com/l7ay8
build.xml:
http://gist.github.com/20804Finally got everything working using the files from the CI Example which what i probably should have done in the first place.
So a rough guide for anyone just starting out with this:
Download the Flex 4 'workspace' from the digital primates hudson server . This appears to contain flexunit library and examples in various stages of development.
I used Flex Builder 4 Beta 2 to set up my Test Suite and Test Cases.
I then loaded the libs folder from:
workspace.zip\workspace\project\FlexUnit4SampleCIProject
into my flex project's libs folder:
this includes:
FlexUnit4.swc
FlexUnit4CIListener.swc
flexUnit4UIRunner.swc
flexTasks.jar
flexUnitTasks.jar
I didn't need to remove the FlexUnit4 stuff that is 'referenced' automatically by flash builder when you start adding flexunit4 tests/suites.
Then I used a modified version of the TestRunner.mxml found in:
workspace.zip\workspace\project\FlexUnit4SampleCIProject\src\test\flex
The lines to pay attention to are the ones that look like:
static public function currentRunTestSuite():Array {
var testsToRun:Array = new Array();
testsToRun.push(packagename.TestSuiteName);
testsToRun.push(packagename.TestClassName);
return testsToRun;
Just make sure you update this list to include all of the test suites &/or individual tests you want to run.
I made this a static function and modified the code in the "FlexUnitApplication.mxml" file to use this function so i'd only need to update one list of suites/tests.
FlexUnitApplication.mxml is generated automatically when you run FlexUnit4 tests in the Flash Builder 4 Beta 2 IDE.
This is the build.xml file I'm using in the project:
http://gist.github.com/208211
Change the name of the project from "Flare" to whatever and adjust the other path settings where required (though you might want to write this from scratch at least once so you understand roughly what is going on).
The Debug Flash Player must be installed on the server otherwise you'll get a:
java.util.concurrent.ExecutionException: Socket timeout waiting for flexunit report
...while it waits for the non-existant debugger to attach. (This is obvious but I did forget and was a bit bewildered for a moment)
Need to also ensure the environment variable:FLEX_HOME is set to the location you installed the flex sdk...by editing your .bashrc setting the environment variable the in the Hudson Configuration.
You'll need to point Hudson at your ant installation and your jdk installation. If you downloaded he sdk, be aware you might need to point it to the jdk folder inside the place you installed the sdk.
And I think that's all the problems I had. Hope it's useful to someone... if anyone who actually knows what they are doing can point out any potential issues/better ways of doing things, feel free to comment.
Thanks to Brian (legrosb) and Mike (mlabriola) for their assistance! -
This is an academical question. I'm satudying Telecommunications and tomorrow I have an exam about Concurrent Programming.
My questions is quite simple and you can ommit this introduction about what is the exercise if you prefer.
We have seen some ways to pass messages between threads. Once we use an active monitor to take control over the mutex. In this case the active monitor consists of a simple Thread which answers proxys threads petitons for accesing to the mutex. To communicate with the Active Monitor we use s-pipes, which are just a pair of sockets connected where you send messages from one socket and read them from the other. For example we have an array of two sockets, connected: data[0] and data[1].
The proxys thread have all of them the socket data[0] that they use for sending petitions in accesing mutex to the Active Monitor. Anything wrong till here?
We use a BufferedReader (I think) for sending messages through the socket.
Question: Can all these threads use this socket to send petitions without synchronizing it?That's not a problem. I didn't explain all the things which are involved in the program. The Control Thread doesn't answer through the same s-pipe.
So if T1 and T2 ask for acces to mutex, they wait until they recieve a responsen in an another s-pipe only dedicated for each of them. The s-pipe I called data[0] and data[1] is used just for sending requests and nothing else.
So there are:
- A pair of sockets for sending petitions to Control Thread, they are used only in one way. In this case data[0] is the socket in the proxys threads (T1, T2, ....) and data[1] is the socket in the Control Thread.
- A pair of sockets for each proxy thread, for answering petitions of all the Proxy Threads. For example. If we have 3 proxy threads: T1, T2 and T3. There are then: RecieveAskT1[1] which is in T1; RecieveAskT1[0] which is in Control Thread.
RecieveAskT2[1] which is in T1; RecieveAskT2[0] which is in Control Thread.
RecieveAskT3[1] which is in T1; RecieveAskT3[0] which is in Control Thread.
So the problem is with the socket data[0] which is used for T1, T2,...
What is important for me is: if some of the methods which are involved in sending "things" through a socket are synchronized? Otherwise I cannot understand how my professer uses data[0] without protecting it against the scheduler.
Previous thanks for you future answer! -
How to improve the performance of socket ?
how to improve the performance of socket ?
. allocation and deallocation of buffer ?No, that exception is thrown when the underlying
socket (tcp/ip) implementation cannot reserve buffer
space for new sockets afaik. I get it on windows
machines when the concurrent connection load reaches
17-18k connections. I do believe it's configurable
though.And what happens if your max server load is 7-8 connections an hour and you never close the connections?
Maybe you are looking for
-
Problem Using SDN -- Craig Cmehil, Marilyn Pratt Pls Response
Hi! Craig & Marilyn! I cannot be able to search forum i cant get any information suitable to my search. When ever i do a search i am getting the following error, <b>No search results for "ALV". You should try a less restrictive search.
-
Whats the biggest hard disk my PowerMac G5 can hold?
Greetings! I got a hold of a PowerMac G5 recently, rather cool machine! Anyway, i want to use it as a fileserver and also for backups of me and my family members computers so im going to need some big hard disks! Unfortunately PPC macs wont boot from
-
Java.lang.StringIndexOutOfBoundsException: String index out of range:-130
I don't know how to eliminate this problem. Somebody can tell me how
-
After eventually downloading IOS 5, I have not been able to set up the icloud or imessage functions because I can not verify my email as it says it is already in use. Help anyone?
-
Hi, We have installed Terminal Services in Windows 2008 R2 system. Now, we have 300 clients in the network (Xp,Vista, W7, Linux and MAC). Are there some possibility to access with tsweb in linux clients? it is possible with Opera or Firefox? Thanks!