diff --git a/contrib/fb303/java/FacebookService.java b/contrib/fb303/java/FacebookService.java
new file mode 100644
index 0000000..b7a23dd
--- /dev/null
+++ b/contrib/fb303/java/FacebookService.java
@@ -0,0 +1,2057 @@
+/**
+ * Autogenerated by Thrift
+ *
+ * DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+ */
+package com.facebook.fb303;
+
+import java.util.ArrayList;
+import java.util.AbstractMap;
+import java.util.HashMap;
+import java.util.HashSet;
+import com.facebook.thrift.*;
+
+import com.facebook.thrift.protocol.*;
+import com.facebook.thrift.transport.*;
+
+public class FacebookService {
+
+  public interface Iface {
+    public String getName() throws TException;
+    public String getVersion() throws TException;
+    public int getStatus() throws TException;
+    public String getStatusDetails() throws TException;
+    public AbstractMap<String,Long> getCounters() throws TException;
+    public long getCounter(String key) throws TException;
+    public void setOption(String key, String value) throws TException;
+    public String getOption(String key) throws TException;
+    public AbstractMap<String,String> getOptions() throws TException;
+    public long aliveSince() throws TException;
+    public com.facebook.thrift.reflection.limited.Service getLimitedReflection() throws TException;
+    public void reinitialize() throws TException;
+    public void shutdown() throws TException;
+  }
+
+  public static class Client implements Iface {
+    public Client(TProtocol prot)
+    {
+      this(prot, prot);
+    }
+
+    public Client(TProtocol iprot, TProtocol oprot)
+    {
+      iprot_ = iprot;
+      oprot_ = oprot;
+    }
+
+    protected TProtocol iprot_;
+    protected TProtocol oprot_;
+
+    protected int seqid_;
+
+    public String getName() throws TException
+    {
+      send_getName();
+      return recv_getName();
+    }
+
+    public void send_getName() throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("getName", TMessageType.CALL, seqid_));
+      getName_args args = new getName_args();
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public String recv_getName() throws TException
+    {
+      TMessage msg = iprot_.readMessageBegin();
+      if (msg.type == TMessageType.EXCEPTION) {
+        TApplicationException x = TApplicationException.read(iprot_);
+        iprot_.readMessageEnd();
+        throw x;
+      }
+      getName_result result = new getName_result();
+      result.read(iprot_);
+      iprot_.readMessageEnd();
+      if (result.__isset.success) {
+        return result.success;
+      }
+      throw new TApplicationException(TApplicationException.MISSING_RESULT, "getName failed: unknown result");
+    }
+
+    public String getVersion() throws TException
+    {
+      send_getVersion();
+      return recv_getVersion();
+    }
+
+    public void send_getVersion() throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("getVersion", TMessageType.CALL, seqid_));
+      getVersion_args args = new getVersion_args();
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public String recv_getVersion() throws TException
+    {
+      TMessage msg = iprot_.readMessageBegin();
+      if (msg.type == TMessageType.EXCEPTION) {
+        TApplicationException x = TApplicationException.read(iprot_);
+        iprot_.readMessageEnd();
+        throw x;
+      }
+      getVersion_result result = new getVersion_result();
+      result.read(iprot_);
+      iprot_.readMessageEnd();
+      if (result.__isset.success) {
+        return result.success;
+      }
+      throw new TApplicationException(TApplicationException.MISSING_RESULT, "getVersion failed: unknown result");
+    }
+
+    public int getStatus() throws TException
+    {
+      send_getStatus();
+      return recv_getStatus();
+    }
+
+    public void send_getStatus() throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("getStatus", TMessageType.CALL, seqid_));
+      getStatus_args args = new getStatus_args();
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public int recv_getStatus() throws TException
+    {
+      TMessage msg = iprot_.readMessageBegin();
+      if (msg.type == TMessageType.EXCEPTION) {
+        TApplicationException x = TApplicationException.read(iprot_);
+        iprot_.readMessageEnd();
+        throw x;
+      }
+      getStatus_result result = new getStatus_result();
+      result.read(iprot_);
+      iprot_.readMessageEnd();
+      if (result.__isset.success) {
+        return result.success;
+      }
+      throw new TApplicationException(TApplicationException.MISSING_RESULT, "getStatus failed: unknown result");
+    }
+
+    public String getStatusDetails() throws TException
+    {
+      send_getStatusDetails();
+      return recv_getStatusDetails();
+    }
+
+    public void send_getStatusDetails() throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("getStatusDetails", TMessageType.CALL, seqid_));
+      getStatusDetails_args args = new getStatusDetails_args();
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public String recv_getStatusDetails() throws TException
+    {
+      TMessage msg = iprot_.readMessageBegin();
+      if (msg.type == TMessageType.EXCEPTION) {
+        TApplicationException x = TApplicationException.read(iprot_);
+        iprot_.readMessageEnd();
+        throw x;
+      }
+      getStatusDetails_result result = new getStatusDetails_result();
+      result.read(iprot_);
+      iprot_.readMessageEnd();
+      if (result.__isset.success) {
+        return result.success;
+      }
+      throw new TApplicationException(TApplicationException.MISSING_RESULT, "getStatusDetails failed: unknown result");
+    }
+
+    public AbstractMap<String,Long> getCounters() throws TException
+    {
+      send_getCounters();
+      return recv_getCounters();
+    }
+
+    public void send_getCounters() throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("getCounters", TMessageType.CALL, seqid_));
+      getCounters_args args = new getCounters_args();
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public AbstractMap<String,Long> recv_getCounters() throws TException
+    {
+      TMessage msg = iprot_.readMessageBegin();
+      if (msg.type == TMessageType.EXCEPTION) {
+        TApplicationException x = TApplicationException.read(iprot_);
+        iprot_.readMessageEnd();
+        throw x;
+      }
+      getCounters_result result = new getCounters_result();
+      result.read(iprot_);
+      iprot_.readMessageEnd();
+      if (result.__isset.success) {
+        return result.success;
+      }
+      throw new TApplicationException(TApplicationException.MISSING_RESULT, "getCounters failed: unknown result");
+    }
+
+    public long getCounter(String key) throws TException
+    {
+      send_getCounter(key);
+      return recv_getCounter();
+    }
+
+    public void send_getCounter(String key) throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("getCounter", TMessageType.CALL, seqid_));
+      getCounter_args args = new getCounter_args();
+      args.key = key;
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public long recv_getCounter() throws TException
+    {
+      TMessage msg = iprot_.readMessageBegin();
+      if (msg.type == TMessageType.EXCEPTION) {
+        TApplicationException x = TApplicationException.read(iprot_);
+        iprot_.readMessageEnd();
+        throw x;
+      }
+      getCounter_result result = new getCounter_result();
+      result.read(iprot_);
+      iprot_.readMessageEnd();
+      if (result.__isset.success) {
+        return result.success;
+      }
+      throw new TApplicationException(TApplicationException.MISSING_RESULT, "getCounter failed: unknown result");
+    }
+
+    public void setOption(String key, String value) throws TException
+    {
+      send_setOption(key, value);
+      recv_setOption();
+    }
+
+    public void send_setOption(String key, String value) throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("setOption", TMessageType.CALL, seqid_));
+      setOption_args args = new setOption_args();
+      args.key = key;
+      args.value = value;
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public void recv_setOption() throws TException
+    {
+      TMessage msg = iprot_.readMessageBegin();
+      if (msg.type == TMessageType.EXCEPTION) {
+        TApplicationException x = TApplicationException.read(iprot_);
+        iprot_.readMessageEnd();
+        throw x;
+      }
+      setOption_result result = new setOption_result();
+      result.read(iprot_);
+      iprot_.readMessageEnd();
+      return;
+    }
+
+    public String getOption(String key) throws TException
+    {
+      send_getOption(key);
+      return recv_getOption();
+    }
+
+    public void send_getOption(String key) throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("getOption", TMessageType.CALL, seqid_));
+      getOption_args args = new getOption_args();
+      args.key = key;
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public String recv_getOption() throws TException
+    {
+      TMessage msg = iprot_.readMessageBegin();
+      if (msg.type == TMessageType.EXCEPTION) {
+        TApplicationException x = TApplicationException.read(iprot_);
+        iprot_.readMessageEnd();
+        throw x;
+      }
+      getOption_result result = new getOption_result();
+      result.read(iprot_);
+      iprot_.readMessageEnd();
+      if (result.__isset.success) {
+        return result.success;
+      }
+      throw new TApplicationException(TApplicationException.MISSING_RESULT, "getOption failed: unknown result");
+    }
+
+    public AbstractMap<String,String> getOptions() throws TException
+    {
+      send_getOptions();
+      return recv_getOptions();
+    }
+
+    public void send_getOptions() throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("getOptions", TMessageType.CALL, seqid_));
+      getOptions_args args = new getOptions_args();
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public AbstractMap<String,String> recv_getOptions() throws TException
+    {
+      TMessage msg = iprot_.readMessageBegin();
+      if (msg.type == TMessageType.EXCEPTION) {
+        TApplicationException x = TApplicationException.read(iprot_);
+        iprot_.readMessageEnd();
+        throw x;
+      }
+      getOptions_result result = new getOptions_result();
+      result.read(iprot_);
+      iprot_.readMessageEnd();
+      if (result.__isset.success) {
+        return result.success;
+      }
+      throw new TApplicationException(TApplicationException.MISSING_RESULT, "getOptions failed: unknown result");
+    }
+
+    public long aliveSince() throws TException
+    {
+      send_aliveSince();
+      return recv_aliveSince();
+    }
+
+    public void send_aliveSince() throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("aliveSince", TMessageType.CALL, seqid_));
+      aliveSince_args args = new aliveSince_args();
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public long recv_aliveSince() throws TException
+    {
+      TMessage msg = iprot_.readMessageBegin();
+      if (msg.type == TMessageType.EXCEPTION) {
+        TApplicationException x = TApplicationException.read(iprot_);
+        iprot_.readMessageEnd();
+        throw x;
+      }
+      aliveSince_result result = new aliveSince_result();
+      result.read(iprot_);
+      iprot_.readMessageEnd();
+      if (result.__isset.success) {
+        return result.success;
+      }
+      throw new TApplicationException(TApplicationException.MISSING_RESULT, "aliveSince failed: unknown result");
+    }
+
+    public com.facebook.thrift.reflection.limited.Service getLimitedReflection() throws TException
+    {
+      send_getLimitedReflection();
+      return recv_getLimitedReflection();
+    }
+
+    public void send_getLimitedReflection() throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("getLimitedReflection", TMessageType.CALL, seqid_));
+      getLimitedReflection_args args = new getLimitedReflection_args();
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public com.facebook.thrift.reflection.limited.Service recv_getLimitedReflection() throws TException
+    {
+      TMessage msg = iprot_.readMessageBegin();
+      if (msg.type == TMessageType.EXCEPTION) {
+        TApplicationException x = TApplicationException.read(iprot_);
+        iprot_.readMessageEnd();
+        throw x;
+      }
+      getLimitedReflection_result result = new getLimitedReflection_result();
+      result.read(iprot_);
+      iprot_.readMessageEnd();
+      if (result.__isset.success) {
+        return result.success;
+      }
+      throw new TApplicationException(TApplicationException.MISSING_RESULT, "getLimitedReflection failed: unknown result");
+    }
+
+    public void reinitialize() throws TException
+    {
+      send_reinitialize();
+    }
+
+    public void send_reinitialize() throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("reinitialize", TMessageType.CALL, seqid_));
+      reinitialize_args args = new reinitialize_args();
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+    public void shutdown() throws TException
+    {
+      send_shutdown();
+    }
+
+    public void send_shutdown() throws TException
+    {
+      oprot_.writeMessageBegin(new TMessage("shutdown", TMessageType.CALL, seqid_));
+      shutdown_args args = new shutdown_args();
+      args.write(oprot_);
+      oprot_.writeMessageEnd();
+      oprot_.getTransport().flush();
+    }
+
+  }
+  public static class Processor implements TProcessor {
+    public Processor(Iface iface)
+    {
+      iface_ = iface;
+      processMap_.put("getName", new getName());
+      processMap_.put("getVersion", new getVersion());
+      processMap_.put("getStatus", new getStatus());
+      processMap_.put("getStatusDetails", new getStatusDetails());
+      processMap_.put("getCounters", new getCounters());
+      processMap_.put("getCounter", new getCounter());
+      processMap_.put("setOption", new setOption());
+      processMap_.put("getOption", new getOption());
+      processMap_.put("getOptions", new getOptions());
+      processMap_.put("aliveSince", new aliveSince());
+      processMap_.put("getLimitedReflection", new getLimitedReflection());
+      processMap_.put("reinitialize", new reinitialize());
+      processMap_.put("shutdown", new shutdown());
+    }
+
+    protected static interface ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException;
+    }
+
+    private Iface iface_;
+    protected final HashMap<String,ProcessFunction> processMap_ = new HashMap<String,ProcessFunction>();
+
+    public boolean process(TProtocol iprot, TProtocol oprot) throws TException
+    {
+      TMessage msg = iprot.readMessageBegin();
+      ProcessFunction fn = processMap_.get(msg.name);
+      if (fn == null) {
+        TProtocolUtil.skip(iprot, TType.STRUCT);
+        iprot.readMessageEnd();
+        TApplicationException x = new TApplicationException(TApplicationException.UNKNOWN_METHOD, "Invalid method name: '"+msg.name+"'");
+        oprot.writeMessageBegin(new TMessage(msg.name, TMessageType.EXCEPTION, msg.seqid));
+        x.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+        return true;
+      }
+      fn.process(msg.seqid, iprot, oprot);
+      return true;
+    }
+
+    private class getName implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        getName_args args = new getName_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        getName_result result = new getName_result();
+        result.success = iface_.getName();
+        result.__isset.success = true;
+        oprot.writeMessageBegin(new TMessage("getName", TMessageType.REPLY, seqid));
+        result.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+      }
+
+    }
+
+    private class getVersion implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        getVersion_args args = new getVersion_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        getVersion_result result = new getVersion_result();
+        result.success = iface_.getVersion();
+        result.__isset.success = true;
+        oprot.writeMessageBegin(new TMessage("getVersion", TMessageType.REPLY, seqid));
+        result.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+      }
+
+    }
+
+    private class getStatus implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        getStatus_args args = new getStatus_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        getStatus_result result = new getStatus_result();
+        result.success = iface_.getStatus();
+        result.__isset.success = true;
+        oprot.writeMessageBegin(new TMessage("getStatus", TMessageType.REPLY, seqid));
+        result.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+      }
+
+    }
+
+    private class getStatusDetails implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        getStatusDetails_args args = new getStatusDetails_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        getStatusDetails_result result = new getStatusDetails_result();
+        result.success = iface_.getStatusDetails();
+        result.__isset.success = true;
+        oprot.writeMessageBegin(new TMessage("getStatusDetails", TMessageType.REPLY, seqid));
+        result.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+      }
+
+    }
+
+    private class getCounters implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        getCounters_args args = new getCounters_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        getCounters_result result = new getCounters_result();
+        result.success = iface_.getCounters();
+        result.__isset.success = true;
+        oprot.writeMessageBegin(new TMessage("getCounters", TMessageType.REPLY, seqid));
+        result.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+      }
+
+    }
+
+    private class getCounter implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        getCounter_args args = new getCounter_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        getCounter_result result = new getCounter_result();
+        result.success = iface_.getCounter(args.key);
+        result.__isset.success = true;
+        oprot.writeMessageBegin(new TMessage("getCounter", TMessageType.REPLY, seqid));
+        result.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+      }
+
+    }
+
+    private class setOption implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        setOption_args args = new setOption_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        setOption_result result = new setOption_result();
+        iface_.setOption(args.key, args.value);
+        oprot.writeMessageBegin(new TMessage("setOption", TMessageType.REPLY, seqid));
+        result.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+      }
+
+    }
+
+    private class getOption implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        getOption_args args = new getOption_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        getOption_result result = new getOption_result();
+        result.success = iface_.getOption(args.key);
+        result.__isset.success = true;
+        oprot.writeMessageBegin(new TMessage("getOption", TMessageType.REPLY, seqid));
+        result.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+      }
+
+    }
+
+    private class getOptions implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        getOptions_args args = new getOptions_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        getOptions_result result = new getOptions_result();
+        result.success = iface_.getOptions();
+        result.__isset.success = true;
+        oprot.writeMessageBegin(new TMessage("getOptions", TMessageType.REPLY, seqid));
+        result.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+      }
+
+    }
+
+    private class aliveSince implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        aliveSince_args args = new aliveSince_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        aliveSince_result result = new aliveSince_result();
+        result.success = iface_.aliveSince();
+        result.__isset.success = true;
+        oprot.writeMessageBegin(new TMessage("aliveSince", TMessageType.REPLY, seqid));
+        result.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+      }
+
+    }
+
+    private class getLimitedReflection implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        getLimitedReflection_args args = new getLimitedReflection_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        getLimitedReflection_result result = new getLimitedReflection_result();
+        result.success = iface_.getLimitedReflection();
+        result.__isset.success = true;
+        oprot.writeMessageBegin(new TMessage("getLimitedReflection", TMessageType.REPLY, seqid));
+        result.write(oprot);
+        oprot.writeMessageEnd();
+        oprot.getTransport().flush();
+      }
+
+    }
+
+    private class reinitialize implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        reinitialize_args args = new reinitialize_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        iface_.reinitialize();
+        return;
+      }
+    }
+
+    private class shutdown implements ProcessFunction {
+      public void process(int seqid, TProtocol iprot, TProtocol oprot) throws TException
+      {
+        shutdown_args args = new shutdown_args();
+        args.read(iprot);
+        iprot.readMessageEnd();
+        iface_.shutdown();
+        return;
+      }
+    }
+
+  }
+
+  public static class getName_args   {
+    public getName_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getName_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getName_args(");
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getName_result   {
+    public String success;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean success = false;
+    }
+
+    public getName_result() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 0:
+            if (field.type == TType.STRING) {
+              this.success = iprot.readString();
+              this.__isset.success = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getName_result");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+
+      if (this.__isset.success) {
+        if (this.success != null) {
+          field.name = "success";
+          field.type = TType.STRING;
+          field.id = 0;
+          oprot.writeFieldBegin(field);
+          oprot.writeString(this.success);
+          oprot.writeFieldEnd();
+        }
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getName_result(");
+      sb.append("success:");
+      sb.append(this.success);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getVersion_args   {
+    public getVersion_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getVersion_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getVersion_args(");
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getVersion_result   {
+    public String success;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean success = false;
+    }
+
+    public getVersion_result() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 0:
+            if (field.type == TType.STRING) {
+              this.success = iprot.readString();
+              this.__isset.success = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getVersion_result");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+
+      if (this.__isset.success) {
+        if (this.success != null) {
+          field.name = "success";
+          field.type = TType.STRING;
+          field.id = 0;
+          oprot.writeFieldBegin(field);
+          oprot.writeString(this.success);
+          oprot.writeFieldEnd();
+        }
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getVersion_result(");
+      sb.append("success:");
+      sb.append(this.success);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getStatus_args   {
+    public getStatus_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getStatus_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getStatus_args(");
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getStatus_result   {
+    public int success;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean success = false;
+    }
+
+    public getStatus_result() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 0:
+            if (field.type == TType.I32) {
+              this.success = iprot.readI32();
+              this.__isset.success = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getStatus_result");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+
+      if (this.__isset.success) {
+        field.name = "success";
+        field.type = TType.I32;
+        field.id = 0;
+        oprot.writeFieldBegin(field);
+        oprot.writeI32(this.success);
+        oprot.writeFieldEnd();
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getStatus_result(");
+      sb.append("success:");
+      sb.append(this.success);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getStatusDetails_args   {
+    public getStatusDetails_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getStatusDetails_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getStatusDetails_args(");
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getStatusDetails_result   {
+    public String success;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean success = false;
+    }
+
+    public getStatusDetails_result() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 0:
+            if (field.type == TType.STRING) {
+              this.success = iprot.readString();
+              this.__isset.success = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getStatusDetails_result");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+
+      if (this.__isset.success) {
+        if (this.success != null) {
+          field.name = "success";
+          field.type = TType.STRING;
+          field.id = 0;
+          oprot.writeFieldBegin(field);
+          oprot.writeString(this.success);
+          oprot.writeFieldEnd();
+        }
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getStatusDetails_result(");
+      sb.append("success:");
+      sb.append(this.success);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getCounters_args   {
+    public getCounters_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getCounters_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getCounters_args(");
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getCounters_result   {
+    public AbstractMap<String,Long> success;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean success = false;
+    }
+
+    public getCounters_result() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 0:
+            if (field.type == TType.MAP) {
+              {
+                TMap _map0 = iprot.readMapBegin();
+                this.success = new HashMap<String,Long>(2*_map0.size);
+                for (int _i1 = 0; _i1 < _map0.size; ++_i1)
+                {
+                  String _key2;
+                  long _val3;
+                  _key2 = iprot.readString();
+                  _val3 = iprot.readI64();
+                  this.success.put(_key2, _val3);
+                }
+                iprot.readMapEnd();
+              }
+              this.__isset.success = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getCounters_result");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+
+      if (this.__isset.success) {
+        if (this.success != null) {
+          field.name = "success";
+          field.type = TType.MAP;
+          field.id = 0;
+          oprot.writeFieldBegin(field);
+          {
+            oprot.writeMapBegin(new TMap(TType.STRING, TType.I64, this.success.size()));
+            for (String _iter4 : this.success.keySet())            {
+              oprot.writeString(_iter4);
+              oprot.writeI64(this.success.get(_iter4));
+              oprot.writeMapEnd();
+            }
+          }
+          oprot.writeFieldEnd();
+        }
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getCounters_result(");
+      sb.append("success:");
+      sb.append(this.success);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getCounter_args   {
+    public String key;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean key = false;
+    }
+
+    public getCounter_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 1:
+            if (field.type == TType.STRING) {
+              this.key = iprot.readString();
+              this.__isset.key = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getCounter_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      if (this.key != null) {
+        field.name = "key";
+        field.type = TType.STRING;
+        field.id = 1;
+        oprot.writeFieldBegin(field);
+        oprot.writeString(this.key);
+        oprot.writeFieldEnd();
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getCounter_args(");
+      sb.append("key:");
+      sb.append(this.key);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getCounter_result   {
+    public long success;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean success = false;
+    }
+
+    public getCounter_result() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 0:
+            if (field.type == TType.I64) {
+              this.success = iprot.readI64();
+              this.__isset.success = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getCounter_result");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+
+      if (this.__isset.success) {
+        field.name = "success";
+        field.type = TType.I64;
+        field.id = 0;
+        oprot.writeFieldBegin(field);
+        oprot.writeI64(this.success);
+        oprot.writeFieldEnd();
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getCounter_result(");
+      sb.append("success:");
+      sb.append(this.success);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class setOption_args   {
+    public String key;
+    public String value;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean key = false;
+      public boolean value = false;
+    }
+
+    public setOption_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 1:
+            if (field.type == TType.STRING) {
+              this.key = iprot.readString();
+              this.__isset.key = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          case 2:
+            if (field.type == TType.STRING) {
+              this.value = iprot.readString();
+              this.__isset.value = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("setOption_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      if (this.key != null) {
+        field.name = "key";
+        field.type = TType.STRING;
+        field.id = 1;
+        oprot.writeFieldBegin(field);
+        oprot.writeString(this.key);
+        oprot.writeFieldEnd();
+      }
+      if (this.value != null) {
+        field.name = "value";
+        field.type = TType.STRING;
+        field.id = 2;
+        oprot.writeFieldBegin(field);
+        oprot.writeString(this.value);
+        oprot.writeFieldEnd();
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("setOption_args(");
+      sb.append("key:");
+      sb.append(this.key);
+      sb.append(",value:");
+      sb.append(this.value);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class setOption_result   {
+    public setOption_result() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("setOption_result");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("setOption_result(");
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getOption_args   {
+    public String key;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean key = false;
+    }
+
+    public getOption_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 1:
+            if (field.type == TType.STRING) {
+              this.key = iprot.readString();
+              this.__isset.key = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getOption_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      if (this.key != null) {
+        field.name = "key";
+        field.type = TType.STRING;
+        field.id = 1;
+        oprot.writeFieldBegin(field);
+        oprot.writeString(this.key);
+        oprot.writeFieldEnd();
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getOption_args(");
+      sb.append("key:");
+      sb.append(this.key);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getOption_result   {
+    public String success;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean success = false;
+    }
+
+    public getOption_result() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 0:
+            if (field.type == TType.STRING) {
+              this.success = iprot.readString();
+              this.__isset.success = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getOption_result");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+
+      if (this.__isset.success) {
+        if (this.success != null) {
+          field.name = "success";
+          field.type = TType.STRING;
+          field.id = 0;
+          oprot.writeFieldBegin(field);
+          oprot.writeString(this.success);
+          oprot.writeFieldEnd();
+        }
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getOption_result(");
+      sb.append("success:");
+      sb.append(this.success);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getOptions_args   {
+    public getOptions_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getOptions_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getOptions_args(");
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getOptions_result   {
+    public AbstractMap<String,String> success;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean success = false;
+    }
+
+    public getOptions_result() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 0:
+            if (field.type == TType.MAP) {
+              {
+                TMap _map5 = iprot.readMapBegin();
+                this.success = new HashMap<String,String>(2*_map5.size);
+                for (int _i6 = 0; _i6 < _map5.size; ++_i6)
+                {
+                  String _key7;
+                  String _val8;
+                  _key7 = iprot.readString();
+                  _val8 = iprot.readString();
+                  this.success.put(_key7, _val8);
+                }
+                iprot.readMapEnd();
+              }
+              this.__isset.success = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getOptions_result");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+
+      if (this.__isset.success) {
+        if (this.success != null) {
+          field.name = "success";
+          field.type = TType.MAP;
+          field.id = 0;
+          oprot.writeFieldBegin(field);
+          {
+            oprot.writeMapBegin(new TMap(TType.STRING, TType.STRING, this.success.size()));
+            for (String _iter9 : this.success.keySet())            {
+              oprot.writeString(_iter9);
+              oprot.writeString(this.success.get(_iter9));
+              oprot.writeMapEnd();
+            }
+          }
+          oprot.writeFieldEnd();
+        }
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getOptions_result(");
+      sb.append("success:");
+      sb.append(this.success);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class aliveSince_args   {
+    public aliveSince_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("aliveSince_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("aliveSince_args(");
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class aliveSince_result   {
+    public long success;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean success = false;
+    }
+
+    public aliveSince_result() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 0:
+            if (field.type == TType.I64) {
+              this.success = iprot.readI64();
+              this.__isset.success = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("aliveSince_result");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+
+      if (this.__isset.success) {
+        field.name = "success";
+        field.type = TType.I64;
+        field.id = 0;
+        oprot.writeFieldBegin(field);
+        oprot.writeI64(this.success);
+        oprot.writeFieldEnd();
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("aliveSince_result(");
+      sb.append("success:");
+      sb.append(this.success);
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getLimitedReflection_args   {
+    public getLimitedReflection_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getLimitedReflection_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getLimitedReflection_args(");
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class getLimitedReflection_result   {
+    public com.facebook.thrift.reflection.limited.Service success;
+
+    public final Isset __isset = new Isset();
+    public final class Isset {
+      public boolean success = false;
+    }
+
+    public getLimitedReflection_result() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          case 0:
+            if (field.type == TType.STRUCT) {
+              this.success = new com.facebook.thrift.reflection.limited.Service();
+              this.success.read(iprot);
+              this.__isset.success = true;
+            } else { 
+              TProtocolUtil.skip(iprot, field.type);
+            }
+            break;
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("getLimitedReflection_result");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+
+      if (this.__isset.success) {
+        if (this.success != null) {
+          field.name = "success";
+          field.type = TType.STRUCT;
+          field.id = 0;
+          oprot.writeFieldBegin(field);
+          this.success.write(oprot);
+          oprot.writeFieldEnd();
+        }
+      }
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("getLimitedReflection_result(");
+      sb.append("success:");
+      sb.append(this.success.toString());
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class reinitialize_args   {
+    public reinitialize_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("reinitialize_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("reinitialize_args(");
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+  public static class shutdown_args   {
+    public shutdown_args() {
+    }
+
+    public void read(TProtocol iprot) throws TException {
+      TField field;
+      TStruct struct = iprot.readStructBegin();
+      while (true)
+      {
+        field = iprot.readFieldBegin();
+        if (field.type == TType.STOP) { 
+          break;
+        }
+        switch (field.id)
+        {
+          default:
+            TProtocolUtil.skip(iprot, field.type);
+            break;
+        }
+        iprot.readFieldEnd();
+      }
+      iprot.readStructEnd();
+    }
+
+    public void write(TProtocol oprot) throws TException {
+      TStruct struct = new TStruct("shutdown_args");
+      TField field = new TField();
+      oprot.writeStructBegin(struct);
+      oprot.writeFieldStop();
+      oprot.writeStructEnd();
+    }
+
+    public String toString() {
+      StringBuilder sb = new StringBuilder("shutdown_args(");
+      sb.append(")");
+      return sb.toString();
+    }
+
+  }
+
+}
