package org.jgroups.tests; import org.jgroups.*; import org.jgroups.jmx.JmxConfigurator; import org.jgroups.util.Util; import javax.management.MBeanServer; import java.io.InputStream; import java.io.OutputStream; /** * Tests transfer of large states. Start first instance with -provider flag and -size flag (default = 1MB). * The start second instance without these flags: it should acquire the state from the first instance. Possibly * tracing should be turned on for FRAG to see the fragmentation taking place, e.g.: * <pre> * trace1=FRAG DEBUG STDOUT * </pre><br> * Note that because fragmentation might generate a lot of small fragments at basically the same time (e.g. size1MB, * FRAG.frag-size=4096 generates a lot of fragments), the send buffer of the unicast socket in UDP might be overloaded, * causing it to drop some packets (default size is 8096 bytes). Therefore the send (and receive) buffers for the unicast * socket have been increased (see ucast_send_buf_size and ucast_recv_buf_size below).<p> * If we didn't do this, we would have some retransmission, slowing the state transfer down. * * @author Bela Ban Dec 13 2001 */ public class LargeState extends ReceiverAdapter { Channel channel; byte[] state=null; boolean rc=false; String props; long start, stop; boolean provider=true, provider_fails=false, requester_fails=false; int size=100000; int total_received=0; long delay=0; public void start(boolean provider, int size, String props, boolean provider_fails, boolean requester_fails, long delay, String name) throws Exception { this.provider=provider; this.provider_fails=provider_fails; this.requester_fails=requester_fails; this.delay=delay; channel=new JChannel(props); channel.setReceiver(this); if(name != null) channel.setName(name); channel.connect("TestChannel"); MBeanServer server=Util.getMBeanServer(); if(server == null) throw new Exception("No MBeanServers found;" + "\nLargeState needs to be run with an MBeanServer present, or inside JDK 5"); JmxConfigurator.registerChannel((JChannel)channel, server, "jgroups", channel.getClusterName(), true); System.out.println("-- connected to channel"); if(provider) { this.size=size; System.out.println("Waiting for other members to join and fetch large state"); for(;;) { Util.sleep(10000); } } start=System.currentTimeMillis(); try { channel.getState(null, 0); } catch(Exception ex) { ex.printStackTrace(); } finally { Util.close(channel); } } static byte[] createLargeState(int size) { return new byte[size]; } public void receive(Message msg) { System.out.println("-- received msg " + msg.getObject() + " from " + msg.getSrc()); } public void viewAccepted(View new_view) { if(provider) System.out.println("-- view: " + new_view); } public void setState(InputStream istream) throws Exception { total_received=0; int received=0; while(true) { byte[] buf=new byte[10000]; received=istream.read(buf); if(received < 0) break; if(delay > 0) Util.sleep(delay); total_received+=received; if(requester_fails) throw new Exception("booom - requester failed"); } stop=System.currentTimeMillis(); System.out.println("<-- received " + Util.printBytes(total_received) + " in " + (stop-start) + "ms"); } public void getState(OutputStream ostream) throws Exception { int frag_size=size / 10; long bytes=0; for(int i=0; i < 10; i++) { byte[] buf=new byte[frag_size]; ostream.write(buf); bytes+=buf.length; if(provider_fails) throw new Exception("booom - provider failed"); if(delay > 0) Util.sleep(delay); } int remaining=size - (10 * frag_size); if(remaining > 0) { byte[] buf=new byte[remaining]; ostream.write(buf); bytes+=buf.length; } System.out.println("--> wrote " + Util.printBytes(bytes)); } public static void main(String[] args) { boolean provider=false, provider_fails=false, requester_fails=false; int size=1024 * 1024; String props=null; long delay=0; String name=null; for(int i=0; i < args.length; i++) { if("-help".equals(args[i])) { help(); return; } if("-provider".equals(args[i])) { provider=true; continue; } if("-provider_fails".equals(args[i])) { provider_fails=true; continue; } if("-requester_fails".equals(args[i])) { requester_fails=true; continue; } if("-size".equals(args[i])) { size=Integer.parseInt(args[++i]); continue; } if("-props".equals(args[i])) { props=args[++i]; continue; } if("-delay".equals(args[i])) { delay=Long.parseLong(args[++i]); continue; } if("-name".equals(args[i])) { name=args[++i]; continue; } help(); return; } try { new LargeState().start(provider, size, props, provider_fails, requester_fails, delay, name); } catch(Exception e) { e.printStackTrace(); } } static void help() { System.out.println("LargeState [-help] [-size <size of state in bytes] [-provider] [-name name] " + "[-props <properties>] [-provider_fails] [-requester_fails] [-delay <ms>]"); } }