[jitsi-dev] Using Java Sockets


#1

Hi,
Sorry that I'm sending you so many questions. I'm now trying to use PseudoTcpJavaSocketso that I can use it as a normal Java Socket (I need that in order to wrap a SSLSocket around it). My problem with this is that there's no corresponding server-version. I.e. there's no way for me to call Accept(timeout), since Socket in Java doesn't have that (it's in ServerSocket). I tried solving that by first creating a PseudoTcpSocketImpl instance, calling Accept on that and then wrapping a PseudoTcpJavaSocket around that. However, that doesn't work because PseudoTcpJavaSocket doesn't know that it's already connected (because it was created after PseudoTcpSocketImpl created the connection) and there throws
To clarify, my code looks like this (I've added a new constructor to PseudoTcpJavaSocket that accepts PseudoTcpSocketImpl):

PseudoTcpSocketImpl pseudoTcpSocketImpl = new PseudoTcpSocketImpl(0b0100_0000_0000_0000_0000_0000_0000_0000, datagramSocket);
pseudoTcpSocketImpl.setMTU(1492);
int timeout = 30_000;
boolean isInClientMode = iceAgent.isControlling();
if (isInClientMode) {
               pseudoTcpSocketImpl.Connect(remoteTransportAddress, timeout);
} else {
               pseudoTcpSocketImpl.Accept(timeout);
}
SSLSocketFactory sslsocketfactory = (SSLSocketFactory) SSLSocketFactory.getDefault();
PseudoTcpJavaSocket pseudoTcpJavaSocket = new PseudoTcpJavaSocket(pseudoTcpSocketImpl);
SSLSocket sslSocket = (SSLSocket) sslsocketfactory.createSocket(pseudoTcpJavaSocket, remoteNodeID, datagramSocket.getPort(), true);

It then throws the following exception on createSocket:
java.net.SocketException: Underlying socket is not connected
               at sun.security.ssl.SSLSocketImpl.<init>(SSLSocketImpl.java:526) ~[na:1.7.0]
               at sun.security.ssl.SSLSocketFactoryImpl.createSocket(SSLSocketFactoryImpl.java:109) ~[na:1.7.0]
               at com.degoo.ice4j.JingleConnection$MessageReadThread.run(JingleConnection.java:316) ~[classes/:na]

How do I solve this? If there some extra code needed in ice4j to handle this then I'll gladly help. I just need some pointers on where to start.

Regards
Carl


#2

Hi,

My problem with this is that there's no corresponding server-version.
I.e. there's no way for me to call Accept(timeout), since Socket in Java
doesn't have that (it's in ServerSocket).

I don't know how to implement ServerSocket or if it is possible. To solve
this you can expose Accept method in PseudoTcpJavaSocket so that it will be
easier to use.

However, that doesn't work because PseudoTcpJavaSocket doesn't know that
it's already connected (because it was created after PseudoTcpSocketImpl
created the connection) and there throws

To clarify, my code looks like this (I've added a new constructor to
PseudoTcpJavaSocket that accepts PseudoTcpSocketImpl):****

** **

PseudoTcpSocketImpl pseudoTcpSocketImpl = new
PseudoTcpSocketImpl(0b0100_0000_0000_0000_0000_0000_0000_0000,
datagramSocket);****

pseudoTcpSocketImpl.setMTU(1492);****

int timeout = 30_000;****

boolean isInClientMode = iceAgent.isControlling();****

if (isInClientMode) {****

               pseudoTcpSocketImpl.Connect(remoteTransportAddress,
timeout);****

} else {****

               pseudoTcpSocketImpl.Accept(timeout);****

}****

SSLSocketFactory sslsocketfactory = (SSLSocketFactory)
SSLSocketFactory.getDefault();****

PseudoTcpJavaSocket pseudoTcpJavaSocket = new
PseudoTcpJavaSocket(pseudoTcpSocketImpl);****

SSLSocket sslSocket = (SSLSocket)
sslsocketfactory.createSocket(pseudoTcpJavaSocket, remoteNodeID,
datagramSocket.getPort(), true);****

** **

It then throws the following exception on createSocket: ****

java.net.SocketException: Underlying socket is not connected****

               at
sun.security.ssl.SSLSocketImpl.<init>(SSLSocketImpl.java:526) ~[na:1.7.0]*
***

               at
sun.security.ssl.SSLSocketFactoryImpl.createSocket(SSLSocketFactoryImpl.java:109)
~[na:1.7.0]****

               at
com.degoo.ice4j.JingleConnection$MessageReadThread.run(JingleConnection.java:316)
~[classes/:na]****

** **

How do I solve this?

There is public method isConnected in java.net.Socket. I don't know how
exactly Socket is used internally by SSLSocketFactory.createSocket()
method. You can try to override some methods and put print out in them to
figure out how it is used by SSLSocketFactory and maybe later with
SSLSocket in case of more problems.

If there some extra code needed in ice4j to handle this then I'll gladly
help. I just need some pointers on where to start.****

I was planing to use PseudoTcpJavaSocket with Apache HttpClient library
however finally I didn't decided to do that, so current implementation
isn't complete and well tested. It would be great if you could share any
improvements :slight_smile:
You should look at methods that belong to java.net.SocketImpl in
PseudoTcpSocketImpl class and methods of java.net.Socket that may be
overriden in PseudoTcpJavaSocket

···

2012/8/15 Carl Hasselskog <carl@degoo.com>

--
Regards, Paweł Domas


#3

Hi all,

I still have problems to establish a working video/audio conference with libjitsi.
Video streams are now quite stable and visible on all clients using an RTPTranslator on conference focus site.
Is it excepted to have also an RTPTranslator for the audio streams or just an AudioMixer on the conference focus site?

When I use MediaService.createMixer() as audio device on conference focus site, the conference focus hears all clients and all clients the conference focus but between the clients is silence. When I use additionally an RTPTranslator the clients can hear audio but it seems to not mixed and the video gets quite useless as there are a lot of artefacts.

So, what would be the right approach to establish an audio conference where all "voices" are mixed into one stream?
Is a video/audio conference already 100% supported by libjitsi?
Thanks in advance.


#4

Hi,
I've now implemented an extended ServerSocket for pseudo-tcp. It works well in my tests (I've successfully sent data over an SSLSocket, that uses PseudoTcpSocketImpl as its underlying socket). See attached. I use it like this:

PseudoTcpSocketImpl pseudoTcpSocketImpl = new PseudoTcpSocketImpl(0b0100_0000_0000_0000_0000_0000_0000_0000, datagramSocket);
int timeout = 30_000;
boolean isInClientMode = iceAgent.isControlling();
PseudoTcpJavaSocket pseudoTcpJavaSocket;
if (isInClientMode) {
                pseudoTcpJavaSocket = new PseudoTcpJavaSocket(pseudoTcpSocketImpl);
                pseudoTcpJavaSocket.connect(remoteTransportAddress, timeout);
} else {
                PseudoTcpJavaServerSocket pseudoTcpJavaServerSocket = new PseudoTcpJavaServerSocket(pseudoTcpSocketImpl);
                pseudoTcpJavaSocket = pseudoTcpJavaServerSocket.accept();
}

My solution is sort of a hack because ServerSocket.setSocketFactory is static for some very strange reason (I've asked about it here http://stackoverflow.com/questions/11982698/why-is-serversocket-setsocketfactory-static but no one seems to know why). This forces me to synchronize on a static field, in order to ensure that concurrent calls to accept() don't interfere with each other.

Feel free to use the code however you like!

Regards
Carl

PseudoTcpJavaServerSocket.java (1.75 KB)

PseudoTcpJavaSocket.java (690 Bytes)

···

From: Paweł Domas [mailto:paweldomas@gmail.com]

Sent: den 15 augusti 2012 15:49
To: dev@jitsi.java.net
Subject: [jitsi-dev] Re: Using Java Sockets

Hi,
2012/8/15 Carl Hasselskog <carl@degoo.com<mailto:carl@degoo.com>>
My problem with this is that there's no corresponding server-version. I.e. there's no way for me to call Accept(timeout), since Socket in Java doesn't have that (it's in ServerSocket).

I don't know how to implement ServerSocket or if it is possible. To solve this you can expose Accept method in PseudoTcpJavaSocket so that it will be easier to use.

However, that doesn't work because PseudoTcpJavaSocket doesn't know that it's already connected (because it was created after PseudoTcpSocketImpl created the connection) and there throws
To clarify, my code looks like this (I've added a new constructor to PseudoTcpJavaSocket that accepts PseudoTcpSocketImpl):

PseudoTcpSocketImpl pseudoTcpSocketImpl = new PseudoTcpSocketImpl(0b0100_0000_0000_0000_0000_0000_0000_0000, datagramSocket);
pseudoTcpSocketImpl.setMTU(1492);
int timeout = 30_000;
boolean isInClientMode = iceAgent.isControlling();
if (isInClientMode) {
               pseudoTcpSocketImpl.Connect(remoteTransportAddress, timeout);
} else {
               pseudoTcpSocketImpl.Accept(timeout);
}
SSLSocketFactory sslsocketfactory = (SSLSocketFactory) SSLSocketFactory.getDefault();
PseudoTcpJavaSocket pseudoTcpJavaSocket = new PseudoTcpJavaSocket(pseudoTcpSocketImpl);
SSLSocket sslSocket = (SSLSocket) sslsocketfactory.createSocket(pseudoTcpJavaSocket, remoteNodeID, datagramSocket.getPort(), true);

It then throws the following exception on createSocket:
java.net.SocketException: Underlying socket is not connected
               at sun.security.ssl.SSLSocketImpl.<init>(SSLSocketImpl.java:526) ~[na:1.7.0]
               at sun.security.ssl.SSLSocketFactoryImpl.createSocket(SSLSocketFactoryImpl.java:109) ~[na:1.7.0]
               at com.degoo.ice4j.JingleConnection$MessageReadThread.run(JingleConnection.java:316) ~[classes/:na]

How do I solve this?

There is public method isConnected in java.net.Socket. I don't know how exactly Socket is used internally by SSLSocketFactory.createSocket() method. You can try to override some methods and put print out in them to figure out how it is used by SSLSocketFactory and maybe later with SSLSocket in case of more problems.

If there some extra code needed in ice4j to handle this then I'll gladly help. I just need some pointers on where to start.

I was planing to use PseudoTcpJavaSocket with Apache HttpClient library however finally I didn't decided to do that, so current implementation isn't complete and well tested. It would be great if you could share any improvements :slight_smile:
You should look at methods that belong to java.net.SocketImpl in PseudoTcpSocketImpl class and methods of java.net.Socket that may be overriden in PseudoTcpJavaSocket

--
Regards, Paweł Domas


#5

Hey Rene,

Hi all,

I still have problems to establish a working video/audio conference with
libjitsi.

Well, they are still a work in progress so that's not entirely unexpected :slight_smile:

Video streams are now quite stable and visible on all clients using an
RTPTranslator on conference focus site.
Is it excepted to have also an RTPTranslator for the audio streams or
just an AudioMixer on the conference focus site?

IIRC we did make sure that translation also worked for audio but mixing
has been tested a lot more.

When I use MediaService.createMixer() as audio device on conference
focus site, the conference focus hears all clients and all clients the
conference focus but between the clients is silence.

That's the approach we use in Jitsi so it should be working. You might
want to check if you handle this any differently than we do there.

When I use
additionally an RTPTranslator the clients can hear audio but it seems to
not mixed and the video gets quite useless as there are a lot of artefacts.

So, what would be the right approach to establish an audio conference
where all "voices" are mixed into one stream?
Is a video/audio conference already 100% supported by libjitsi?

Audio conferences have been working well for quite a while now. We are
just getting started with video though.

Hope this helps,
Emil

···

On 15.08.12, 20:58, Rene Lamotte wrote:


#6

Hey Carl

I've now implemented an extended ServerSocket for pseudo-tcp. It works
well in my tests (I've successfully sent data over an SSLSocket, that
uses PseudoTcpSocketImpl as its underlying socket). See attached. I use
it like this:

[snip code]

My solution is sort of a hack because ServerSocket.setSocketFactory is
static for some very strange reason (I've asked about it here
http://stackoverflow.com/questions/11982698/why-is-serversocket-
setsocketfactory-static
<http://stackoverflow.com/questions/11982698/why-is-
serversocket-setsocketfactory-static> but no one seems to know why).
This forces me to synchronize on a static field, in order to ensure that
concurrent calls to accept() don't interfere with each other.

I think I can kind of answer that.
The idea of a factory is that code, that needs a certain object calls the
factory to obtain that object. The difference between simply creating the
object with new Xy() is that the factory may return whatever implementation
it would like to - as long as the returned object adheres to the declared
interface.
ServerSocket.setSocketFactory is a method to replace the /default/ factory
for sockets of the entire Java application. If you absolutely need data in
your custom socket that isn't provided by the arguments of the factory, your
pretty much out of luck as it is a limitation of the factory interface (the
foreign code that calls the factory doesn't know of any more data to
provide).

The idea of locking some field in a socket to call accept() sounds totally
wrong.
I'm not sure if follow the code flow correctly (it's been a while since I've
dealt with SocketFactory), but at the time accept() is called, the socket is
already created for a "long" time. Why is it necessary to change the factory
at this point?

I haven't followed the whole PseudoTCP-discussion really, so sorry if I jump
onto something...

Feel free to use the code however you like!

Regards
Carl

Regards,
Ingo

.


#7

Seems that I've hijacked an other one's thread. Sorry about that.

Hi all,

I still have problems to establish a working video/audio conference with
libjitsi.

Well, they are still a work in progress so that's not entirely unexpected :slight_smile:

Video streams are now quite stable and visible on all clients using an
RTPTranslator on conference focus site.
Is it excepted to have also an RTPTranslator for the audio streams or
just an AudioMixer on the conference focus site?

IIRC we did make sure that translation also worked for audio but mixing
has been tested a lot more.

Ok, will concentrate more on mixing then.

When I use MediaService.createMixer() as audio device on conference
focus site, the conference focus hears all clients and all clients the
conference focus but between the clients is silence.

That's the approach we use in Jitsi so it should be working. You might
want to check if you handle this any differently than we do there.

When I use
additionally an RTPTranslator the clients can hear audio but it seems to
not mixed and the video gets quite useless as there are a lot of artefacts.

So, what would be the right approach to establish an audio conference
where all "voices" are mixed into one stream?
Is a video/audio conference already 100% supported by libjitsi?

Audio conferences have been working well for quite a while now. We are
just getting started with video though.

Ok, will provide feedback when I get it working as expected.

···

Hope this helps,
Emil


#8

I understand how a factory works and I agree that a different solution is preferable. If you have any suggestions I'd gladly change to that. However, I still don't understand why they make the factory a static global variable. What if you want different sockets in different parts of your application? Introducing more global state for no apparent reason doesn't seem that clever.

I suspect that in order to solve this one needs to refactor PseudoTcpSocketImpl so that it can be created with no parameters sent to the constructor and then have Socket initialize the PseudoTcpSocketImpl-instance. Unfortunately I don't have enough experience with neither PseudoTcpSocketImpl nor Socket to do that. Also Socket seems a bit messy, with many circular dependencies and complex flow, so the risk of something going wrong during that refactoring is quite high.

Regards
Carl

···

-----Original Message-----

From: Ingo Bauersachs [mailto:ingo@sip-communicator.org] On Behalf Of Ingo Bauersachs

Sent: den 17 augusti 2012 02:52
To: dev@jitsi.java.net
Subject: [jitsi-dev] Re: Using Java Sockets

Hey Carl

I've now implemented an extended ServerSocket for pseudo-tcp. It works
well in my tests (I've successfully sent data over an SSLSocket, that
uses PseudoTcpSocketImpl as its underlying socket). See attached. I
use it like this:

[snip code]

My solution is sort of a hack because ServerSocket.setSocketFactory is
static for some very strange reason (I've asked about it here
http://stackoverflow.com/questions/11982698/why-is-serversocket-
setsocketfactory-static
<http://stackoverflow.com/questions/11982698/why-is-
serversocket-setsocketfactory-static> but no one seems to know why).
This forces me to synchronize on a static field, in order to ensure
that concurrent calls to accept() don't interfere with each other.

I think I can kind of answer that.
The idea of a factory is that code, that needs a certain object calls the factory to obtain that object. The difference between simply creating the object with new Xy() is that the factory may return whatever implementation it would like to - as long as the returned object adheres to the declared interface.
ServerSocket.setSocketFactory is a method to replace the /default/ factory for sockets of the entire Java application. If you absolutely need data in your custom socket that isn't provided by the arguments of the factory, your pretty much out of luck as it is a limitation of the factory interface (the foreign code that calls the factory doesn't know of any more data to provide).

The idea of locking some field in a socket to call accept() sounds totally wrong.
I'm not sure if follow the code flow correctly (it's been a while since I've dealt with SocketFactory), but at the time accept() is called, the socket is already created for a "long" time. Why is it necessary to change the factory at this point?

I haven't followed the whole PseudoTCP-discussion really, so sorry if I jump onto something...

Feel free to use the code however you like!

Regards
Carl

Regards,
Ingo


#9

When I use MediaService.createMixer() as audio device on conference
focus site, the conference focus hears all clients and all clients the
conference focus but between the clients is silence.

That's the approach we use in Jitsi so it should be working. You might
want to check if you handle this any differently than we do there.

Audio conferences have been working well for quite a while now. We are
just getting started with video though.

Ok, I think I managed to get a working scenario but I've run into some problems and would like to have them confirmed.

It seems, that in order to mix the audio streams, the conference focus media streams must have a valid capture device configured and must have a sending media direction.

At first sight this sounds logical but this leads into a big (for me :-)) problem:
When the conference focus peer disables the microphone, nobody in the conference can hear any other peer as there is no more audio data sent by the conference focus.

Even worse, it seems to be impossible to implement an audio chat with a conference focus that acts only as a relay.
Please correct me if I'm wrong.

Is it somehow possible to do audio mixing and sending to all peers without having a microphone activated on conference focus site (only mixing and forwarding the audio of all connected peers)?

Ok, will provide feedback when I get it working as expected.

Done with this mail. :wink:


#10

Carl, Pawel

I understand how a factory works and I agree that a different solution
is preferable. If you have any suggestions I'd gladly change to that.
However, I still don't understand why they make the factory a static
global variable. What if you want different sockets in different parts
of your application? Introducing more global state for no apparent
reason doesn't seem that clever.

That is simply for the /default/ factory. If you need different sockets in
different parts of the application, simply create the needed factory and
call it directly:
new MyFactory().create(...)

I suspect that in order to solve this one needs to refactor
PseudoTcpSocketImpl so that it can be created with no parameters sent to

the

constructor and then have Socket initialize the

PseudoTcpSocketImpl-instance.

Unfortunately I don't have enough experience with neither

PseudoTcpSocketImpl

nor Socket to do that. Also Socket seems a bit messy, with many circular
dependencies and complex flow, so the risk of something going wrong during
that refactoring is quite high.

I don't really know the all the sockets stuff, even less for PseudoTCP, and
just by looking at the framework-design from java.net.*, the classes should
export the following:
- PseudoTcpSocketImpl should not really be visible to/used by clients (after
all, it is an "Impl")
- PseudoTcpJavaServerSocket should have a constructor on which
address/port/however-pseudoTcp-identifies-its-peer it should listen on (just
like java.net.ServerSocket)
- PseudoTcpJavaServerSocket.accept returns a newly created
PseudoTcpJavaSocket

(btw., Pawel, why is there a "Java" in the class name?)

Carl, the whole factory seems unnecessary. If you create a new
PseudoTcpJavaSocket inside accept it's Impl is used without calling the
factory.
http://docs.oracle.com/javase/6/docs/technotes/guides/net/extendingSocks.htm
l

Regards
Carl

I somehow have the feeling I missed something obvious...

HTH,
Ingo


#11

When I use MediaService.createMixer() as audio device on conference
focus site, the conference focus hears all clients and all clients the
conference focus but between the clients is silence.

That's the approach we use in Jitsi so it should be working. You might
want to check if you handle this any differently than we do there.

Audio conferences have been working well for quite a while now. We are
just getting started with video though.

Ok, I think I managed to get a working scenario but I've run into some
problems and would like to have them confirmed.

It seems, that in order to mix the audio streams, the conference focus
media streams must have a valid capture device configured and must have
a sending media direction.

At first sight this sounds logical but this leads into a big (for me
:-)) problem:
When the conference focus peer disables the microphone, nobody in the
conference can hear any other peer as there is no more audio data sent
by the conference focus.

Even worse, it seems to be impossible to implement an audio chat with a
conference focus that acts only as a relay.
Please correct me if I'm wrong.

Is it somehow possible to do audio mixing and sending to all peers
without having a microphone activated on conference focus site (only
mixing and forwarding the audio of all connected peers)?

Well, it is currently possible to have Jitsi act as focus and be on
mute. Does this work for you?

The same thing is not possible for video but would be possible real soon
(like this week).

It also sounds like you might be needing something that looks a lot more
like Jitsi Videobridge. We are currently working on that.

Emil

···

On 16.08.12, 00:18, Rene Lamotte wrote:

Ok, will provide feedback when I get it working as expected.

Done with this mail. :wink:

--
Emil Ivov, Ph.D. 67000 Strasbourg,
Project Lead France
Jitsi
emcho@jitsi.org PHONE: +33.1.77.62.43.30
http://jitsi.org FAX: +33.1.77.62.47.31


#12

Hi,

Sorry for all that mess. I've commited the SocketImpl maybe too early. I
didn't had time to polish it as I wanted to push GSoC work as far as it's
possible. But now it will be my priority.

I don't really know the all the sockets stuff, even less for PseudoTCP, and
just by looking at the framework-design from java.net.*, the classes should
export the following:
- PseudoTcpSocketImpl should not really be visible to/used by clients
(after
all, it is an "Impl")

- PseudoTcpJavaServerSocket should have a constructor on which

address/port/however-pseudoTcp-identifies-its-peer it should listen on
(just
like java.net.ServerSocket)

  I agree on that.

- PseudoTcpJavaServerSocket.accept returns a newly created

PseudoTcpJavaSocket

This would require many changes in the protocol and some "connection"
system which will multiplex packets between different clients. Maybe I'll
do that in future. At the moment there can be only one client connected to
the socket.

(btw., Pawel, why is there a "Java" in the class name?)

It was intended to use mainly PseudoTcpSocketImpl because of missing

accept method for example. PseudoTcpJavaSocket name is because it
implements "java.net".Socket and it was inteded to use with some APIs or
libraries that offer some specific functionality for java.net.Socket
classes. It will never be able to replace normal java.net.Socket. I mean it
can not be plugged into the application in order to replace system TCP
sockets.

···

2012/8/17 Ingo Bauersachs <ingo@jitsi.org>

--
Regards, Paweł Domas


#13

I agree that we should expose PseudoTcpJavaServerSocket instead of PseudoTcpSocketImpl.

Regarding the factory problem: I know that one can simply create a new factory. The problem is the way ServerSocket uses the static factory. If you look in implAccept(Socket s) you can see that it gets its SocketImpl instance by calling getImpl() -> createImpl() -> setImpl(). In setImpl() it uses the static factory field if it's !=null, otherwise it calls new SocksSocketImpl(). That's why I think the only way to make ServerSocket use PseudoTcpSocketImpl when accepting is by setting the instance in static factory and synchronizing on accept. I'm gladly proven wrong though, because it's definitely a non-optimal solution!

Regards
Carl

···

-----Original Message-----

From: Ingo Bauersachs [mailto:ingo@sip-communicator.org] On Behalf Of Ingo Bauersachs

Sent: den 17 augusti 2012 22:36
To: dev@jitsi.java.net
Subject: [jitsi-dev] Re: Using Java Sockets

Carl, Pawel

I understand how a factory works and I agree that a different solution
is preferable. If you have any suggestions I'd gladly change to that.
However, I still don't understand why they make the factory a static
global variable. What if you want different sockets in different parts
of your application? Introducing more global state for no apparent
reason doesn't seem that clever.

That is simply for the /default/ factory. If you need different sockets in different parts of the application, simply create the needed factory and call it directly:
new MyFactory().create(...)

I suspect that in order to solve this one needs to refactor
PseudoTcpSocketImpl so that it can be created with no parameters sent
to

the

constructor and then have Socket initialize the

PseudoTcpSocketImpl-instance.

Unfortunately I don't have enough experience with neither

PseudoTcpSocketImpl

nor Socket to do that. Also Socket seems a bit messy, with many
circular dependencies and complex flow, so the risk of something going
wrong during that refactoring is quite high.

I don't really know the all the sockets stuff, even less for PseudoTCP, and just by looking at the framework-design from java.net.*, the classes should export the following:
- PseudoTcpSocketImpl should not really be visible to/used by clients (after all, it is an "Impl")
- PseudoTcpJavaServerSocket should have a constructor on which address/port/however-pseudoTcp-identifies-its-peer it should listen on (just like java.net.ServerSocket)
- PseudoTcpJavaServerSocket.accept returns a newly created PseudoTcpJavaSocket

(btw., Pawel, why is there a "Java" in the class name?)

Carl, the whole factory seems unnecessary. If you create a new PseudoTcpJavaSocket inside accept it's Impl is used without calling the factory.
http://docs.oracle.com/javase/6/docs/technotes/guides/net/extendingSocks.htm
l

Regards
Carl

I somehow have the feeling I missed something obvious...

HTH,
Ingo


#14

Well, it is currently possible to have Jitsi act as focus and be on
mute. Does this work for you?

Ok, a first quick and dirty try has been successful. Will do more tests tomorrow. Thanks for the hint, this didn't come into my mind.

The same thing is not possible for video but would be possible real soon
(like this week).

Hmmm, I guess we won't need that as the video is relatively stable with translation. I guess the rtp translator doesn't care about the MediaDirection because even with RECVONLY on conference focus site the video is transmitted ok to all peers.

It also sounds like you might be needing something that looks a lot more
like Jitsi Videobridge. We are currently working on that.

Do you have some more info about that? Another spin off?


#15

Sorry for all that mess. I've commited the SocketImpl maybe too early. I
didn't had time to polish it as I wanted to push GSoC work as far as it's
possible. But now it will be my priority.

An open source mantra is "commit early, commit often", so it is fine if your
code is not finished. However IMO it should be in a clean state (always
compilable and adhering to the rules of the project). But this was other
developers are for: review and help :slight_smile:

I don't really know the all the sockets stuff, even less for PseudoTCP,
and just by looking at the framework-design from java.net.*, the
classes should export the following:
- PseudoTcpSocketImpl should not really be visible to/used by clients
(after all, it is an "Impl")

- PseudoTcpJavaServerSocket should have a constructor on which
address/port/however-pseudoTcp-identifies-its-peer it should listen on
(just like java.net.ServerSocket)

  I agree on that.

- PseudoTcpJavaServerSocket.accept returns a newly created
PseudoTcpJavaSocket

This would require many changes in the protocol and some "connection"

system

which will multiplex packets between different clients. Maybe I'll do that

in

future. At the moment there can be only one client connected to the

socket.

Huh? Maybe this is how PseudoTCP works - I have no idea. But I had the
impression that a ServerSocket can be created by simply spawning a new
Socket on the server when a client connects. You still have a 1:1
relationship between the client and the server.

(btw., Pawel, why is there a "Java" in the class name?)

It was intended to use mainly PseudoTcpSocketImpl because of missing

accept

method for example.

Well that is how Java intends to write custom sockets.

PseudoTcpJavaSocket name is because it implements
"java.net".Socket and it was inteded to use with some APIs or libraries

that

offer some specific functionality for java.net.Socket classes.

Please drop the "Java" part, it is unnecessary. PseudoTcpSocket will do just
fine to represent what it does.

It will never
be able to replace normal java.net.Socket. I mean it can not be plugged

into

the application in order to replace system TCP sockets.

Maybe not, but it should nonetheless be as compatible as possible.

Regards,
Ingo

···

2012/8/17 Ingo Bauersachs <ingo@jitsi.org>


#16

handlers which are sharing the same DatagramSocket. For now it is not
written that way. PseudoTCP now is implemented that when server gets first
valid PTCP packet it stores remote socket address and ignores all packets
that come from different host. If I would like to spawn new socket for each
new connected client I would have to dispatch these packets to/from
appropriate hosts. There will be 1:1 relationship between the client and
the server, but there is also required some kind of manager who will
coordinate actions on shared DatagramSocket.

···

2012/8/19 Ingo Bauersachs <ingo@jitsi.org>

>> - PseudoTcpJavaServerSocket.accept returns a newly created
>> PseudoTcpJavaSocket
>
> This would require many changes in the protocol and some "connection"
system
> which will multiplex packets between different clients. Maybe I'll do
that
in
> future. At the moment there can be only one client connected to the
socket.

Huh? Maybe this is how PseudoTCP works - I have no idea. But I had the
impression that a ServerSocket can be created by simply spawning a new
Socket on the server when a client connects. You still have a 1:1
relationship between the client and the server.

Yes it should work that way but there are required many PseudoTCP state

--
Regards, Paweł Domas


#17

Regarding the factory problem: I know that one can simply create a new
factory. The problem is the way ServerSocket uses the static factory. If

you

look in implAccept(Socket s) you can see that it gets its SocketImpl

instance

by calling getImpl() -> createImpl() -> setImpl(). In setImpl() it uses

the

static factory field if it's !=null, otherwise it calls new
SocksSocketImpl(). That's why I think the only way to make ServerSocket

use

PseudoTcpSocketImpl when accepting is by setting the instance in static
factory and synchronizing on accept. I'm gladly proven wrong though,

because

it's definitely a non-optimal solution!

Well, you're right. I made a total confusion with the creation of the Impl
for the Socket itself and the ServerSocket (implAccept uses the Impl of the
passed Socket, but not for the ServerSocket).

Ingo


#18

Well, in your defence it should have been implemented the way you assumed it was. That would have been a lot better. :slight_smile:

···

-----Original Message-----

From: Ingo Bauersachs [mailto:ingo@sip-communicator.org] On Behalf Of Ingo Bauersachs

Sent: den 19 augusti 2012 23:26
To: dev@jitsi.java.net
Subject: [jitsi-dev] Re: Using Java Sockets

Regarding the factory problem: I know that one can simply create a new
factory. The problem is the way ServerSocket uses the static factory.
If

you

look in implAccept(Socket s) you can see that it gets its SocketImpl

instance

by calling getImpl() -> createImpl() -> setImpl(). In setImpl() it
uses

the

static factory field if it's !=null, otherwise it calls new
SocksSocketImpl(). That's why I think the only way to make
ServerSocket

use

PseudoTcpSocketImpl when accepting is by setting the instance in
static factory and synchronizing on accept. I'm gladly proven wrong
though,

because

it's definitely a non-optimal solution!

Well, you're right. I made a total confusion with the creation of the Impl for the Socket itself and the ServerSocket (implAccept uses the Impl of the passed Socket, but not for the ServerSocket).

Ingo


#19

Well, it is currently possible to have Jitsi act as focus and be on
mute. Does this work for you?

Ok, a first quick and dirty try has been successful. Will do more tests tomorrow. Thanks for the hint, this didn't come into my mind.

One more quick note...
It seems that a audio/video session on a quad core 2,6 ghz pc with 4gb ram uses something around 65% of cpu when doing audio mixing. Is this known to be than cpu intensive or do you think there must be something wrong with my code?

···

Am 16.08.2012 01:49, schrieb Rene Lamotte:

The same thing is not possible for video but would be possible real soon
(like this week).

Hmmm, I guess we won't need that as the video is relatively stable with translation. I guess the rtp translator doesn't care about the MediaDirection because even with RECVONLY on conference focus site the video is transmitted ok to all peers.

It also sounds like you might be needing something that looks a lot more
like Jitsi Videobridge. We are currently working on that.

Do you have some more info about that? Another spin off?


#20

Okay, I see that it's a bit more complicated than I thought to separate the
client and server socket. Just some random thoughts for a possible
implementation:
- Create a "Master"-DatagramSocket inside PseudoTcpServerSocket
- Based on the source address, create a PseudoTcpSocket whose underlying
DatagramSocket is "connected" [1]

Not sure if it's possible to create multiple DatagramSockets with the same
listening address. If not use a copy-on-write map in the
PseudoTcpServerSocket that is cleaned up when the TCP-socket is closed or
timed out.

Ingo

[1]
http://docs.oracle.com/javase/1.4.2/docs/api/java/net/DatagramSocket.html#co
nnect(java.net.SocketAddress)

···

2012/8/19 Ingo Bauersachs <ingo@jitsi.org>

- PseudoTcpJavaServerSocket.accept returns a newly created
PseudoTcpJavaSocket

This would require many changes in the protocol and some "connection"
system which will multiplex packets between different clients.
Maybe I'll do that in future. At the moment there can be only
one client connected to the socket.

Huh? Maybe this is how PseudoTCP works - I have no idea. But I had the
impression that a ServerSocket can be created by simply spawning a new
Socket on the server when a client connects. You still have a 1:1
relationship between the client and the server.

Yes it should work that way but there are required many PseudoTCP state
handlers which are sharing the same DatagramSocket. For now it is not
written that way. PseudoTCP now is implemented that when server gets
first valid PTCP packet it stores remote socket address and ignores all
packets that come from different host. If I would like to spawn new
socket for each new connected client I would have to dispatch these
packets to/from appropriate hosts. There will be 1:1 relationship
between the client and the server, but there is also required some kind
of manager who will coordinate actions on shared DatagramSocket.