Hi All,

Over the last couple of weeks, I spent some time trying to generate Comm Effect 
events from Java (as opposed to Python). I thought I would post my results 
here, in case it would be of help to anyone else.

If someone has a better approach (or finds that I was not doing something the 
way I should have been), please let me know.

Down the road, we will be using a similar approach to generate other events as 
well from Java code in order to drive the behavior of EMANE.

The first step was to generate the Java source from the .proto files that were 
in the libemane directory. One problem was that it could not generate the .java 
file for event.proto because of a conflict in the class name. So, we had to 
edit Event.proto and add the following option:
    option java_outer_classname="BasicEvent";
This should probably be fixed in the event.proto file.

Then, I combined all the generated Java code into a single JAR file. The 
following Java code uses that JAR file to generate and send events that are 
equivalent to the following command:
    emaneevent-commeffect 1:4 –t 1 latency=.5


Here is my code which sends a single commeffect to all nodes 2:4 indicating a
500 msec latency value to apply to all packets received from NEM 1.

There are a couple of places that I had to do things that I was not expecting 
to. The first case is that the type of the event (CommEffectEvent), identified 
by the id 103, had to be set manually into the BasicEvent instance.

The second case is that I had to compute the length of the serialized event and 
prefix the byte array being transmitted over the network with this length. 
Again, something that I would have expected to be done automatically.

Some of this had to be done by reverse engineering the network packet generated 
by the emaneevent-commeffect command, and it took me a while to do it. If there 
are better ways to do what I have done, please let me know. Perhaps some 
additional documentation would be useful. And, I hope this example would be 
useful to others as well.

Thanks.
Maggie
______________________________________________________________________
// CommEffectEvent builder
Commeffectevent.CommEffectEvent.Builder commEffectEventBuilder = 
Commeffectevent.CommEffectEvent.newBuilder();
for (int id=2; id<=4; id++) {
    Commeffectevent.CommEffectEvent.CommEffect.Builder  commEffectBuilder =  
Commeffectevent.CommEffectEvent.CommEffect.newBuilder();
    commEffectBuilder.setLatencySeconds(0.5f);
    commEffectBuilder.setNemId(id);
    commEffectBuilder.setJitterSeconds(0);
    commEffectBuilder.setBroadcastBitRatebps(0);
    commEffectBuilder.setProbabilityDuplicate(0);
    commEffectBuilder.setUnicastBitRatebps(0);
    commEffectBuilder.setProbabilityLoss(0);

    //Need to add the commEffect to the event builder as a list
    commEffectEventBuilder.addCommEffects(commEffectBuilder);
}
ByteString commEffectEventBA = commEffectEventBuilder.build().toByteString();

// Serialization builder
EMANEMessage.BasicEvent.Event.Data.Serialization.Builder serialBuilder = 
BasicEvent.Event.Data.Serialization.newBuilder();
serialBuilder.setNemId (1);
serialBuilder.setEventId (103); // This should be done automatically, but I had 
to hard code it
serialBuilder.setData (commEffectEventBA);
serialBuilder.build();

//Basic event builder
EMANEMessage.BasicEvent.Event.Builder evtBuilder = 
EMANEMessage.BasicEvent.Event.newBuilder();

// Generate a random uuid of 16 bytes – probably a better way to do this
byte[] randomUUIDByteArray = new byte[16];
Random randomGenerator = new Random();
for (int i=0; i<16; i++) {
    int randomInt = randomGenerator.nextInt(100);
    ByteBuffer bb = ByteBuffer.wrap (randomUUIDByteArray);
    bb.putInt (randomInt);
}

ByteString uuidByteStr = ByteString.copyFrom (randomUUIDByteArray);
evtBuilder.setUuid (uuidByteStr);
evtBuilder.setSequenceNumber (1);

BasicEvent.Event.Data.Builder dataBuilder = BasicEvent.Event.Data.newBuilder();
dataBuilder.addSerializations (serialBuilder);
BasicEvent.Event.Data data = dataBuilder.build();
//Set data in the Basic event.
byte[] fullDataByteArray = evtBuilder.setData (data).build().toByteArray();

// The following code compute the length of the event and prepends the network 
packet with 2 bytes
// containing that length. Again, this probably should be done automatically
int arrayLen = fullDataByteArray.length;
byte[] newbuf = new byte [fullDataByteArray.length + 2];
ByteBuffer bb = ByteBuffer.wrap (newbuf);
bb.putShort ((short) arrayLen);
bb.put (fullDataByteArray);

while (true) {
    MulticastSocket mcs = new MulticastSocket();
    InetAddress group = InetAddress.getByName ("224.1.2.8");
    mcs.joinGroup (group);

    DatagramPacket dp = new DatagramPacket (newbuf, newbuf.length, group, 
45703);
    System.err.print("..");

    mcs.send (dp);
    Thread.sleep (1000);
}
_______________________________________________________





---------------------------------------------------------------------
Maggie R. Breedy
Research Associate
Florida Institute for Human and Machine Cognition
Pensacola, FL.
_______________________________________________
emane-users mailing list
[email protected]
http://pf.itd.nrl.navy.mil/mailman/listinfo/emane-users

Reply via email to