Memoria Compartilhada isso existe em Java?

Galera é o seguinte,

Eu tenho duas aplicações diferentes, que devem trocar informação entre si, esta aplicação foi desenvolvida em C++.

O negocio é o seguinte elas se comunicam entre si, através de uma Share Memory.

Agora eu tenho que migrar essas aplicações para Java.

Gostaria de Saber se existe Share Memory em Java. Ou uma Forma mais simples de trocar informações entre as duas aplicações, tem que ser uma forma MUITO RÁPIDA, por isso a Share Memory.

Muito Obrigado GUJeiros, vc’s tem me ajudado muito.

Olá

Acho que sim, usando Java.nio, conceitos direct buffers ou memory mapped files.

Se seus dados são muitos e vc usa arquivo de memória mapeada do tipo MapViewOfFile e CreateFileMapping/OpenFileMapping para compartilhar dados de um arquivo entre processos então acho que pode usar o conceito Memory-Mapped files do java.nio. Pode ser que a performance seja diferente pois não se pode comparar Java com C. Para mim, mesmo que o Java ainda não permita fazer tudo que o C faz, acho mais fácil fazer com Java que por exemplo se programa igual no WinNT/2000/XP e no Win98/ME/Pokemon.

Recomendo o livro Java NIO do Ron Hitchens. Baixe os exemplos de http://www.javanio.info/filearea/bookexamples/
Veja:
http://www.javanio.info/filearea/bookexamples/unpacked/com/ronsoft/books/nio/channels/
MappedHttp.java
MapFile.java
ChannelTransfer.java

Veja http://www.onjava.com/lpt/a/2742 (itens 6 e principalmente 5) e leia tudo que encontrar de java.nio, especialmente sobre os métodos map() ***, transferTo() e transferFrom() da classe FileChannel

*** retorna um MappedByteBuffer então precisa estudar tb esta classe e as demais da API Buffer

Acho que é isto, talvez tenha dito bobagem pois C/Win32 não está no meu dia a dia.

[]s
Luca

Nao sei qual a natureza de ambas as aplicacoes, mas o java apresenta um ambiente multithread, onde as variaveis podems ser compartilhadas entre as threads. Isso eh ainda tende a ser mais rapido que o modelo de shared memory que voce apresentou (claro que dependendo do suporte do SO).
O incoveniente eh que voce deve rodar as duas aplicacoes na mesma JVM. Se isso nao for um empecilho para voce, basta entao botar as variaveis que voce necessita compartilhar num singleton, por exemplo, e acessar das duas aplicacao.

Agora se realmente eh necessario que as duas aplicacoes rodem em JVM separadas, voce tera um trabalho um pouco mair, talvez pesquisando NIO, como sugeriu o post anterior, voce ache uma alternativa equivalente ao Shared memory do C.

Valeu Luca, vou ler sobre o assunto, valeu mesmo.
Valeu tanque, mas é ai que o bicho pega, pode sem em diferente JVM

Mas surgiu outra duvida, falando com alguns amigos, eles me falaram para utilizar socket, para comunicação entre os dois aplicativos, eles me disseram que seria muito mais fácil e ainda a aplicação ficaria mais distribuída.

Eu pergunto, se eu utilizar socket, será que terá uma queda muito grande na velocidade da troca de informações ???

Pq, pelo que percebi socket é muitttttttttooooooo mais fácil que usar esse NIO !!!

O que vc’s acham ???

Olá

O que o tanque falou foi muito bem lembrado para comunicação entre processos diferentes na mesma JVM. É possível uma applet carregar uma classe de outra. O bicho pega na mesma JVM quando são aplicações feitas por empresas diferentes e há conflito de nomes ou na captura dos eventos.

Nem falei em sockets porque pensei que se sockets fossem viáveis já estariam sendo usados no C++. Mas na verdade sockets devem resolver muitíssimo bem. É fácil usar e agora com o java.nio ficou bem melhor. Sei de aplicações bastante complexas que usam sockets para trocar dados e inclusive chamar classes na outra aplicação.

O caso dos Channels do java.nio seria apenas no caso de muitos dados onde é viável usar memory mapped files. Veja http://java.sun.com/developer/qow/archive/183/index.jsp

A própria API java.nio chama a atenção que para a maioria dos SOs é melhor usar os métodos tradicionais de leitura e gravação em um arquivo de acesso sincronizado quando se lida com pequenos conjuntos de dados.

Uma pergunta: o que vc quer fazer tem a ver com sua outra pergunta sobre DSM e este DSM é Distributed Shared Memory?

[]s
Luca

Uma alternativa seria compartilhar objetos via JNDI para mais de uma VM.

Veja esse artigo do Java World:

:arrow: http://www.javaworld.com/javaworld/jw-07-1999/jw-07-cooltools.html

Sockets são muito mais lentos que memoria mapeada quando voce está no C, mas em java a situação é bem diferente.

Em java consigo os seguintes números num p4 2.4C:

-java.nio sockets: 400mB/s via loopback
-java.io sockets: 300mB/s via lookback
-mmio 155mB/s

Todos os testes foram executados usando 2 threads, então a performance com socket deve cair muito mais quando 2 processos forem usados que com mmio. Sun JVM 1.4.2 -server.

Moral da historia, a implementação de memory mapping da Sun para java deixa a desejar. Use sockets que vai estar tudo ok. Se voce precisa de mais banda que qualquer uma dessas opções, sugiro desistir do java.

Olá

ecarmo, vc ainda está devendo a resposta sobre a questão de computação paralela, DSM, etc.

Louds, pode explicar melhor seus testes?

Para mim os resultados favoráveis ao memory mapped IO deveriam ocorrer só nos casos da transmissão de blocos grandes. O que entendo por grandes? NÃO SEI, precisaria preparar uma bateria de testes. Foi isto q vc fez?

[]s
Luca

Existe outra coisa importante, o suporte do SO a tecnologia de memory mapped IO. Caso o suporte do SO seja ruim ou ate nulo, a JVM da SUN teria que emular o recurso, o que justificaria os baixos resultados. Ja se o SO tiver um bom suporte ao recurso e a performance ainda ficar sofrivel, ai sim poderemos xingar a JVM da sun.

Conheco muito pouco sobre o NIO, mas se o que estao sugerindo usar eh o memory mapped file (equivalente ao mmap do unix) realmente a performance tende a ser mais baixa que outras alternativas tipo socket, com rarissimas excessoes. Ainda mais em ambiente windows, onde acredito que nao exista algo equivalente ao mmap.

O ideal seria mesmo o uso do recurso de shared memory (shmctl, shmat) isso acredito que exista equivalentes para windows. Se isso for acessivel pela NIO, beleza, espera-se um desempenho equivalente a solucao em C. Senao vai ser mesmo o negocio via socket eh a saida, com desempenho menor que o desta solucao em C usando estes recursos.

Meus tentes foram bem simples: transmissão de blocos de 10k. O SO foi um Suse 8. Com nio voce pode apenas usar file mapped shm, que pode gerar algum overhead em relação a named shm.

Eu já tinha ouvido que a implementação de mmio no Java não tava legal ainda, mas não sabia que era para tanto, eu esperava algo em torno de uns 600mB/s. Vale lembrar também que essa performance para sockets é artificial dado que foi obtida inproc.

SIm luca, aminha pergunta tem a ver sim, eu num estou muito contente em ter que fazer a “coversacao” entre os dois sistemas via SHM, pois acredito que seja mais dificil a sua implementacao com relacao ao Socket.

E outra estou pensando em fazer com que as aplicacoes possao ser distribuidas entre varias maquinas mais facilmente.

Eu conheco SHM em C, e sei que não muito agradavel controlar e fazer ela funcionar, meu medo é que em JAVA tambem seja chato a sua implementacao.

Em java usar shm para IPC é loucura, só vale a pena quando voce tem algo como 1 lista de valores a compartilhar e apenas alguns itens dela vão ser alterados. Fazer isso com sockets exigiria um protocolo não trivial.

Duas coisas que tornam shm em java ruim de trabalhar:

-voce não tem como criar locks ou objetos nela.
-exige backing storage em 1 arquivo.

O comum é vc usar shm com um canal paralelo de notificação e sincronização, algo como 1 pipe, file lock ou socket.

Se sockets te resolvem o problema, maravilha, se eles ainda não derem conta do recado, faça a aplicação em C criar um named pipe ou unix socket e a aplicação java usa como se fosse um arquivo.